With the following ASP.NET models
public class User { public string Name { get; set; } public LEmail LEmail { get; set; } } public class LEmail { public IList<CLabel> Labels; public IList<CEmail> Emails; } public class CLabels { public IList<CLabel> Labels { get; set; } } public class CLabel { public string Name { get; set; } } public abstract class CEmail { public string SelectedLabel { get; set; } public string Name { get; set; } }
Filling this with dummy data and sending the corresponding view as a User object, I have the following knockout definitions in the view:
@using (Html.BeginForm("MyAction", "MyController", FormMethod.Post, new { id = "MyEditor" })) { @Html.EditorFor(m => @Model.LEmail) <p> <input type="submit" value="Save" data-bind="enable: Emails().length > 0" /> <a href="/">Cancel</a> </p> <p data-bind="visible: saveFailed" class="error">A problem occurred saving the data.</p> <div id="debug" style="clear: both"> <hr /> <h2>Debug:</h2> <div data-bind="text: ko.toJSON(viewModel)"></div> </div> } <script type="text/javascript"> $(function() { ko.applyBindings(viewModel); $("#profileEditorForm").validate({ submitHandler: function(form) { if (viewModel.save()) window.location.href = "/"; return false; } }); }); var viewModel = { Name: ko.observable("@Model.Name"), Labels: ko.observableArray(@Html.Json(Model.LEmail.Labels) || []), Emails: ko.observableArray(@Html.Json(Model.LEmail.Emails) || []), addEmail: function() { viewModel.Emails.push(@Html.Json(new CEmail())); }, removeEmail: function(eml) { viewModel.Emails.remove(eml); }, saveFailed: ko.observable(false), </script>
And finally, the editor template, which should actually take care of a variable-length list, looks like this:
@model MyDomain.ViewModels.LEmail <table> <tbody data-bind="template: { name: 'EmailsTemplate', foreach: Emails }" /> </table> <button data-bind="click: addEmail">Add Email</button> <script id="EmailsTemplate" type="text/html"> <tr> <td> @* PROBLEM IS HERE!! Labels won't show (they will it this code taken out of template) *@ <select data-bind="options: Labels"></select></td> <td> <input type="text" data-bind="value: Name, uniqueName: true" class="required" /></td> <td> <a href="#" data-bind="click: function() { viewModel.removeEmail(this); }">Delete</a></td> </tr> </script>
Essentially I
- can't make it work in
EditorTemplate for combobox (or drop down list). It will not be attached to labels no matter what I do. If I take it out of the template somewhere else - it works as expected. Also, based on the choice to populate the "SelectedValue" inside the email - how to do it.
After everything is selected (it should be simple), how to publish it all back without losing value (its super-nested model, as you can see).
Thank you in advance!
source share