AngularJS - how to send int[] to an action? - asp.net-mvc

Ok, I have a checkbox list showing roles data on my project.
To retrieve these roles, I'm doing this below:
$scope.Roles = [];
$scope.init = function() {
$.get('/Navigation/NavigationNewDependencies', {}, function(result) {
for (var I = 0; I < result.Roles.length; ++I) {
var splited = result.Roles[I].split(";");
$scope.Roles.push({ id: splited[0], name: splited[1], checked: false });
}
$scope.$apply();
});
}
And showing this way:
<div>
Roles:
<ul data-ng-repeat="role in Roles">
<li><input type="checkbox" data-ng-model="role.checked" />{{role.name}}</li>
</ul>
</div>
Ok, it works properly. I want to send to an action these checked roles on the form, you know? How can I do it?
I'm trying to do the POST this way below:
$scope.getSelectedRoles = function () {
var selectedRoles = [];
for (var I = 0; I < $scope.Roles.length; ++I) {
if ($scope.Roles[I].checked == true) {
var role = $scope.Roles[I];
selectedRoles.push({ RoleId: role.id, RoleName: role.name });
}
}
return selectedRoles;
}
$scope.submit = function () {
$.post('/Navigation/New', {
title: $scope.model.NavigationName,
description: $scope.model.NavigationDescription,
controller: $scope.model.NavigationController,
action: $scope.model.NavigationAction,
roles: $scope.getSelectedRoles()
}, function (result) {
if (result.IsValid) {
window.location.href = result.ReturnUrl;
} else {
alert(result.Message);
}
});
}
... But I can't get the right selected roles on the form.
First: How can I get the selected roles with some computed property or something else?
Second: the right parameters to receive this selected roles are params int[] roles?
Thank you all!

Something like this:
//Ends up being the array of ints for the action.
//You can put this in any event handler you want, like another function attached
//to a ngCLick directive
var selectedRoles = $scope.Roles.filter(function(role) { return role.checked}).
.map(function(role) { return role.id});
$.put('/Navigation/NavigationNewDependencies', {roles: selectedRoles})
.success(function(){//Do something cool on successfully sending to server});
This assumes a few things:
Your '/Navigation/NavigationNewDependencies' action can handle 'put's
The array of ints you are passing to the action is an array of the selected role ids

I'm assuming you want to do a standard, non-ajax form submit and hit an MVC controller action. If that's the case, update your checkbox markup to this:
<input type="checkbox" data-ng-model="role.checked" value="{{ role.id }}" name="roles" />
Then wrap it all in a form tag with its action attribute pointing to an action method with a single parameter named "roles" of type int[].
UPDATE:
#Kiwanax, this should do it:
Angular Controller:
function RolesCtrl($scope, $http) {
// use Angular's $http service to communicate with the server
// won't need to call $scope.$apply();
$http.get('/Navigation/NavigationNewDependencies').success(function (result) {
// try to send json object array from the server (instead of a string)
$scope.roles = result;
// but you don't have control over it,
// process your string result the way you are currently doing it
});
$scope.getSelectedRoleIds = function () {
var result = [];
angular.forEach($scope.roles, function (value, key) {
if (value.checked) result.push(value.id);
});
return result;
};
$scope.postData = function () {
$http.post(
'/Navigation/New',
{ roles: $scope.getSelectedRoleIds() }
).success(function () {
alert('done');
});
};
}
View (use the ng-submit attribute to offload form submission handling to Angular):
<div ng-app ng-controller="RolesCtrl">
<form ng-submit="postData()">
<ul data-ng-repeat="role in roles">
<li><input type="checkbox" ng-model="role.checked"/>{{role.name}}</li>
</ul>
<button>submit roles</button>
</form>
MVC Controller's (Navigation) Action:
[HttpPost]
public ActionResult New(int[] roles)
{
// process roles Ids
return View();
}

Related

Fill Select2 dropdown box from database in MVC 4

I need help writing the jquery/ajax to fill a Select2 dropdown box.
For those who don't know what Select2 is, it is a javascript extension to provide Twitter Bootstrap looks and search / type-ahead functionality to an html select list dropdown box. For more information look at the examples here: Select2 Github page
UPDATED - Solved!
So I finally put this all together, and the solution to my problems was that I was missing functions to format the results and the list selection. The code below produces a functioning Select2 dropbox with type-ahead perfectly.
Json Method on Controller:
public JsonResult FetchItems(string query)
{
DatabaseContext dbContext = new DatabaseContext(); //init dbContext
List<Item> itemsList = dbContext.Items.ToList(); //fetch list of items from db table
List<Item> resultsList = new List<Item>; //create empty results list
foreach(var item in itemsList)
{
//if any item contains the query string
if (item.ItemName.IndexOf(query, StringComparison.OrdinalIgnoreCase) >= 0)
{
resultsList.Add(item); //then add item to the results list
}
}
resultsList.Sort(delegate(Item c1, Item c2) { return c1.ItemName.CompareTo(c2.ItemName); }); //sort the results list alphabetically by ItemName
var serialisedJson = from result in resultsList //serialise the results list into json
select new
{
name = result.ItemName, //each json object will have
id = result.ItemID //these two variables [name, id]
};
return Json(serialisedJson , JsonRequestBehavior.AllowGet); //return the serialised results list
}
The Json controller method above returns a list of serialised Json objects, whose ItemName contains the string 'query' provided (this 'query' comes from the search box in the Select2 drop box).
The code below is the Javascript in the view(or layout if you prefer) to power the Select2 drop box.
Javascript:
$("#hiddenHtmlInput").select2({
initSelection: function (element, callback) {
var elementText = "#ViewBag.currentItemName";
callback({ "name": elementText });
},
placeholder: "Select an Item",
allowClear: true,
style: "display: inline-block",
minimumInputLength: 2, //you can specify a min. query length to return results
ajax:{
cache: false,
dataType: "json",
type: "GET",
url: "#Url.Action("JsonControllerMethod", "ControllerName")",
data: function (searchTerm) {
return { query: searchTerm };
},
results: function (data) {
return {results: data};
}
},
formatResult: itemFormatResult,
formatSelection: function(item){
return item.name;
}
escapeMarkup: function (m) { return m; }
});
Then in the body of the view you need a hidden Input element, which Select2 will render the dropbox to.
Html:
<input id="hiddenHtmlInput" type="hidden" class="bigdrop" style="width: 30%" value=""/>
Or attach a MVC Razor html.hidden element to your view model to enable you to post the picked item Id back to the server.
Html (MVC Razor):
#Html.HiddenFor(m => m.ItemModel.ItemId, new { id = "hiddenHtmlInput", #class = "bigdrop", style = "width: 30%", placeholder = "Select an Item" })
Solved! Finally.
The full jquery is below, what was needed were two functions to format the returned results from the controller. This is because the dropbox needs some html markup to be wrapped around the results in order to be able to display them.
Also contractID was needed as an attribute in the controller as without it results were shown in the dropdown, but they could not be selected.
$("#contractName").select2({
placeholder: "Type to find a Contract",
allowClear: true,
minimumInputLength: 2,
ajax: {
cache: false,
dataType: "json",
type: "GET",
url: "#Url.Action("FetchContracts", "Leads")",
data: function(searchTerm){
return { query: searchTerm };
},
results: function(data){
return { results: data };
}
},
formatResult: contractFormatResult,
formatSelection: contractFormatSelection,
escapeMarkup: function (m) { return m; }
});
function contractFormatResult(contract) {
var markup = "<table class='contract-result'><tr>";
if (contract.name !== undefined) {
markup += "<div class='contract-name'>" + contract.name + "</div>";
}
markup += "</td></tr></table>"
return markup;
}
function contractFormatSelection(contract) {
return contract.name;
}
The problem is that you are returning a List<Contract> from that controller method, but the MVC runtime doesn't know how to hand that off to the browser. You need to return a JsonResult instead:
public JsonResult FetchContracts()
{
TelemarketingContext teleContext = new TelemarketingContext();
var contracts = teleContext.Contracts.ToList();
var json = from contract in contracts
select new {
name = contract.ContractName,
id = contract.ContactID,
};
return Json(json, JsonRequestBehavior.AllowGet);
}
Now, the data param of the AJAX : Success function will be the JSON from the controller. I'm not familiar with how this plugin works, but you should be able to loop through the json in data manually if you need to.
Select 2 seems to be a standard select with jquery attached so this should work:
Model:
public class vmDropDown
{
public IEnumerable<SelectListItem> DeviceList { get; set; }
[Required(ErrorMessage = "Please select at least one item")]
public IEnumerable<int> SelectedItems { get; set; }
}
Controller:
[HttpGet]
public ActionResult Assign(int id)
{
return View(CreateUnassignedModel(id));
}
[HttpPost]
public ActionResult Assign(vmDeviceAssign model)
{
if (ModelState.IsValid)
{
_deviceLogic.Assign(model.GroupId, model.SelectedItems);
return View("ConfirmDevice");
}
else // Validation error, so redisplay data entry form
{
return View(CreateUnassignedModel(model.GroupId));
}
}
private vmDeviceAssign CreateUnassignedModel(int id)
{
return new vmDeviceAssign
{
DeviceList = _deviceLogic.GetUnassigned(),
SelectedItems = null
};
}
View:
<div class="editor-field">
#Html.ListBoxFor(model => model.SelectedItems, new SelectList(Model.DeviceList, "Value", "Text"))
#Html.ValidationMessageFor(model => model.SelectedItems)
</div>
Cant give explanation as am at work but if you leave a message ill pick it up tonight

Populating dropdown with JSON result - Cascading DropDown using MVC3, JQuery, Ajax, JSON

I've got a cascading drop-drown using mvc. Something like, if you select a country in the first-dropdown, the states of that country in the second one should be populated accordingly.
At the moment, all seems fine and I'm getting Json response (saw it using F12 tools), and it looks something like [{ "stateId":"01", "StateName": "arizona" } , { "stateId" : "02", "StateName":"California" }, etc..] ..
I'd like to know how to populate my second-dropdown with this data. My second drop-down's id is "StateID". Any help would be greatly appreciated.
Below is the code used to produce the JSON Response from the server:
[HttpPost]
public JsonResult GetStates(string CountryID)
{
using (mdb)
{
var statesResults = from q in mdb.GetStates(CountryID)
select new Models.StatesDTO
{
StateID = q.StateID,
StateName = q.StateName
};
locations.statesList = stateResults.ToList();
}
JsonResult result = new JsonResult();
result.Data = locations.statesList;
return result;
}
Below is the client-side HTML, my razor-code and my script. I want to write some code inside "success:" so that it populates the States dropdown with the JSON data.
<script type="text/javascript">
$(function () {
$("select#CountryID").change(function (evt) {
if ($("select#CountryID").val() != "-1") {
$.ajax({
url: "/Home/GetStates",
type: 'POST',
data: { CountryID: $("select#CountryID").val() },
success: function () { alert("Data retrieval successful"); },
error: function (xhr) { alert("Something seems Wrong"); }
});
}
});
});
</script>
To begin with, inside a jQuery event handler function this refers to the element that triggered the event, so you can replace the additional calls to $("select#CountryID") with $(this). Though where possible you should access element properties directly, rather than using the jQuery functions, so you could simply do this.value rather than $(this).val() or $("select#CountryID").val().
Then, inside your AJAX calls success function, you need to create a series of <option> elements. That can be done using the base jQuery() function (or $() for short). That would look something like this:
$.ajax({
success: function(states) {
// states is your JSON array
var $select = $('#StateID');
$.each(states, function(i, state) {
$('<option>', {
value: state.stateId
}).html(state.StateName).appendTo($select);
});
}
});
Here's a jsFiddle demo.
Relevant jQuery docs:
jQuery.each()
jQuery()
In my project i am doing like this it's below
iN MY Controller
public JsonResult State(int countryId)
{
var stateList = CityRepository.GetList(countryId);
return Json(stateList, JsonRequestBehavior.AllowGet);
}
In Model
public IQueryable<Models.State> GetList(int CountryID)
{
var statelist = db.States.Where(x => x.CountryID == CountryID).ToList().Select(item => new State
{
ID = item.ID,
StateName = item.StateName
}).AsQueryable();
return statelist;
}
In view
<script type="text/javascript">
function cascadingdropdown() {
$("#stateID").empty();
$("#stateID").append("<option value='0'>--Select State--</option>");
var countryID = $('#countryID').val();
var Url="#Url.Content("~/City/State")";
$.ajax({
url:Url,
dataType: 'json',
data: { countryId: countryID },
success: function (data) {
$("#stateID").empty();
$("#stateID").append("<option value='0'>--Select State--</option>");
$.each(data, function (index, optiondata) {
$("#stateID").append("<option value='" + optiondata.ID + "'>" + optiondata.StateName + "</option>");
});
}
});
}
</script>
i think this will help you......
Step 1:
At very first, we need a model class that defines properties for storing data.
public class ApplicationForm
{
public string Name { get; set; }
public string State { get; set; }
public string District { get; set; }
}
Step 2:
Now, we need an initial controller that will return an Index view by packing list of states in ViewBag.StateName.
public ActionResult Index()
{
List<SelectListItem> state = new List<SelectListItem>();
state.Add(new SelectListItem { Text = "Bihar", Value = "Bihar" });
state.Add(new SelectListItem { Text = "Jharkhand", Value = "Jharkhand" });
ViewBag.StateName = new SelectList(state, "Value", "Text");
return View();
}
In above controller we have a List containing states attached to ViewBag.StateName. We could get list of states form database using Linq query or something and pack it to ViewBag.StateName, well let’s go with in-memory data.
Step 3:
Once we have controller we can add its view and start creating a Razor form.
#Html.ValidationSummary("Please correct the errors and try again.")
#using (Html.BeginForm())
{
<fieldset>
<legend>DropDownList</legend>
#Html.Label("Name")
#Html.TextBox("Name")
#Html.ValidationMessage("Name", "*")
#Html.Label("State")
#Html.DropDownList("State", ViewBag.StateName as SelectList, "Select a State", new { id = "State" })
#Html.ValidationMessage("State", "*")
#Html.Label("District")
<select id="District" name="District"></select>
#Html.ValidationMessage("District", "*")
<p>
<input type="submit" value="Create" id="SubmitId" />
</p>
</fieldset>
}
You can see I have added proper labels and validation fields with each input controls (two DropDownList and one TextBox) and also a validation summery at the top. Notice, I have used which is HTML instead of Razor helper this is because when we make JSON call using jQuery will return HTML markup of pre-populated option tag. Now, let’s add jQuery code in the above view page.
Step 4:
Here is the jQuery code making JSON call to DDL named controller’s DistrictList method with a parameter (which is selected state name). DistrictList method will returns JSON data. With the returned JSON data we are building tag HTML markup and attaching this HTML markup to ‘District’ which is DOM control.
#Scripts.Render("~/bundles/jquery")
<script type="text/jscript">
$(function () {
$('#State').change(function () {
$.getJSON('/DDL/DistrictList/' + $('#State').val(), function (data) {
var items = '<option>Select a District</option>';
$.each(data, function (i, district) {
items += "<option value='" + district.Value + "'>" + district.Text + "</option>";
});
$('#District').html(items);
});
});
});
</script>
Please make sure you are using jQuery library references before the tag.
Step 5:
In above jQuery code we are making a JSON call to DDL named controller’s DistrictList method with a parameter. Here is the DistrictList method code which will return JSON data.
public JsonResult DistrictList(string Id)
{
var district = from s in District.GetDistrict()
where s.StateName == Id
select s;
return Json(new SelectList(district.ToArray(), "StateName", "DistrictName"), JsonRequestBehavior.AllowGet);
}
Please note, DistrictList method will accept an ‘Id’ (it should be 'Id' always) parameter of string type sent by the jQuery JSON call. Inside the method, I am using ‘Id’ parameter in linq query to get list of matching districts and conceptually, in the list of district data there should be a state field. Also note, in the linq query I am making a method call District.GetDistrict().
Step 6:
In above District.GetDistrict() method call, District is a model which has a GetDistrict() method. And I am using GetDistrict() method in linq query, so this method should be of type IQueryable. Here is the model code.
public class District
{
public string StateName { get; set; }
public string DistrictName { get; set; }
public static IQueryable<District> GetDistrict()
{
return new List<District>
{
new District { StateName = "Bihar", DistrictName = "Motihari" },
new District { StateName = "Bihar", DistrictName = "Muzaffarpur" },
new District { StateName = "Bihar", DistrictName = "Patna" },
new District { StateName = "Jharkhand", DistrictName = "Bokaro" },
new District { StateName = "Jharkhand", DistrictName = "Ranchi" },
}.AsQueryable();
}
}
Step 7:
You can run the application here because cascading dropdownlist is ready now. I am going to do some validation works when user clicks the submit button. So, I will add another action result of POST version.
[HttpPost]
public ActionResult Index(ApplicationForm formdata)
{
if (formdata.Name == null)
{
ModelState.AddModelError("Name", "Name is required field.");
}
if (formdata.State == null)
{
ModelState.AddModelError("State", "State is required field.");
}
if (formdata.District == null)
{
ModelState.AddModelError("District", "District is required field.");
}
if (!ModelState.IsValid)
{
//Populate the list again
List<SelectListItem> state = new List<SelectListItem>();
state.Add(new SelectListItem { Text = "Bihar", Value = "Bihar" });
state.Add(new SelectListItem { Text = "Jharkhand", Value = "Jharkhand" });
ViewBag.StateName = new SelectList(state, "Value", "Text");
return View("Index");
}
//TODO: Database Insertion
return RedirectToAction("Index", "Home");
}
Try this inside the ajax call:
$.ajax({
url: "/Home/GetStates",
type: 'POST',
data: {
CountryID: $("select#CountryID").val()
},
success: function (data) {
alert("Data retrieval successful");
var items = "";
$.each(data, function (i, val) {
items += "<option value='" + val.stateId + "'>" + val.StateName + "</option>";
});
$("select#StateID").empty().html(items);
},
error: function (xhr) {
alert("Something seems Wrong");
}
});
EDIT 1
success: function (data) {
$.each(data, function (i, val) {
$('select#StateID').append(
$("<option></option>")
.attr("value", val.stateId)
.text(val.StateName));
});
},
I know this post is a year old but I found it and so might you. I use the following solution and it works very well. Strong typed without the need to write a single line of Javascript.
mvc4ajaxdropdownlist.codeplex.com
You can download it via Visual Studio as a NuGet package.
You should consider using some client-side view engine that binds a model (in your case JSON returned from API) to template (HTML code for SELECT). Angular and React might be to complex for this use case, but JQuery view engine enables you to easily load JSON model into template using MVC-like approach:
<script type="text/javascript">
$(function () {
$("select#CountryID").change(function (evt) {
if ($("select#CountryID").val() != "-1") {
$.ajax({
url: "/Home/GetStates",
type: 'POST',
data: { CountryID: $("select#CountryID").val() },
success: function (response) {
$("#stateID").empty();
$("#stateID").view(response);
},
error: function (xhr) { alert("Something seems Wrong"); }
});
}
});
});
</script>
It is much cleaner that generating raw HTML in JavaScript. See details here: https://jocapc.github.io/jquery-view-engine/docs/ajax-dropdown
Try this:
public JsonResult getdist(int stateid)
{
var res = objdal.getddl(7, stateid).Select(m => new SelectListItem { Text = m.Name, Value = m.Id.ToString() });
return Json(res,JsonRequestBehavior.AllowGet);
}
<script type="text/javascript">
$(document).ready(function () {
$("#ddlStateId").change(function () {
var url = '#Url.Content("~/")' + "Home/Cities_SelectedState";
var ddlsource = "#ddlStateId";
var ddltarget = "#ddlCityId";
$.getJSON(url, { Sel_StateName: $(ddlsource).val() }, function (data) {
$(ddltarget).empty();
$.each(data, function (index, optionData) {
$(ddltarget).append("<option value='" + optionData.Text + "'>" + optionData.Value + "</option>");
});
});
});
});
</script>

Pass checkboxes to controller asp.net mvc

I have some images that every images has a checkbox beside like this :
<input type="checkbox" name="select" value="<%=item.Id%>" />
Now I want to send the selected checkboxes to controller by clicking a hyperlink. I have :
<a href='<%: Url.Action("DeleteSelected", "Product", new { #ShopID = ViewBag.shopIDempty } ) %>'>Delete</a>
and in controller:
public ActionResult DeleteSelected(int[] select, int ShopID)
{
foreach (int checkBoxSelected in select)
{
//Do something...
}
return RedirectToAction("Index");
}
But nothing pass to int[] select and it is null always. What is wrong?
Do these==>
1) Make an array which contains the selected checkbox value
var delete= new Array();
$('.checkboxed').live('click', function () {
if ($(this)[0].checked == true) {
var itemdel= $(this).val();
delete.push(itemdel);
} else {
var remve = $(this).val();
for (var i = 0; i < delete.length; i++) {
if (delete[i] == remve) {
delete.splice(i, 1);
break;
}
}
}
});
2)Make an ajax call on clicking the hyper link
$.ajax({
type: 'POST',
contentType: 'application/json; charset=utf-8',
url: '/Product/DeleteSelected'
+ '?ShopID =' + ShopIdValue,
dataType: 'json',
data: $.toJSON(delete),
success: function (result) {
window.location.href=result;
},
async: false,
cache: false
});
3) Make your Action Like this
public ActionResult DeleteSelected(int[] select)
{
var shopid= Request["ShopID "];
}
Try this:
[HttpPost]
public ActionResult DeleteSelected(FormCollection collection)
{
try
{
string[] test = collection.GetValues("select");
}
catch (Exception ex)
{
return null;
}
}
I do want to note that the approach you are taking requires a form to wrap the all of the checkboxes or you need to specifically build an object to send to the controller as Syed showed. If you go the form approach, you will need to either use the a link to trigger the form submit or convert the a link to a submit button and have a hidden field for the ShopID.

ASP.NET MVC Sort Listing by Selected item in DropDownList

I have a List of Listings within my Database. On my View, I have a DropDownList which contains categories. A category contains many listings.
When I select a specific category, I wish to only display those listings which have the category selected.
My main worry is how to generate the JQuery to call my SortListing method in my ListingController.
Here is the current HTML (Razor):
#Html.DropDownListFor(m => m.Categories, Model.Categories, "Select a Category")
My SortListing Method:
public List<Listing> SortListing(string categoryId)
{
var listings = new List<Listing>();
foreach (var listing in _service.ListAllEntities<Listing>())
{
if (listing.CategoryId == categoryId)
{
listings.Add(listing);
}
}
return listings;
}
EDIT I have the following. Put the categoryGuid is coming in null.
This is my code:
$(function () {
$('#SelectedCategoryGuid').change(function () {
var url = $(this).data('url');
var categoryId = $(this).val();
$.ajax({
url: url,
type: 'GET',
cache: false,
data: { categoryId: categoryId },
success: function (result) {
// TODO: manipulate the result returned from the controller action
}
});
});
});
</script>
<h2>Index</h2>
#Html.ActionLink("Create New Listing", "Create")
<br/>
<strong>Filter Listings</strong>
#Html.DropDownListFor(
m => m.SelectedCategoryGuid,
Model.Categories,
"Select a Category",
new {
id = "SelectedCategoryGuid",
data_url = Url.Action("SortListing", "Listing")
}
)
My main worry is how to generate the JQuery to call my SortListing
method in my ListingController.
Actually you should be having other worries as well that I will try to cover throughout my answer.
There's an issue with your DropDownListFor helper. You have used the same property on your model for both binding the selected category value and the list of categories which is wrong. The first parameter of the DropDownListFor helper represents a lambda expression pointing to a primitive type property on your view model:
#Html.DropDownListFor(
m => m.CategoryId,
Model.Categories,
"Select a Category",
new {
id = "categoryDdl",
data_url = Url.Action("SortListing", "Listing")
}
)
and then subscribe to the .change() event and trigger the AJAX request:
$(function() {
$('#categoryDdl').change(function() {
var url = $(this).data('url');
var categoryId = $(this).val();
$.ajax({
url: url,
type: 'GET',
cache: false,
data: { categoryId: categoryId },
success: function(result) {
// TODO: manipulate the result returned from the controller action
}
});
});
});
Now let's take a look at your SortListing controller action because there are issues with it. In ASP.NET MVC standard convention dictates that controller actions must return ActionResults. In your case you seem to be returning some List<Listing>. So the first thing you have to decide is the format you would like to use. One possibility is to return those listings as JSON formatted values:
public ActionResult SortListing(string categoryId)
{
var listings = _service
.ListAllEntities<Listing>()
.Where(x => x.CategoryId == categoryId)
.ToList();
return Json(listings, JsonRequestBehavior.AllowGet);
}
In this case inside your AJAX success callback you will receive this collection of listings and you will have to update your DOM:
success: function(result) {
// result represents an array of listings
// so you could loop through them and generate some DOM elements
}
Another possibility is to have your controller action return a partial view:
public ActionResult SortListing(string categoryId)
{
var listings = _service
.ListAllEntities<Listing>()
.Where(x => x.CategoryId == categoryId)
.ToList();
return PartialView("Listings", listings);
}
and then you will have a corresponding partial view:
#model List<Listing>
#foreach (var listing in Model)
{
<div>#listing.SomeProperty</div>
}
and then inside the success callback you will refresh some containing placeholder:
success: function(result) {
$('#SomeDivIdThatWrapsAroundTheListingsPartial').html(result);
}
So to recap you could either have the controller action return JSON and then manually build the corresponding DOM tree using javascript or return a partial view which will already contain the corresponding markup and simply refresh some containing div with this partial.

ajax request to return partial view

I'm trying to make request returns on ajax updated partial view. Apparently request is not returned from the ajax-function.
Here ajax-code:
<script type="text/javascript">
function doAjaxPost(myid) {
// get the form values
var ApplSort = $('#DropDownListSort').val();
var radio_check_val=0;
for (i = 0; i < document.getElementsByName('radio').length; i++) {
if (document.getElementsByName('radio')[i].checked) {
radio_check_val = document.getElementsByName('radio')[i].value;
}
}
// alert("myid=" + myid +";"+ "ApplSort=" + ApplSort + ";" + "radio_check_val=" + radio_check_val);
$.ajax(
{
type: 'POST',
contentType: 'application/json; charset=utf-8',
data: { ApplSort: ApplSort, radio_check_val: radio_check_val, myid: myid },
UpdateTargetId: "tabledata",
dataType: 'html',
url: 'Partner/PartnerApplications',
success: function (data) {
var result = data;
$('tabledata').html(result);
},
error: function (error) {
alert('Ошибка AJAX-запроса. Обновите страницу!');
}
});
}
</script>
Fail is called and the page is completely updated.
Here's updated content in the view:
<div id="target">
#Html.Partial("~/Views/Partner/PartnerApplicationsPartial.cshtml")
</div>
controller's code:
[HttpPost]
public ActionResult PartnerApplications(int[] ApplSort, int[] radio_check_val, int[] myid)
{
MordaPartner MrdPrt = new MordaPartner(Server, Request);
if (Request.IsAjaxRequest())
{
var obj = MrdPrt.morda_obj.CookieAuthenticationPartner(Server, Request, Response, MrdPrt.PartnerLogin, MrdPrt.PartnerPassword);
if (obj != null)
{
//alert("ApplSort=" + ApplSort + ";" + "ApplSelectOffer=" + ApplSelectOffer + ";" + "ApplSelectAuction=" + ApplSelectAuction + ";" + "ApplSelectNoOffer=" + ApplSelectNoOffer);
var objs = from s in MrdPrt.morda_obj.entities.applications where s.application_user_city == obj.partner_city & s.application_blocked != 1 orderby s.application_id ascending select s;
return Json(new { data = this.RenderPartialViewToString("PartnerApplicationsPartial", objs) });
}
else
{
return RedirectToAction("Registration");
}
}
else { return RedirectToAction("PartnerApplications"); }
}
RenderPartialViewToString it was taken from here: http://www.c-sharpcorner.com/blogs/7150/implementing-renderpartialviewtostring-in-asp-net-mvc-3.aspx
script is loaded:
<script src="#Url.Content("~/Scripts/jquery.unobtrusive-ajax.min.js")" type="text/javascript"></script>
What am I doing wrong?
I think your easiest solution since you are just wanting to do a partial...
#using( Ajax.BeginForm( "PartnerApplications",
null,
new AjaxOptions() {
HttpMethod = "POST",
InsertionMode = InsertionMode.Replace,
UpdateTargetId = "target",
LoadingElementId = "AjaxSearch" },
new { id = "UserSearchForm" } ) ) {
<input type="text" id="id" name="id" placeholder="Enter Search" />
}
This is an ability that is built into MVC that makes it VERY easy to update an element with the results of a partial.
All this is saying is that you want a new Ajax Form that calls the PartnerApplications Action. You want the action called with an HttpMethod that is a POST request and you want the results to replace (InsertionMode.Replace) the existing elements in the target (whatever that may be) and while the request is taking place you want the element AjaxSearch visible (this is optional, but something I use to show that it's working).
This will generate the required JavaScript for you and until you get into something beyond simply returning a partial works EXCELLENT!
EDIT: Also you will need to update your Action...
return Json(new { data = this.RenderPartialViewToString("PartnerApplicationsPartial", objs) });
needs changed to....
return PartialView("PartnerApplicationsPartial", objs);
EDIT BASED ON COMMENTS:
Without knowing the data better that is being sent to the server I can't tell you what to write in order to replace that method. I would however look at the properties of new AjaxOptions(){} because it has some additional properties that allow you to specify the name of a JavaScript function to call on four states (before/after/success/fail) of the Ajax request. So if you are needing to calculate something you can do this by specifying a JavaScript function that will be processed before the Ajax request is submitted.
Also you are doing a lot more work then needed to get the selected radio button value (especially since you are using jQuery).
You can replace...
var radio_check_val=0;
for (i = 0; i < document.getElementsByName('radio').length; i++) {
if (document.getElementsByName('radio')[i].checked) {
radio_check_val = document.getElementsByName('radio')[i].value;
}
}
with something similar to....
var radio_check_val = $('radio').filter(':checked').val();
//this will only work if there is only one set of radio buttons on the page.
//Otherwise you will need to add a name to the selector.
You should not RedirectToAction. Instead of redirect return PartialView('Registration');.
Related questions:
MVC Return Partial View as JSON.
Load PartialView for AJAX and View for non-AJAX request

Resources