我有一个模型,我想用它来生成/绑定一个弹出窗体,该窗体仍然隐藏在页面上,直到需要使用。
<table id="dlgNewEdit" class="vtableform hide">
<tr>
<td>@Html.CustomLabelFor(m => new NewEditModel().Name)</td>
<td>
@Html.HiddenFor(m => new NewEditModel().OemEquipmentMakeId)
@Html.CustomTextBoxFor(m => new NewEditModel().Name, new { @class = "focus w300" })
@Html.ValidationMessageFor(m => new NewEditModel().Name)
</td>
</tr>
<tr>
<td>@Html.CustomLabelFor(m => new NewEditModel().Description)</td>
<td>
@Html.CustomTextAreaFor(m => new NewEditModel().Description, new { @class = "w300" })
@Html.ValidationMessageFor(m => new NewEditModel().Description)
</td>
</tr>
</table>
导致:
<table id="dlgNewEdit" class="vtableform hide">
<tr>
<td><label class="required" for="Name">* Name</label></td>
<td>
<input data-val="true" data-val-number="The field OemEquipmentMakeId must be a number." data-val-required="The OemEquipmentMakeId field is required." id="OemEquipmentMakeId" name="OemEquipmentMakeId" type="hidden" value="0" />
<input autocomplete="off" class="required tip focus w300" data-val="true" data-val-length="Cannot exceed 50 characters" data-val-length-max="50" data-val-required="Required" id="Name" maxlength="50" name="Name" title="Enter the make name" type="text" value="" />
<span class="field-validation-valid" data-valmsg-for="Name" data-valmsg-replace="true"></span>
</td>
</tr>
<tr>
<td><label for="Description">Description</label></td>
<td>
<textarea class="w300 tip" cols="20" data-val="true" data-val-length="Cannot exceed 500 characters" data-val-length-max="500" id="Description" name="Description" rows="2" title="Enter a brief description">
</textarea>
<span class="field-validation-valid" data-valmsg-for="Description" data-valmsg-replace="true"></span>
</td>
</tr>
</table>
正如您所看到的,我无法想出任何方法来生成正确的表单ID /名称而不在我的所有表达式中使用“new NewEditModel()”。这样做很好,但似乎有点冗长。我希望我的字段名称与我的模型属性完全匹配,因为我希望模型在以下操作中绑定,该操作通过jQuery ajax调用:
[HttpPost]
[ValidateAntiForgeryToken]
public JsonNetResult New(NewEditModel model)
{
}
我尝试创建了一个变量:
var myModel = new NewEditModel();
使用:
@Html.HiddenFor(m => myModel.OemEquipmentMakeId)
但是这会生成id / name“myModel.OemEquipmentMakeId”,它不会在我的动作中绑定。有没有办法在不同的庄园里做我想做的事?
*编辑* 以下是视图的更详细表示。同样,我要从ajax形式来回传递的模型不是绑定到页面的模型。这是一个搜索结果页面。当用户单击行上的编辑时,我从服务器通过ajax获取记录并显示在弹出窗口中。单击弹出窗口上的确定通过ajax调用操作。这就是我希望模型在动作中正确绑定的地方。 bootdialog是一个自定义的jQuery插件,我改编自bootbox(Bootstrap模式插件),可以将DOM内容加载到弹出窗口中。
@model IndexModel
@section startupscripts
{
$('.command-add').on('click', function() { addMake(); })
$('#SearchGrid')
.on('click', '.command-edit', function() { editMake($(this).data('id')); })
.on('click', '.command-delete', function() { deleteMake($(this).data('id')); });
filter(@Model.Criteria.Page.GetValueOrDefault(1), '@Model.Criteria.SortExpression');
}
@section scripts {
<script type="text/javascript">
var _currentPage, _currentSort;
function filter(page, sort) {
...
}
function resetSearch() {
...
}
function addMake() {
notify();
bootdialog.prompt($('#dlgNewEdit'),
{
title: 'New OEM Equipment Make',
formAction: '@Url.Action("New")',
formMethod: 'POST',
showClose: false,
buttons: [
{
label: 'OK',
value: true,
isPrimary: true,
callback: function (data) {
notify('success', 'New OEM equipment make \'' + data.name + '\' successfully created');
filter(_currentPage, _currentSort);
}
},
{ label: 'Cancel', value: false }
]
});
}
function editMake(id) {
notify();
var bError = false;
// Load the information from the DB
$.ajax({
url: '@Url.Action("Edit")',
data: { id: id },
async: false,
cache: false,
type: 'GET',
error: function (xhr, status, error) {
notify('error', 'There was an error querying the database', error);
bError = true;
},
success: function (data) {
if (data.errors) {
for (var i = 0; i < data.errors.length; i++)
notify('error', 'There was an error querying the database', data.errors[i].message);
bError = true;
} else {
$('#dlgNewEdit #@Html.IdFor(m => new NewEditModel().OemEquipmentMakeId)').val(id);
$('#dlgNewEdit #@Html.IdFor(m => new NewEditModel().Name)').val(data.data.name);
$('#dlgNewEdit #@Html.IdFor(m => new NewEditModel().Description)').val(data.data.description);
}
}
});
if (bError) return;
bootdialog.prompt($('#dlgNewEdit'),
{
title: 'Edit OEM Equipment Make',
formAction: '@Url.Action("Edit")',
formMethod: 'POST',
showClose: false,
buttons: [
{
label: 'OK',
value: true,
isPrimary: true,
callback: function (data) {
notify('success', 'OEM equipment make \'' + data.name + '\' successfully updated');
filter(_currentPage, _currentSort);
}
},
{ label: 'Cancel', value: false }
]
});
}
function deleteMake(id) {
notify();
bootdialog.confirm(
'Are you sure you want to delete this OEM equipment make?',
{ title: 'Delete OEM Equipment Make' },
function (e) {
if (e) {
$.ajax({
type: 'POST',
async: false,
url: '@Url.Action("Delete")',
data: AddAntiForgeryToken({ id: id }),
success: function (data) {
if (data.data != null) {
notify('success', 'OEM equipment make \'' + data.data.name + '\' successfully deleted');
filter(_currentPage, _currentSort);
} else {
for (var i = 0; i < data.errors.length; i++)
notify('error', 'There was an error deleting the OEM equipment make', data.errors[i].message);
}
},
error: function (xhr, status, error) {
notify('error', 'There was an error deleting the OEM equipment make', error);
},
dataType: 'json'
});
}
}
);
}
</script>
}
<div class="row">
<div class="span3">
<div class="well well-side">
@using (Html.BeginForm("SearchGrid", null, FormMethod.Get, new {id = "frmSearch"}))
{
<div class="vertical-control-group">
@Html.CustomLabelFor(m => m.Criteria.Name)
@Html.CustomTextBoxFor(m => m.Criteria.Name)
</div>
<div class="vertical-control-group-commands">
@Html.CustomLinkButton("Search", new { @class = "btn-primary", onclick = "filter(1, 'Name');", title = "Click to search" })
@Html.CustomLinkButton("Reset", new { onclick = "resetSearch();", title = "Click to reset" })
</div>
@Html.HiddenFor(m => m.Criteria.Page)
@Html.HiddenFor(m => m.Criteria.SortExpression)
}
<div class="vertical-control-group-divider"></div>
<div class="vertical-control-group-commands">
<a href="javascript:void(0);" class="btn btn-inverse tip command-add" title ="Create new make">New Make</a>
</div>
</div>
</div>
<div class="span9" id="SearchGrid">
@{
Html.RenderAction("Loading", "Master", new { area = "", text = "Loading makes. Please wait..." });
}
</div>
</div>
<table id="dlgNewEdit" class="vtableform hide">
<tr>
<td>@Html.CustomLabelFor(m => new NewEditModel().Name)</td>
<td>
@Html.HiddenFor(m => new NewEditModel().OemEquipmentMakeId)
@Html.CustomTextBoxFor(m => new NewEditModel().Name, new { @class = "focus w300" })
@Html.ValidationMessageFor(m => new NewEditModel().Name)
</td>
</tr>
<tr>
<td>@Html.CustomLabelFor(m => new NewEditModel().Description)</td>
<td>
@Html.CustomTextAreaFor(m => new NewEditModel().Description, new { @class = "w300" })
@Html.ValidationMessageFor(m => new NewEditModel().Description)
</td>
</tr>
</table>
答案 0 :(得分:0)
我刚刚启动了一个MVC3项目,并将其添加为索引视图。
@using MvcApplication3.Models
@model NewEditModel
@{
ViewBag.Title = "Home Page";
}
<div>
@using (Html.BeginForm())
{
@Html.TextBoxFor(m=>m.Name)
<input type="submit" value="submit"/>
}
</div>
在HomeController中我添加了:
public class HomeController : Controller
{
public ActionResult Index()
{
return View();
}
[HttpPost]
public ActionResult Index(NewEditModel model)
{
//model contains the name from the view
return View();
}
}
从表单发布的值显示在模型中。
所以不需要new NewEditModel()
因此,基于您的视图,我仍然建议使用部分视图。
将表格拉成部分视图,例如名为“_SearchTable”,设置模型并使用m => m.Property
语法,然后在视图中,您只需将表替换为@Html.Partial("_SearchTable", new NewEditModel())
这是一个新的局部视图:
@model NewEditModel
<table id="dlgNewEdit" class="vtableform hide">
<tr>
<td>@Html.CustomLabelFor(m => m.Name)</td>
<td>
@Html.HiddenFor(m => m.OemEquipmentMakeId)
@Html.CustomTextBoxFor(m => m.Name, new { @class = "focus w300" })
@Html.ValidationMessageFor(m => m.Name)
</td>
</tr>
<tr>
<td>@Html.CustomLabelFor(m => m.Description)</td>
<td>
@Html.CustomTextAreaFor(m => m.Description, new { @class = "w300" })
@Html.ValidationMessageFor(m => m.Description)
</td>
</tr>
</table>
并且您的索引视图变为:
@model IndexModel
@section startupscripts
{
$('.command-add').on('click', function() { addMake(); })
$('#SearchGrid')
.on('click', '.command-edit', function() { editMake($(this).data('id')); })
.on('click', '.command-delete', function() { deleteMake($(this).data('id')); });
filter(@Model.Criteria.Page.GetValueOrDefault(1), '@Model.Criteria.SortExpression');
}
@section scripts {
<script type="text/javascript">
var _currentPage, _currentSort;
function filter(page, sort) {
...
}
function resetSearch() {
...
}
function addMake() {
notify();
bootdialog.prompt($('#dlgNewEdit'),
{
title: 'New OEM Equipment Make',
formAction: '@Url.Action("New")',
formMethod: 'POST',
showClose: false,
buttons: [
{
label: 'OK',
value: true,
isPrimary: true,
callback: function (data) {
notify('success', 'New OEM equipment make \'' + data.name + '\' successfully created');
filter(_currentPage, _currentSort);
}
},
{ label: 'Cancel', value: false }
]
});
}
function editMake(id) {
notify();
var bError = false;
// Load the information from the DB
$.ajax({
url: '@Url.Action("Edit")',
data: { id: id },
async: false,
cache: false,
type: 'GET',
error: function (xhr, status, error) {
notify('error', 'There was an error querying the database', error);
bError = true;
},
success: function (data) {
if (data.errors) {
for (var i = 0; i < data.errors.length; i++)
notify('error', 'There was an error querying the database', data.errors[i].message);
bError = true;
} else {
$('#dlgNewEdit #@Html.IdFor(m => new NewEditModel().OemEquipmentMakeId)').val(id);
$('#dlgNewEdit #@Html.IdFor(m => new NewEditModel().Name)').val(data.data.name);
$('#dlgNewEdit #@Html.IdFor(m => new NewEditModel().Description)').val(data.data.description);
}
}
});
if (bError) return;
bootdialog.prompt($('#dlgNewEdit'),
{
title: 'Edit OEM Equipment Make',
formAction: '@Url.Action("Edit")',
formMethod: 'POST',
showClose: false,
buttons: [
{
label: 'OK',
value: true,
isPrimary: true,
callback: function (data) {
notify('success', 'OEM equipment make \'' + data.name + '\' successfully updated');
filter(_currentPage, _currentSort);
}
},
{ label: 'Cancel', value: false }
]
});
}
function deleteMake(id) {
notify();
bootdialog.confirm(
'Are you sure you want to delete this OEM equipment make?',
{ title: 'Delete OEM Equipment Make' },
function (e) {
if (e) {
$.ajax({
type: 'POST',
async: false,
url: '@Url.Action("Delete")',
data: AddAntiForgeryToken({ id: id }),
success: function (data) {
if (data.data != null) {
notify('success', 'OEM equipment make \'' + data.data.name + '\' successfully deleted');
filter(_currentPage, _currentSort);
} else {
for (var i = 0; i < data.errors.length; i++)
notify('error', 'There was an error deleting the OEM equipment make', data.errors[i].message);
}
},
error: function (xhr, status, error) {
notify('error', 'There was an error deleting the OEM equipment make', error);
},
dataType: 'json'
});
}
}
);
}
</script>
}
<div class="row">
<div class="span3">
<div class="well well-side">
@using (Html.BeginForm("SearchGrid", null, FormMethod.Get, new {id = "frmSearch"}))
{
<div class="vertical-control-group">
@Html.CustomLabelFor(m => m.Criteria.Name)
@Html.CustomTextBoxFor(m => m.Criteria.Name)
</div>
<div class="vertical-control-group-commands">
@Html.CustomLinkButton("Search", new { @class = "btn-primary", onclick = "filter(1, 'Name');", title = "Click to search" })
@Html.CustomLinkButton("Reset", new { onclick = "resetSearch();", title = "Click to reset" })
</div>
@Html.HiddenFor(m => m.Criteria.Page)
@Html.HiddenFor(m => m.Criteria.SortExpression)
}
<div class="vertical-control-group-divider"></div>
<div class="vertical-control-group-commands">
<a href="javascript:void(0);" class="btn btn-inverse tip command-add" title ="Create new make">New Make</a>
</div>
</div>
</div>
<div class="span9" id="SearchGrid">
@{
Html.RenderAction("Loading", "Master", new { area = "", text = "Loading makes. Please wait..." });
}
</div>
</div>
@Html.Partial("_SearchTable", new NewEditModel())