In my web site I'm getting data from xml in first controller action method and display as dropdown (html select and option).When a user selects an item in first dropdown, selected item sent to the next view's controller as a parameter using jquery $.post. I have keep breakpoints and see what is going on. Data trasfer is success until second view . But display nothing. I have attached screenshot of my break points and codes.
This is my controllers.
public ActionResult First()
{
//get the location data
var Loc = getData("Location", "", "", "");
List<FirstData> Ilc = new List<FirstData>();
foreach(var val in Loc)
{
Ilc.Add(new Firstdata
{
Destination = val
});
}
ViewBag.Loc = Ilc;
return View();
}
this is how I pass data from first view to second action controller method
<script type:"text/javascript">
$(document).ready(function() {
$("#chk a").addCIass("btn btn-default");
$("#chk a").click(function () {
var url = '#Url.Action("Check","Cruise")';
$.post(url, { LocNane: $("#desti").val() }, function (data) {
//alert("succes");
});
});
});
</script>
this is how my second controller gets pass data[I made a breakpoint here]
public ActionResult Check(string LocName)
{
string d = LocNane;
var Nan = getData('Location',"Name",d,"");
List<Seconddata> nf = new List<Seconddata>();
foreach (var val in Nam)
{
nf.Add(new Seconddata
{
Naneof = val
});
}
ViewBag.Nn = nf;
}
and this is my second view and display data in break point
<body>
<div>
#foreach( var item in #VieuBag.Nm)
{
<h3>one</h3>
}
</div>
</body>
I put "#item.Nameof" inside the header tags , but it didn't work. so just to chek I put one. after go through the loop nothing display.what's the wrong.please help me with this.
The problem here is the success handler of $.post does not append/insert the returned html in any element. You can do something like this in success handler where divId is element Id in page where you want to show the returned html.
$("#divId").append(data);
Related
$(".category-sub-opition-list li").click(function () {
var id = $(this).attr("id");
var category = getUrlParameter('category');
#{
var category = Request.QueryString["category"];
var cat = Model.Items.Where(i => i.Id.ToString() == category).FirstOrDefault();
if(cat==null)
{
Code to Redirec to page
}
}
});
in JQuery I want to check Model list, whether the option is available in List or not, If category does not exists in list, I want to redirect page.
I don't recommend writing razor inside js in this way with so may blocks. Create a separate function
#{
var category = Request.QueryString["category"];
var cat = Model.Items.Where(i => i.Id.ToString() == category).FirstOrDefault();
if(cat==null)
{
<script>
function redirectIfNeeded(){
window.location = "#Url.Action()";
// yes here using razor should be fine since it is just a line.
//You can also hard code the url.
}
</script>
}
}
You can now call your js function under var category = getUrlParameter('category'); without the razor code.
I'm unsure if this is possible but I want to use jQuery to assign value from my bound model to different textboxes inside a PartialView.
Originally when the page loads, it populates correctly with all of the model information. However I would like to implement a DDL to view historical updates (retrieved from my pre-populated DB).
I am able to call an Action method inside my respective controller which accepts a revisionID. I have verified that the method is returning the correct data.
Please see below for my code snippets:
Partial View:
$('#revisionDDL').change(function () {
var selectedRevisionID = $(this).val();
if (selectedRevisionID == '') {
selectedRevisionID = #Model.RevisionID - 1;
}
var url = '#Url.Action("GetAgreementByRevision")';
$.get(url, { revisionID: selectedRevisionID }, function () {
$('#ChangeReason').val('#Model.ChangeReason');
})
});
Input element:
<div class="input-group">
<span class="input-group-addon" id="change-reason">Change Reason</span>
#Html.TextAreaFor(m => m.ChangeReason, new { #class = "form-control", #rows = "1" })
</div>
Controller method:
public ActionResult GetAgreementByRevision(int revisionID)
{
Agreement revisedAgreement = new Agreement();
revisedAgreement = _agreementService.GetAgreementDetailsByRevision(revisionID);
return PartialView("AgreementDetailsFormPartial", revisedAgreement);
}
If I am not able to accomplish this, what would be my other options?
Your method in the controller returns PartialView which returns HTML content and you're trying to pass that HTML content as a value in the text area - this is not how it should work. You should return Json(revisedAgreement, JsonRequestBehavior.AllowGet); and then access this object in JavaScript.
$.get(url, { revisionID: selectedRevisionID }, function (data) {
// 'data' is your Agreement object
$('#ChangeReason').val(data.SomePropertyHere);
});
VS2013, WebForms, .NET 4.51
I want to use a hidden field to maintain the contents of my Knock Out view model across postbacks. So I took the KO code from http://knockoutjs.com/examples/cartEditor.html and then read http://www.codeproject.com/Articles/153735/Using-KnockoutJS-in-your-ASP-NET-applications for some ideas.
The end result is the following:
<asp:HiddenField ID="HiddenField1" runat="server" />
<script type='text/javascript' src="http://knockoutjs.com/examples/resources/sampleProductCategories.js"></script>
<script type="text/javascript">
function formatCurrency(value) {
return "$" + value.toFixed(2);
}
var CartLine = function () {
var self = this;
self.category = ko.observable();
self.product = ko.observable();
self.quantity = ko.observable(1);
self.subtotal = ko.computed(function () {
return self.product() ? self.product().price * parseInt("0" + self.quantity(), 10) : 0;
});
// Whenever the category changes, reset the product selection
self.category.subscribe(function () {
self.product(undefined);
});
};
var Cart = function () {
// Stores an array of lines, and from these, can work out the grandTotal
var self = this;
self.lines = ko.observableArray([new CartLine()]); // Put one line in by default
self.grandTotal = ko.computed(function () {
var total = 0;
$.each(self.lines(), function () { total += this.subtotal() })
return total;
});
// Operations
self.addLine = function() {
self.lines.push(new CartLine());
SaveList();
};
self.removeLine = function(line) {
self.lines.remove(line);
SaveList();
};
self.save = function () {
var dataToSave = $.map(self.lines(), function (line) {
return line.product() ? {
productName: line.product().name,
quantity: line.quantity()
} : undefined
});
alert("Could now send this to server: " + JSON.stringify(dataToSave));
};
self.SaveList = function () {
var myHidden = document.getElementById('<%= HiddenField1.ClientID %>');
if (myHidden)//checking whether it is found on DOM, but not necessary
{
var dataToSave = $.map(self.lines(), function (line) {
return line.product() ? {
productName: line.product().name,
quantity: line.quantity()
} : undefined;
});
alert("Saving - " + JSON.stringify(dataToSave));
myHidden.value = JSON.stringify(dataToSave);
}
};
};
var stringViewModel = document.getElementById('<%=HiddenField1.ClientID %>').value;
var viewModel;
if (document.getElementById('<%=HiddenField1.ClientID %>').value == '') {
alert('Nothing In Hidden Field');
viewModel = new Cart();
} else {
viewModel = ko.utils.parseJson(stringViewModel);
for (var propertyName in viewModel) {
viewModel[propertyName] = ko.observable(viewModel[propertyName]);
}
}
ko.applyBindings(viewModel);
$(document.forms[0]).submit(function () {
alert('In Submit');
viewModel.SaveList();
});
</script>
So basically when the page loads we create a new instance of the Cart. And when the form is posted we successfully have the cart serialized to HiddenField1 and I can see the expected value in the code behind:
protected void btnSave_OnClick(object aSender, EventArgs aE)
{
if (HiddenField1.Value == null)
{
}
}
however after the postback the contents of stringViewModel
var stringViewModel = document.getElementById('<%=HiddenField1.ClientID %>').value;
is always blanl / empty? Why is that?
And then assuming I have the correct JSON is the following the correct way to apply it back to the view model?
viewModel = ko.utils.parseJson(stringViewModel);
for (var propertyName in viewModel) {
viewModel[propertyName] = ko.observable(viewModel[propertyName]);
}
EDIT: I tried a few things with no luck
Added all JS code to jQuert OnReady() handler
Tried using instead of ASP:HiddenField
In all cases in PostBack I can see the value assigned to the hidden field by SaveList(), but when the page is displayed again (after postback) the value of the hidden field is an empty string
For the first part, what you're doing is correct. Use the console (press F12 in your browser) to examine the hidden field, and check if it has the value. If you see it in the server side, it should be in the client side. You can also run js code, and set breakpoints to discover what the problem is. You can also add a PreRender handler in the server side, and add a breakpoint and debug to check that the Value has not been deleted in the server side (this event happens just before the page is rendered to be sent to the browser).
For the second part, the fastest way to do what you need is to use knockout mapping, which creates a model from a JavaScript object, or from JSON. You need to use this: ko.mapping.fromJSON. This will create a new viewmodel, which you can directly bind, from your JSON. (As you can read in the docs, you can customize how the view model is created).
However, what you're doing is quite strange. You normally use Knockout with Web API, or Web Services, or Page methods, without reloading the page. The model is recovered, and updated, changed, etc. through one of those technologies, using AJAX.
I have created a dropdownlist on the view and showing a list.
#Html.DropDownListFor(m => m.SelectedId, new SelectList(Model.List, "ID", "Name"))
I want to refresh the page when the user selects the value from the drop down.
I don't know how to map the selection event from dropdown to a controller function without clicking any button.
On the view load there is a controller function which is populating the view with the list.
public ActionResult Populate()
{
List<string> list = get it from sql server
ViewModel viewModel = new ViewModel();
viewModel.list = list;
return view();
}
But how do you call a controller function which will take the selected value as an Id and retrieves the data and refreshes the page with the result.
You can't do it without javascript help. Just bind on select event and send the form or make an ajax request.
using jQuery:
$('#yourDropDownId').change(function(){
$('#yourFormId').submit();
});
or if you need ajax call insted of submit use $.post or $.get.
Add this to your layout in the head:
<script type="text/javascript">
$(document).ready(function () {
$('select:[autopostback=true],input[type=checkbox]:[autopostback=true],input[type=radio]:[autopostback=true]').live('change',function () {
$(this).closest('form').submit();
});
});
</script>
in your view:
#using (Html.BeginForm())
{
#Html.DropDownListFor(m => m.SelectedId, new SelectList(Model.List, "ID", "Name"), new { autopostback = "true" })
}
The form that your dropdownlist is in will get submitted when you change selection of your dropdownlist. If the result of the action of that form is the same page, it will be reloaded with whatever stuff being updated
$(document).ready(function() {
$("#ddl").change(function() {
var strSelected = "";
$("#ddl option:selected").each(function() {
strSelected += $(this)[0].value;
});
var url = "/Home/MyAction/" + strSelected;
$.post(url, function(data) {
// do something if necessary
});
});
});
or
<%=Html.DropDownListFor(m => m.SelectedId, new SelectList(Model.List, "ID", "Name"), new { onchange="this.form.submit();" })%>
It's simple. In your javascript you have:
$(document).ready(function () {
$('#SelectedId').change(function () {
var id = $(this).val();
$.getJSON("/YourController/YourAction", { id: id},
function (data) {
$("#SomeDivSelector").html(data);
});
});
});
Your controller should look like:
[AcceptVerbs(HttpVerbs.Get)]
public JsonResult YourAction(int id)
{
//do something
return Json(ControlToString("~/Views/YourController/YourView.cshtml", yourModelWithData), JsonRequestBehavior.AllowGet);
}
And ControlToString is defined:
private string ControlToString(string controlPath, object model)
{
//CshtmlView control = new CshtmlView(controlPath);
RazorView control = new RazorView(this.ControllerContext, controlPath, null, false, null);
this.ViewData.Model = model;
using (System.Web.UI.HtmlTextWriter writer = new System.Web.UI.HtmlTextWriter(new System.IO.StringWriter()))
{
control.Render(new ViewContext(this.ControllerContext, control, this.ViewData, this.TempData, writer), writer);
string value = ((System.IO.StringWriter)writer.InnerWriter).ToString();
return value;
}
}
Regards.
What you want to apply, against the concept of the technology you're using.
MVC based on ASP.NET technology, but another way executing. MVC not use better of life cycle of ASP.NET, so, does not "Postback". MVC - in the root based on architectural pattern, that allows to separate the different layers of any system, therefore approach to the development on current technology is completely different. learn more about MVC: http://www.asp.net/mvc
if you want still implement your problem you can use ASP.NET concept and use AutoPostback property of DropDownList control.
Consider following:
Partial View:
<%= Html.ListBox("BlackList", Model.Select(
x => new SelectListItem
{
Text = x.Word,
Value = x.ID.ToString(),
Selected = Model.Any(y=> y.ID == x.ID)
}))%>
Main View:
<td><% Html.RenderPartial("GetBlackList", ViewData["BlackList"]); %></td>
Controller:
[AcceptVerbs(HttpVerbs.Post)]
public ActionResult DeleteWord(int[] wordIdsToDelete)
{
if (!ModelState.IsValid)
return View();
try
{
_wordManager.DeleteWord(wordIdsToDelete);
return RedirectToAction("WordList");
}
catch
{
return View();
}
}
Model (WordManager)
public void DeleteWord(int[] idsToDelete)
{
var dataContext = GetLinqContext();
var currentList = GetTabooWordList();
foreach (var id in idsToDelete)
{
foreach (var item in currentList)
{
if (item.ID == id)
{
dataContext.BadWords.DeleteOnSubmit(item);
}
}
}
dataContext.SubmitChanges();
}
The question is how correctly pass the parameter - idsForDel ?
I.E I have to pass a client data to the server?
<%= Html.ActionLink("Delete Selected", "DeleteWord", "AdminWord", new { wordIds = idsForDel })%>
I think this can be made by jQuery. Any ideas?
You can bind to an array using the Model Binding to a List
(Haacked.com Model binding to a list, here you can see how to bind complex types as well).
Although I'm not happy with code where I create elements
so I can serialize it in order to bind it to the controllers action input parameter, this code works just what you want:
<script type="text/javascript">
function DeleteWords() {
var el = $("<form></form>");
//for every selected item create new input element and insert it
//inside of temporarty created form element
var selItems = $('#BlackList option:selected').each(function(intIndex) {
//is important how you name input elements (as you can read in link I referenced)
el.append($('<input/>')
.attr({ type: "hidden", name: "wordIdsToDelete", value: $(this).val() })
);
});
//make an ajax call with serialized temporary form
$.ajax({
type: "POST",
url: "/YourController/DeleteWord",
data: $(el).serialize(),
// error: HandleUnespectedError,
success: function(response) {
//handle response }
});}
Hope this helps...
How about this code?
<%= Html.ActionLink("Delete Selected", "DeleteWord",
"AdminWord", new { id="send" })%>
<script type="text/javascript">
$(function() {
$("#send").click(function() {
$.post(
$("form:first").attr("action"),
$("#GetBlackList").serialize()
);
});
});
</script>
And, If two or more records are deleted, DeleteAllOnSubmit is good.
dataContext.BadWords.DeleteAllOnSubmit(
currentList.Where(item=>currentList.Containts(item.id)).ToList()
);