I'm using Kendo MultiSelect in my mvc5 project. So I have a View with multiselect:
#model Library.ViewModels.Models.BookViewModel
#{
ViewBag.Title = "Edit";
}
<script>
$(document).ready(function () {
$("#multiselect").kendoMultiSelect({
placeholder: "--Select Public Houses--",
dataTextField: "PublicHouseName",
dataValueField: "PublicHouseId",
autoBind: true,
dataSource: {
transport: {
read: {
dataType: "json",
url: "/book/getallpublichouses"
}
}
}
});
});
</script>
And I have 2 viewModels:
public class BookViewModel
{
public int BookId { get; set; }
public string Name { get; set; }
public string AuthorName { get; set; }
public int YearOfPublishing { get; set; }
public ICollection<PublicHouseViewModel> PublicHouses { get; set; }
}
public class PublicHouseViewModel
{
public int PublicHouseId { get; set; }
public string PublicHouseName { get; set; }
public string Country { get; set; }
public ICollection<BookViewModel> Books { get; set; }
}
In my Kendo MultiSelect a get all Public Houses from Book controller in JSON format. Next I selected some values:
So, how can I pass this selected values in public ICollection<PublicHouseViewModel> PublicHouses { get; set; } property in BookViewModel ?
You can use:
public int[] PublicHouses { get; set; }
instead of:
public ICollection<PublicHouseViewModel> PublicHouses { get; set; }
Or you can create a new field in BookViewModel only for posting.
When you are posting values from kendoMultiSelect, he posts only "dataValueField". After you post only id's you can do the rest of the logic in POST action.
It depends how you implemented your POST action and also on the relationship between two tables: Is it 1...N, or N....N.
Related
I'm creating a new MVC WebSite using EntityFramework and, on my _Layout.cshtml I'm calling a PartialView, which is a Modal to insert a record on a specific table.
The partial view contains the following DDL:
<div class="form-group">
#Html.LabelFor(model => model.Currency, htmlAttributes: new { #class = "control-label col-md-2" })
<div class="col-md-10">
<select class="form-control" id="CurrencyId" name="CurrencyId">
<option value="">Select currency...</option>
</select>
</div>
</div>
It uses an autogenerated model:
using System;
using System.Collections.Generic;
public partial class Property
{
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors")]
public Property()
{
this.Attachments = new HashSet<Attachment>();
this.BankAccountCorrienteProperties = new HashSet<BankAccountCorrienteProperty>();
this.Contracts = new HashSet<Contract>();
this.Photos = new HashSet<Photo>();
this.Renters = new HashSet<Renter>();
}
public int IdProperty { get; set; }
public Nullable<int> IdOwner { get; set; }
public Nullable<int> PropertyType { get; set; }
public string StreetName { get; set; }
public Nullable<decimal> SquareMetersSize { get; set; }
public Nullable<bool> Garage { get; set; }
public Nullable<int> PropertyStatus { get; set; }
public string ConstructionDate { get; set; }
public Nullable<short> RentOrSell { get; set; }
public Nullable<int> Currency { get; set; }
public Nullable<decimal> Price { get; set; }
public string Notes { get; set; }
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
public virtual ICollection<Attachment> Attachments { get; set; }
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
public virtual ICollection<BankAccountCorrienteProperty> BankAccountCorrienteProperties { get; set; }
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
public virtual ICollection<Contract> Contracts { get; set; }
public virtual Currency Currency1 { get; set; }
public virtual Owner Owner { get; set; }
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
public virtual ICollection<Photo> Photos { get; set; }
public virtual PropertyType PropertyType1 { get; set; }
public virtual PropertyStatu PropertyStatu { get; set; }
[System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
public virtual ICollection<Renter> Renters { get; set; }
}
And to load the data into the dropdown I had to use Ajax as follows:
getDdlInfo("../Currency/ListCurrencies", function (result) {
$.each(result.data, function (key, item) {
$("#CurrencyId").append($('<option></option>').val(item.CurrencyId).text(item.CurrencyName));
});
function getDdlInfo(path, callBackFunct) {
$.ajax({
type: "GET",
url: path,
success: function (result) {
return callBackFunct(result);
},
error: function (data) {
}
});
For then sending the value to the controller, where an HTTP Post is there to send data to database:
function createProperty() {
$.ajax({
url: '../Property/CreateProperty',
type: 'POST',
cache: false,
async: true,
data: $('form').serialize(),
success: function (result) {
//TODO: Modal de propiedad cargada
}
});
My problem here is that:
1) Whenever createProperty() goes into the controller, all data is there, except for the dropdown. It gets to the controller always null, no matter if I select a value or not and...
2) Is this the correct approach for this? Am I missing something? I tried using Razor DropDownList but I couldn't find the way to do it correctly.
Thank you.
On your model the property is called Currency, so your input's name needs to match that to successfully model bind. Changing the name on the input to Currency should resolve it.
<select class="form-control" id="CurrencyId" name="Currency">
I have page where I save user, contact and address details. The users could have multiple contact and address, So I have added the control to populate dynamically.
Form is working fine, except if any exception occurrs, the controller action return view with model.
This follows the structure of Model:
Model
public class UserModel
{
public UserDetail User { get; set; }
public IList<UserContact> Contact { get; set; }
public IList<UserAddress> Address { get; set; }
}
Contact Model :
public partial class UserContact
{
public int Id { get; set; }
public int UserId { get; set; }
public string ContactType { get; set; }
public string Mobile { get; set; }
public string Email { get; set; }
public bool IsActive { get; set; }
public virtual UserDetail UserDetail { get; set; }
}
Address Model
public partial class UserAddress
{
public int Id { get; set; }
public int UserId { get; set; }
public string AddressType { get; set; }
public string AddressName { get; set; }
public string AddressLine1 { get; set; }
public string AddressLine2 { get; set; }
public string City { get; set; }
public string State { get; set; }
public string PostCode { get; set; }
public bool IsActive { get; set; }
public virtual UserDetail UserDetail { get; set; }
}
When value return, the following function suppose to check the Contact and Address and then then populate each record in dynamic created input section in view.
<script type="text/javascript">
$(document).ready(function () {
AddDynamicData();
function AddDynamicData() {
var valuesContacts = eval('#Html.Raw(Json.Encode(Model.Contact))');
var valuesAddresses = eval('#Html.Raw(Json.Encode(Model.Address))');
if (valuesContacts != null) {
var iContact = 0;
$(valuesContacts).each(function () {
$("#divContact").append(GetDynamicContact(iContact++, valuesContacts.contactType, valuesContacts.mobile, valuesContacts.email));
});
}
if (valuesAddresses != null) {
var iAddress = 0;
$(valuesAddresses).each(function () {
$("#divAddress").append(GetDynamicAddress(iAddress++, valuesAddresses.addressType, valuesAddresses.addressName, valuesAddresses.addressLine1, valuesAddresses.addressLine2, valuesAddresses.city, valuesAddresses.state, valuesAddresses.postCode));
});
}
}
</script>
The Function does not work properly, It does create the field but does not populate the user input data into textbox... Please advise how to fix the same and how to populate the records in view....
Added the View after submitting the form
<Update>
#Updated New Code with function & added screenshot
</Update>
I'm used Kendo MultiSelect in my mvc5 project.
So I have a View with multiselect:
#model Library.ViewModels.Models.BookViewModel
#{
ViewBag.Title = "Edit";
}
<script>
$(document).ready(function () {
$("#multiselect").kendoMultiSelect({
placeholder: "--Select Public Houses--",
dataTextField: "PublicHouseName",
dataValueField: "PublicHouseId",
autoBind: true,
dataSource: {
transport: {
read: {
dataType: "json",
url: "/book/getallpublichouses"
}
}
}
});
$("#multiselect").getKendoMultiSelect().value([/* there must be a string array of ID's of pre-selected values here*/]);
});
</script>
My BookViewModel looks like this:
public class BookViewModel
{
public int BookId { get; set; }
[Required(ErrorMessage = "This field is Required")]
[StringLength(15, ErrorMessage = "Must be under 15 characters")]
public string Name { get; set; }
public string AuthorName { get; set; }
[Required(ErrorMessage = "This field is Required")]
[Range(1, 2019, ErrorMessage = "Must be between 1 and 2019")]
public int YearOfPublishing { get; set; }
public List<int> PubHouses { get; set; }
public ICollection<PublicHouseViewModel> PublicHouses { get; set; }
}
The property public List<int> PubHouses { get; set; } contains a List of ID's which must be pre-selected in kendo MultiSelect.
So how can I pass this list of int in property BookViewModel.PubHouses like string array in kendo MultiSelect?
I seem to be having a problem posting the selected values from my Kendo Multiselect widget to an action on my controller. I've never had this issue before and as far as I know I am doing everything right, but something is obviously causing an issue.
I have this input on my view:
<input id="ProductHandlingTypes" name="ProductHandlingTypes" style="width: 100%"/>
My ViewModel
public class BuyerProfileViewModel
{
public string UserId { get; set; }
public string Name { get; set; }
public int BuyerTypeId { get; set; }
public string Address { get; set; }
public string City { get; set; }
public string State { get; set; }
public string Zipcode { get; set; }
public string Description { get; set; }
public List<int> ProductHandlingTypes { get; set; }
public bool Producer { get; set; }
}
And my JavaScript:
$("#ProductHandlingTypes").kendoMultiSelect({
placeholder: "-- Select Type(s) --",
dataTextField: "Name",
dataValueField: "Id",
dataSource: new kendo.data.DataSource({
transport: {
read: {
url: "/Helper/GetProductHandlingTypes",
dataType: "json",
type: "GET"
}
}
})
});
$("#btnSave").on("click", function (e) {
e.preventDefault();
var formCreate = $(".form-register-buyer");
formCreate.validate();
if (formCreate.valid()) {
var options = {
url: $(formCreate).attr("action"),
type: $(formCreate).attr("method"),
data: $(formCreate).serialize()
};
$.ajax(options)
.done(function(data) {
if (data.success === true) {
window.location.href = data.redirectTo;
} else {
toastr.options = { "postiionClass": "toast-bottom-full-width" };
toastr.error(data.message, "Uh, Oh!");
}
});
}
});
When I submit my form to the controller I can see that all of the correct values are being passed except for ProductHandlingTypes. It just says it has a count of 1 and when I expand it out it says 0.
I have a treeview in kendoUI in which main nodes are calling into an mvc controller and that controller looks to whether there is an nullable id passed in and then uses a different model.
What I hit the url : http://localhost:2949/Report/GetReportGroupAssignments
I see this JSON
[
{"Id":1,"ReportGroupName":"Standard Reports","ReportGroupNameResID":null,"SortOrder":1},
{"Id":2,"ReportGroupName":"Custom Reports","ReportGroupNameResID":null,"SortOrder":2},
{"Id":3,"ReportGroupName":"Retail Reports","ReportGroupNameResID":null,"SortOrder":3},
{"Id":4,"ReportGroupName":"Admin Reports","ReportGroupNameResID":null,"SortOrder":5},
{"Id":5,"ReportGroupName":"QA Reports","ReportGroupNameResID":null,"SortOrder":4}
]
Now my mvc controller looks like this
public JsonResult GetReportGroupAssignments(int? id)
{
var model = new List<ReportGroup>();
var defModel = new List<ReportDefinition>();
try
{
if (id == null)
{
model = _reportService.GetReportGroups("en-us").ToList();
return Json(model, JsonRequestBehavior.AllowGet);
}
else
{
defModel = _reportService.GetReportDefinitions().Where(e=>e.ReportGroupID ==Convert.ToInt32(id)).ToList();
return Json(defModel, JsonRequestBehavior.AllowGet);
}
}
catch (Exception ex)
{
Logger.Error(ex, "Error loading LoadReportList.");
return null;
}
}
My Kendo javascript looks like the following:
var serviceRoot = "/Report"; // "//demos.telerik.com/kendo-ui/service";
homogeneous = new kendo.data.HierarchicalDataSource({
transport: {
read: {
url: serviceRoot + "/GetReportGroupAssignments", //"/LoadReportTree", // "/Employees",
dataType: "json"
}
},
schema: {
model: {
id: "Id" //"ReportGroupName"
,hasChildren: "Id"
}
}
});
var treeview = $("#treeview").kendoTreeView({
expanded: true,
dragAndDrop: true,
dataSource: homogeneous,
dataTextField: "ReportGroupName"
}).data("kendoTreeView");
Seems that the calls (which I discovered that children records have a "load" method that it called behind the seens, so basically I pass in the ID in order to get the data from the other model ( table in db)
(Id is mapped with automapper to ReportGroupID )
So when i click to the left of "Standard Rports" I am getting all of these children as undefined, How do I get these to show up properly?
Update: My ReportDefinition class:
public class ReportDefinition {
public override int Id { get; set; }
public string ReportKey { get; set; }
public string ReportName { get; set; }
public int? ReportNameResID { get; set; }
public string ReportDef { get; set; }
public int? ReportDefinitionResID { get; set; }
public string ReportAssembly { get; set; }
public string ReportClass { get; set; }
public int ReportGroupID { get; set; }
public int AppID { get; set; }
public int SortOrder { get; set; }
public bool IsSubReport { get; set; }
}
I think your problem is that the class ReportDefinition does not have a property called: ReportGroupName. That is why TreeView displays 'undefined'.
Try adding this Property to your ReportDefinition class like:
public class ReportDefinition {
// Other Properties
// I guess this property is missing
public string ReportGroupName { get; set; }
}