此篇範例程式 : 下載 (此範例在DynamicController之中)
呈上一篇,EditorTemplate (一) 我們可以來看到產生的原始碼如下
Name的部分是由 productList[index].屬性名組成,換句話說,如果今天要由前端動態新增一筆書籍資料,則必須按照這個規則編排下去,後端才能透過ViewModel的方式取得書籍資料
看起來一切美好圓滿,但如果今天的列表是可以新增之外,還要能動態刪除呢?
是不是我的[index]就要一直重新計算,不然送到後端就會不見了
*如果今天有4個textbox但是name分別是
productList[0].id
productList[1].id
productList[2].id
productList[5].id
這樣後端只會拿到0~2的ID,不按照順序編排的就會消失
還好.NET其實提供另外一種方式來繫結ViewModel
1 | <input type="hidden" name="productList.Index" value="0072b890-0e1a-4c93-a5a7-9cafe84b65f8" /> |
這樣的話就可以不用管排序,自由的新增刪除List的項目,但EditorTemplate也需要改一改,不然EditTemplate產出的是[0]這種格是,但是前端產出的格是是[Guid],這樣會有問題。
所以EditTemplate改成用這個方法產出
*以下程式碼轉載自:
搞搞就懂 - 點部落 :[ASP Net MVC] 如何綁定可動態新增或移除之資料集合(EditorTemplate)
新增一組HtmlHelper ```csharp
public static MvcHtmlString EditorForMany<TModel, TValue>(this HtmlHelper<TModel> html, Expression<Func<TModel, IEnumerable<TValue>>> expression, string htmlFieldName = null) where TModel : class { var items = expression.Compile()(html.ViewData.Model); var sb = new StringBuilder(); var hasPrefix = false; if (String.IsNullOrEmpty(htmlFieldName)) { var prefix = html.ViewContext.ViewData.TemplateInfo.HtmlFieldPrefix; hasPrefix = !String.IsNullOrEmpty(prefix); htmlFieldName = (prefix.Length > 0 ? (prefix + ".") : String.Empty) + ExpressionHelper.GetExpressionText(expression); } if (items != null) { foreach (var item in items) { var dummy = new { Item = item }; var guid = Guid.NewGuid().ToString(); var memberExp = Expression.MakeMemberAccess(Expression.Constant(dummy), dummy.GetType().GetProperty("Item")); var singleItemExp = Expression.Lambda<Func<TModel, TValue>>(memberExp, expression.Parameters); sb.Append(String.Format(@"<input type=""hidden"" name=""{0}.Index"" value=""{1}"" />", htmlFieldName, guid)); sb.Append(html.EditorFor(singleItemExp, null, String.Format("{0}[{1}]", hasPrefix ? ExpressionHelper.GetExpressionText(expression) : htmlFieldName, guid))); } } return new MvcHtmlString(sb.ToString()); }
}
1 |
|