Bind local data to kendo grid and make it sortable - kendo-ui

I am trying to setup kendo mvc ui grid using local data and make it sortable as in this demo Binding to local data.
However grid doesn't show data and if I hook up the onDataBound event, data inside there is undefined.
If I comment out DataSource setup on view, data gets populated at first, but disappears after sorting performed on any column.
I am using Kendo UI version: "2013.3.1119", asp.net mvc 4.
Please advice.
Thanks.
view
#model TestViewModel
#(Html.Kendo().Grid(Model.TestList)
.Name("grid2")
.Columns(columns =>
{
columns.Bound( p => p.Id ).Title( "ID" );
columns.Bound( p => p.Name ).Title("Product Name");
})
.Pageable()
.Sortable()
.Scrollable(scr=>scr.Height(430))
.Filterable()
.DataSource(dataSource => dataSource
.Ajax()
.PageSize(20)
.ServerOperation(false))
)
controller and model
public class TestController : Controller
{
//
// GET: /Test/
public ActionResult Index()
{
var mdl = new TestViewModel();
mdl.TestList = Test().ToList();
return View(mdl);
}
public IEnumerable<TestMe> Test()
{
var lst = new List<TestMe>();
for( int i = 0; i < 5; i++ )
{
lst.Add( new TestMe
{
Id = i,
Name = i.ToString(),
} );
}
return lst;
}
}
public class TestViewModel
{
public List<TestMe> TestList { get; set; }
public TestViewModel()
{
TestList = new List<TestMe>();
}
}
public class TestMe
{
public int Id { get; set; }
public string Name { get; set; }
}

Related

KendoUI (Telerik 2018) - TreeList is not showing newly created record till manual refresh

I am able to create new record in TreeList for MVC. But it shows newly created record only after refreshing the page. Edit and Delete works fine.
Razor Code
#(Html.Kendo().TreeList<KendoEx.Web.Models.Level>()
.Name("lvlTreeList")
.Toolbar(toolbar =>
{
toolbar.Create();
})
.Columns(columns =>
{
columns.Add().Field(e => e.LvlName).Title("Name").Width(120);
columns.Add().Field(e => e.LvlType).Title("Type").Width(80);
columns.Add().Field(e => e.Rating1).Title("Rating 1").Filterable(false).Width(100);
columns.Add().Field(e => e.Rating2).Title("Rating 2").Filterable(false).Width(100);
columns.Add().Command(c =>
{
c.CreateChild().Text("Add child");
c.Edit();
c.Destroy();
}).Width(180);
})
.Editable(e => e.Mode("inline"))
.DataSource(dataSource => dataSource
.Read(read => read.Action("GetLevel", "Level"))
.Create(create => create.Action("Save", "Level"))
.Update(update => update.Action("Save", "Level"))
.Destroy(delete => delete.Action("Remove", "Level"))
.Model(m =>
{
m.Id(f => f.Id);
m.ParentId(f => f.ParentLvl).DefaultValue(0);
m.Expanded(true);
m.Field(f => f.LvlName);
m.Field(f => f.LvlType);
m.Field(f => f.Rating1);
m.Field(f => f.Rating1);
}))
.Height(550))
Controller Methods
public JsonResult GetLevel([DataSourceRequest] DataSourceRequest request)
{
var lvlList = LoadLevels().ToTreeDataSourceResult(request);
return Json(lvlList, JsonRequestBehavior.AllowGet);
}
private IEnumerable<Level> LoadLevels()
{
IEnumerable<Level> lvlList = Enumerable.Empty<Level>(); ;
using (var client = new HttpClient())
{
client.BaseAddress = new Uri(ConfigurationManager.AppSettings["WebApiExUrl"]);
var responseTask = client.GetAsync("getlevel");
responseTask.Wait();
var result = responseTask.Result;
if (result.IsSuccessStatusCode)
{
var readTask = result.Content.ReadAsAsync<FormattedResult<Level>>();
readTask.Wait();
if (string.IsNullOrEmpty(readTask.Result.Error))
{
IEnumerable<Level> tempList = readTask.Result.Data;
lvlList = tempList.Select(m => new Level
{
Id = m.Id,
LvlName = m.LvlName,
LvlType = m.LvlType,
ParentLvl = m.ParentLvl,
Rating1 = m.Rating1,
Rating2 = m.Rating2,
hasChildren = tempList.Where(s => s.ParentLvl == m.Id).Count() > 0
});
}
}
}
return lvlList;
}
public JsonResult Save([DataSourceRequest] DataSourceRequest request, Level level)
{
if (level != null && ModelState.IsValid)
{
try
{
using (var client = new HttpClient())
{
client.BaseAddress = new Uri(ConfigurationManager.AppSettings["KpiApiUrl"]);
var postTask = client.PostAsJsonAsync("savelevel", level);
postTask.Wait();
var result = postTask.Result;
if (result.IsSuccessStatusCode)
{
var readTask = result.Content.ReadAsStringAsync();
readTask.Wait();
}
}
}
catch (Exception ex)
{
ModelState.AddModelError(string.Empty, "Unexpected error");
}
}
return Json(new[] { level }.ToTreeDataSourceResult(request, ModelState));
}
Model
public class Level
{
public int Id { get; set; }
public string LvlName { get; set; }
public string LvlType { get; set; }
public int? ParentLvl { get; set; }
[RegularExpression(#"^(\d{1,2}(\.\d{0,2})?)?(<|<=|>|>=)(\d{1,3}(\.\d{0,2})?)$", ErrorMessage = "Invalid")]
public string Rating1 { get; set; }
[RegularExpression(#"^(\d{1,2}(\.\d{0,2})?)?(<|<=|>|>=)(\d{1,3}(\.\d{0,2})?)$")]
public string Rating2 { get; set; }
}
If the 'Save' method returns
return Json(LoadLevels().ToDataSourceResult(request, ModelState), JsonRequestBehavior.AllowGet);
instead of
return Json(new[] { level }.ToTreeDataSourceResult(request, ModelState));
the TreeList shows duplicate records
The 'Save' event of TreeList also behaves in the same way.
function onSave() {
$("#lvlTreeList").data("kendoTreeList").dataSource.read();
}
Version Info: Telerik 2018.1.221.545, MVC 5.2, .NET 4.6
Please advise on this. Thanks.
Demo Link: https://demos.telerik.com/aspnet-mvc/treelist/editing
Calling read() in Sync event of DataSource, refreshes the TreeList and displays newly created level.
Razor Code
#(Html.Kendo().TreeList<..>()
.Name("lvlTreeList")
/*..*/
.DataSource(dataSource => dataSource
.Events(e => e.Sync("lvlTreeList_Sync"))
/*...*/
))
Javascript
<script>
function lvlTreeList_Sync() {
this.read();
}
</script>
Refer: https://www.telerik.com/forums/refresh-after-upda

MVC 3 Model binding and No parameterless constructor defined for this object

I created a view that was working wonderfully until I added some JQuery to support cascading drop downs. I believe in doing that, I broke the binding between the view and the model. I'm getting the error "No parameterless constructor defined for this object." when the form is submitted. The obvious solution would be to add a parameterless constructor, but I'm assuming that the postmodel will be null? Code Snippets below.
Thanks in Advance for your help.
View:
<script type="text/javascript">
$(document).ready(function () {
$("#ddlCategories").change(function () {
var iCategoryId = $(this).val();
$.getJSON(
"#Url.Content("~/Remote/SubCategoriesByCateogry")",
{ id: iCategoryId },
function (data) {
var select = ResetAndReturnSubCategoryDDL();
$.each(data, function (index, itemData) {
select.append($('<option/>', { value: itemData.Value, text: itemData.Text }));
});
});
});
function ResetAndReturnSubCategoryDDL() {
var select = $('#ddlSubCategory');
select.empty();
select.append($('<option/>', { value: '', text: "--Select SubCategory--" }));
return select;
}
});
...
<div class="editor-field">
#Html.DropDownList("iCategoryID", Model.Categories,"--Select Category--", new Dictionary<string,object>{ {"class","dropdowns"},{"id","ddlCategories"}})
#Html.ValidationMessage("iCategoryID")
</div>
<div class="editor-label">
#Html.LabelFor(model => model.SubCategories, "SubCategory")
</div>
<div class="editor-field">
#Html.DropDownListFor(model => model.SubCategories, new SelectList(Enumerable.Empty<SelectListItem>(), "iSubCategoryID", "SubCategory",Model.SubCategories), "--Select SubCategory--", new { id = "ddlSubCategory" })
#Html.ValidationMessage("iSubCategoryID")
</div>
Controller:
[HttpPost]
public ActionResult Create(VendorCreateModel postModel)
{
VendorCreateEditPostValidator createValidator = new VendorCreateEditPostValidator(
postModel.iCategoryID,
postModel.iSubCategoryID,
postModel.AppliedPrograms,
m_unitOfWork.ProgramRepository,
new ModelStateValidationWrapper(ModelState));
if (ModelState.IsValid)
{
int categoryId = int.Parse(postModel.iCategoryID);
int subcategoryId = int.Parse(postModel.iSubCategoryID);
var programIds = postModel.AppliedPrograms.Select(ap => int.Parse(ap));
var programs = m_unitOfWork.ProgramRepository.GetPrograms(programIds);
Vendor vendor = postModel.Vendor;
vendor.Category = m_unitOfWork.CategoryRepository.GetCategory(categoryId);
vendor.SubCategory = m_unitOfWork.SubCategoryRepository.GetSubCategory(subcategoryId);
foreach (Program p in programs)
vendor.Programs.Add(p);
m_unitOfWork.VendorRepository.Add(vendor);
m_unitOfWork.SaveChanges();
return RedirectToAction("Index");
}
VendorCreateModel model = new VendorCreateModel(
postModel.Vendor,
postModel.iCategoryID,
postModel.iSubCategoryID,
postModel.AppliedPrograms,
User.Identity.Name,
m_unitOfWork.CategoryRepository,
m_unitOfWork.SubCategoryRepository,
m_unitOfWork.PermissionRepository);
return View(model);
}
RemoteController:
[AcceptVerbs(HttpVerbs.Get)]
public JsonResult SubCategoriesByCateogry(int id)
{
System.Diagnostics.Debug.WriteLine(id);
var SubCategories = db.SubCategories
.Where(v => v.iCategoryID == id)
.OrderBy(v => v.sDesc)
.ToList();
var modelData = SubCategories.Select(v => new SelectListItem()
{
Text = v.sDesc,
Value = v.iSubCategoryID.ToString()
});
return Json(modelData, JsonRequestBehavior.AllowGet);
}
VendorCreateModel:
public class VendorCreateModel
{
public VendorCreateModel()
{
}
public VendorCreateModel(
Vendor vendor,
string categoryId,
string subcategoryId,
IEnumerable<string> appliedPrograms,
string username,
ICategoryRepository categoryRepository,
ISubCategoryRepository subcategoryRepository,
IPermissionRepository permissionRepository)
{
UserHasProgramsValidator programValidator = new UserHasProgramsValidator(username, permissionRepository);
var availablePrograms = programValidator.AvailablePrograms;
HashSet<Category> applicableCategories = new HashSet<Category>();
foreach (var p in availablePrograms)
foreach (var c in categoryRepository.GetCategoriesByProgram(p.iProgramID))
applicableCategories.Add(c);
this.Vendor = vendor;
this.AppliedPrograms = appliedPrograms;
this.Categories = new SelectList(applicableCategories.OrderBy(x => x.sDesc).ToList(), "iCategoryID", "sDesc");
this.SubCategories = new SelectList(subcategoryRepository.GetAllSubCategories().OrderBy(x => x.sDesc).ToList(), "iSubCategoryID", "sDesc");
if (!string.IsNullOrEmpty(categoryId))
{
int temp;
if (!int.TryParse(categoryId, out temp))
throw new ApplicationException("Invalid Category Identifier.");
}
this.iCategoryID = categoryId;
this.iSubCategoryID = subcategoryId;
this.ProgramItems = availablePrograms
.Select(p => new SelectListItem()
{
Text = p.sDesc,
Value = p.iProgramID.ToString(),
Selected = (AppliedPrograms != null ? AppliedPrograms.Contains(p.iProgramID.ToString()) : false)
});
}
public Vendor Vendor { get; set; }
public SelectList Categories { get; set; }
public SelectList SubCategories { get; set; }
public string iCategoryID { get; set; }
public string iSubCategoryID { get; set; }
public IEnumerable<SelectListItem> ProgramItems { get; set; }
[AtLeastOneElementExists(ErrorMessage = "Please select at least one program.")]
public IEnumerable<string> AppliedPrograms { get; set; }
}
I correct the issue and wanted to share in case someone else was banging their head against their desk like Ihave been. Basically I changed the dropdownlistfor to reflect:
#Html.DropDownListFor(model => model.iSubCategoryID, new SelectList(Enumerable.Empty<SelectListItem>(), "iSubCategoryID", "SubCategory",Model.SubCategories), "--Select SubCategory--", new Dictionary<string,object>{ {"class","dropdowns"},{"id","ddlSubCategory"},{"name","iSubCategoryID"}})
Assuming here the problem is in your VendorCreateModel, you either need to add a parameterless constructor or remove it, and create an instance in your action method and populate it by TryUpdateModel. Or parse the form using FormsCollection (not a fan).
You don't have the code for your viewmodel posted here but the basic assumption is that it will map.

Load data in Telerik grid by dropdownlist selected value

I am a beginner in Telerik Grid in ASP.NET MVC3. I try to bind Grid with dropdownlist selected value. Please see my code below.
My web model class
public class CustomerEventRolesModels
{
public int Event { get; set; }
public IEnumerable<System.Web.Mvc.SelectListItem> Events { get; set; }
public Telerik.Web.Mvc.GridModel<CustomerEventRolesModel> GridData { get; set; }
}
public class CustomerEventRolesModel : BaseNopEntityModel
{
public string Customer { get; set; }
public bool Sponsor { get; set; }
public bool Speaker { get; set; }
}
My .cshtml
<table id="grdCustomerEventRoleData" class="adminContent" style="display: none">
<tr>
<td>
<p>
</p>
</td>
</tr>
<tr>
<td>
#(Html.Telerik().Grid<CustomerEventRolesModel>(Model.GridData.Data)
.Name("grdCustomerEventRoles")
.Columns(columns =>
{
columns.Bound(x => x.Customer);
columns.Bound(x => x.Speaker).Template(x => Html.CheckBox("spk", x.Speaker));
columns.Bound(x => x.Sponsor).Template(x => Html.CheckBox("spn", x.Sponsor));
}
) .Pageable(settings => settings.Total(Model.GridData.Total)
.PageSize(gridPageSize)
.Position(GridPagerPosition.Both))
.ClientEvents(events => events.OnDataBinding("onDataBinding"))
.DataBinding(dataBinding => dataBinding.Ajax().Select("FilterByDropdown", "Customer"))
.EnableCustomBinding(true))
) )
</td>
</tr>
<script type="text/javascript">
var initialLoad = true;
$("#select-event").change(function () {
if ($("#select-event option:selected").val() > 0) {
$("#grdCustomerEventRoleData").show();
$("#grdCustomerEventRoles").data("tGrid").rebind();
}
else {
$("#grdCustomerEventRoleData").show();
}
});
function onDataBinding(e) {
if (initialLoad == true) {
e.preventDefault();
initialLoad = false;
}
else {
var classificationId = $("#select-event option:selected").val();
if (classificationId != "")
e.data = $.extend(e.data, {
selEvent: classificationId
});
else {
e.preventDefault();
$("#grdCustomerEventRoleData").hide();
}
}
}
Actions in controller
public ActionResult FirstBind()
{
if (!_permissionService.Authorize(StandardPermissionProvider.ManageCustomers))
return AccessDeniedView();
var model = new CustomerEventRolesModels();
model.Event = 0;
List<Nop.Core.Domain.Catalog.Product> products = _productRepository.Table.Where(p => p.EventDate != null && p.EventDate >= DateTime.Now).ToList();
model.Events = products.Select(p => new System.Web.Mvc.SelectListItem
{
Text = p.Name,
Value = p.Id.ToString()
});
var grdmodel = new GridModel<CustomerEventRolesModel>
{
Data = null,
Total = 0
};
model.GridData = grdmodel;
return View(model);
}
[HttpPost, GridAction(EnableCustomBinding = true)]
public ActionResult FilterByDropdown(GridCommand command, int selEvent)
{
if (!_permissionService.Authorize(StandardPermissionProvider.ManageCustomers))
return AccessDeniedView();
if (selEvent == 0)
return View();
var model = new CustomerEventRolesModels();
model.Event = selEvent;
var roles = (from lst in _customerEventRoleRepository.Table
join cust in _customerRepository.Table on lst.CustomerId equals cust.Id
join product in _productRepository.Table on lst.EventId equals product.Id
join role in _customerRoleRepository.Table on lst.RoleId equals role.Id
orderby lst.Id descending
select new CustomerEventRolesModel
{
Id = lst.Id,
Customer = cust.Email,
Sponsor = (role.Name == "Sponsor") ? true : false,
Speaker = (role.Name == "Speaker") ? true : false
}).ToList();
var grdmodel = new GridModel<CustomerEventRolesModel>
{
Data = roles,
Total = roles.Count
};
model.GridData = grdmodel;
return new JsonResult
{
Data = model
};
}
FilterByDropdown action is works correctly but Grid is not binded.
I am clueless.
Please help.
If you want to add a dropdown to a Telerik MVC Grid when editing a row, you will need to follow next few steps (aside from making the grid ajax bound and the rows editable).
Let’s say we want the column representing a name (“Name” from the model) to be a dropdown, from which a name can be selected rather than typed. Add a folder named “EditorTemplates” to the folder containing the view that the grid is on. It will contain a separate partial view for each dropdown we want to show in the row that is being edited. Make a partial view (mentioned above), name it e.g. “ClientName.cshtml”, containing a Telerik DropDownList named “Name” and bound to required list of names.
#(Html.Telerik().DropDownList()
.Name("Name")
.BindTo(new SelectList((IEnumerable)ViewData["CustomerNames"], "Text", "Value"))
)
Add the following attribute to the “Name” property of the data type that the grid uses e.g. Grid uses “Customer” class, containing “string Name” field:
public class Customer{ [UIHint("ClientName"), Required] public string Name { get; set; } }
The UIHint property specifies which field template to use when a specific column is rendered.
Add the following java script to the page containing the grid function:
function onEditCustomerList(e) { if (e.dataItem != null) { $(e.form).find('#Name').data('tDropDownList').select(function (dataItem) { return dataItem.Text == e.dataItem['Name']; });
} }
This should do the trick.
You're returning the wrong model.
Try this in FilterByDropdown:
var grdmodel = new GridModel<CustomerEventRolesModel>
{
Data = roles,
Total = roles.Count
};
return new JsonResult
{
Data = grdmodel
};

Multiple ViewModels in View

I'm looking to display two Telerik Kendo grids with different information(models) in one view and I'm not sure how to do it.
Model:
using System.Collections.Generic;
namespace KendoUIMvcApplication1.Models
{
public class Car
{
public int Id { get; set; }
public string Name { get; set; }
}
public class Truck
{
public int Id { get; set; }
public string Name { get; set; }
}
public class Vehicles
{
public IEnumerable<Car> CarCol { get; set; }
public IEnumerable<Truck> TruckCol { get; set; }
}
}
Controller (Creating some test objects):
using System.Collections.Generic;
using System.Web.Mvc;
using KendoUIMvcApplication1.Models;
namespace KendoUIMvcApplication1.Controllers
{
public class HomeController : Controller
{
public ActionResult Index()
{
var carList = new List<Car>();
var truckList = new List<Truck>();
var vehCol = new Vehicles();
var car1 = new Car
{
Id = 1,
Name = "Passat"
};
var car2 = new Car
{
Id = 2,
Name = "Passat"
};
carList.Add(car1);
carList.Add(car2);
var truck1 = new Truck
{
Id = 1,
Name = "S10"
};
var truck2 = new Truck
{
Id = 1,
Name = "Blazer"
};
truckList.Add(truck1);
truckList.Add(truck2);
vehCol.CarCol = carList;
vehCol.TruckCol = truckList;
return View(vehCol);
}
}
}
View (Here I'm trying to display the two grids. The first one for cars and the second one for trucks):
#using KendoUIMvcApplication1.Models
#model IEnumerable<Vehicles>
#*// Car Grid*#
#(Html.Kendo().Grid(Model)
.Name("Grid")
.Columns(columns => {
columns.Bound(c => c.Id);
columns.Bound(c => c.Name);
})
)
<div></div>
#*// Truck Grid*#
#(Html.Kendo().Grid(Model))
.Name("Grid")
.Columns(columns => {
columns.Bound(t => t.Id);
columns.Bound(t => t.Name);
})
)
Your model should be of type Vehicles:
#model Vehicles
Then you can access the two collections:
#Html.Kendo().Grid(Model.CarCol)
...
and
#Html.Kendo().Grid(Model.TruckCol)
...

Nested EditorTemplates in Telerik MVC Grid Edit Popup Window Not Displaying in Custom Edit Template

I have a grid using AJAX DATABINDING.
When I issue a POPUP EDITING command with TEMPLATENAME SPECIFIED my NESTED EDITOR TEMPLATES are not populating.
My Models
namespace eGate.BackOffice.WebClient.Model
{
public class TemplateTesterModel
{
public int TemplateModelId { get; set; }
public string TemplateModelName { get; set; }
public List<UserRole> UserRoles { get; set; }
}
}
{
public class TemplateTesterModels : List<TemplateTesterModel>
{
}
}
My View
#model eGate.BackOffice.WebClient.Model.TemplateTesterModels
#Html.EditorFor(m=>m)
#( Html.Telerik().Grid<eGate.BackOffice.WebClient.Model.TemplateTesterModel>()
.Name("Grid")
.DataKeys(keys => { keys.Add(m=>m.TemplateModelId); })
.Columns(columns =>
{
columns.Bound(o => o.TemplateModelId);
columns.Bound(o => o.TemplateModelName).Width(200);
columns.Bound(o => o.UserRoles).ClientTemplate(
"<# for (var i = 0; i < UserRoles.length; i++) {" +
"#> <#= UserRoles[i].RoleName #> <#" +
"} #>")
;
columns.Command(commands =>
{
commands.Edit().ButtonType(GridButtonType.Text);
}).Width(180).Title("Commands");
})
.DataBinding(dataBinding => dataBinding.Ajax()
.Select("_SelectAjaxEditing", "TemplateTester")
.Insert("_InsertAjaxEditing", "Grid")
.Update("_SaveAjaxEditing", "TemplateTester")
.Delete("_DeleteAjaxEditing", "TemplateTester")
)
.Editable(editable => editable.Mode(GridEditMode.PopUp).TemplateName("TemplateTesterModel"))
)
My Controller
namespace eGate.BackOffice.WebClient.Controllers
{
public class TemplateTesterController : Controller
{
public ActionResult Index()
{
return View(GetTemplateTesters());
//return View(new GridModel(GetTemplateTesters()));
}
private TemplateTesterModels GetTemplateTesters() {
TemplateTesterModels returnme = new TemplateTesterModels();
returnme.Add(new TemplateTesterModel());
returnme[0].TemplateModelId = 0;
returnme[0].TemplateModelName = "Template Tester 0";
returnme[0].UserRoles = new List<UserRole>();
returnme[0].UserRoles.Add(new UserRole() { RoleName = "Role1", IsChecked = true, Description = "Role for 1" });
returnme[0].UserRoles.Add(new UserRole() { RoleName = "Role2", IsChecked = false, Description = "Role for 2" });
returnme[0].UserRoles.Add(new UserRole() { RoleName = "Role3", IsChecked = false, Description = "Role for 3" });
return returnme;
}
[GridAction]
public ActionResult _SelectAjaxEditing()
{
return View(new GridModel(GetTemplateTesters()));
}
[AcceptVerbs(HttpVerbs.Post)]
[GridAction]
public ActionResult _SaveAjaxEditing(int id)
{
return View(new GridModel(GetTemplateTesters()));
}
[GridAction]
public ActionResult _InsertAjaxEditing(){
return View(new GridModel(GetTemplateTesters()));
}
[AcceptVerbs(HttpVerbs.Post)]
[GridAction]
public ActionResult _DeleteAjaxEditing(int id)
{
return View(new GridModel(GetTemplateTesters()));
}
}
}
My EditorTemplates
Shared/EditorTemplates/TemplateTesterModel.cshtml
#model eGate.BackOffice.WebClient.Model.TemplateTesterModel
<div>TemplateTesterModel Editor</div>
<div>#Html.EditorFor(m=>m.TemplateModelId)</div>
<div>#Html.EditorFor(m=>m.TemplateModelName)</div>
<div>Roles</div>
<div>#Html.EditorFor(m=>m.UserRoles)</div>
Shared/EditorTemplates/UserRole.cshtml
#model eGate.BackOffice.WebClient.Model.UserRole
<div>
I can has user role?
#Html.CheckBoxFor(m=>m.IsChecked)
</div>
This renders out as such:
As you can see the #Html.EditFor statements that precede the grid filter down through to the userrole EditorTemplate as expected. Additionally we can see that role data is in the grid because it is showing up in the role column.
But click the edit window and this is the result:
As you can see the UserRoles template is not populating with the roles on the UserRoles property of the TemplateTesterModel we're editing.
Am I missing something? Why is the .UserRoles property not populating in the telerik grid pop-up window?
This could be a "by design" decision of ASP.NET MVC. It does not automatically render display and editor templates for nested complex objects. I even have a blog post discussing this.
Long story short you need to create a custom editor template for the parent model.

Resources