您好我正在尝试使用Bootstrap模式在asp .net mvc中创建一个页面(CRUD操作)。我研究了一些文章,发现部分观点最适合这种方法。我已经完成了大部分功能,但遇到了一些问题。请检查并指导。
这是我的主要索引视图。这是将在其他页面中使用的局部视图。此视图显示插入到数据库中的数据,并具有为添加和编辑操作呈现部分视图的Div:
<div class="grading" id="tblUserEducation">
<div class="persn-detl sp-0">
<p>
<h3>Education</h3>
<a href="javascript:void()" data-toggle="modal" data-target="#userEducationModal">Add Education</a>
</p>
@foreach (var item in Model.userEducationVm)
{
<div class="col-xs-12">
<h5>@Html.DisplayFor(modelItem => item.School) </h5>
<div>@Html.DisplayFor(modelItem => item.Degree), @Html.DisplayFor(modelItem => item.Fieldofstudy), @Html.DisplayFor(modelItem => item.Grade)</div>
@if (item.Activities != null)
{
<p>
Activities: @Html.DisplayFor(modelItem => item.Activities)
</p>
}
<p>From Year: @Html.DisplayFor(modelItem => item.FromYear) To Year @Html.DisplayFor(modelItem => item.ToYear)</p>
@if (item.Description != null)
{
<p>
Description:<br />
@Html.DisplayFor(modelItem => item.Description)
</p>
}
<div class="add-editing">
<ul>
<li><a href="javascript:void()" onclick="editUserEducation(@item.Id)"><i class="fa fa-pencil-square-o" aria-hidden="true"></i></a></li>
</ul>
</div>
</div>
}
</div>
</div>
<!-- Modal -->
<div class="modal fade" id="userEducationModal" role="dialog" data-backdrop="static" data-keyboard="false">
<div class="modal-dialog">
<!-- Modal content-->
<div class="modal-content">
<div class="modal-header">
<button id="btnCloseEducationModal" type="button" class="close" data-dismiss="modal">×</button>
<h4 class="modal-title">Education</h4>
</div>
<div class="modal-body" id="divUserEducation" style="height:500px;overflow-x:auto !important;">
@{Html.RenderAction("Create", "UserEducation"); }
</div>
<div class="modal-footer"> </div>
</div>
</div>
</div>
我的创建局部视图(删除了一些HTML):
@using (Ajax.BeginForm("Create", "UserEducation", new AjaxOptions { HttpMethod = "POST", UpdateTargetId = "divUserEducation" }))
{
@Html.AntiForgeryToken()
<div>
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
<div class="form-group">
<label for="School" class="form-control-label">School:</label>
@Html.EditorFor(model => model.School, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.School, "", new { @class = "text-danger" })
</div>
<div class="form-group">
<label for="Degree" class="form-control-label">Degree:</label>
@Html.EditorFor(model => model.Degree, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.Degree, "", new { @class = "text-danger" })
</div>
</div>
<div>
<input type="submit" value="Save" class="btn btn-success" />
</div>
}
这是我的索引和创建控制器:
public ActionResult Index()
{
var model = new UserEducationViewModel
{
userEducationVm = userEducationService.getUserEducationAllRecords(),
YearsInDropDown = clsCommonMethods.getYearsForDropDown()
};
return PartialView("_UserEducationIndex", model);
}
[HttpPost]
public ActionResult Create(UserEducationViewModel vObj)
{
try
{
if (ModelState.IsValid)
{
UserEducation obj = new UserEducation();
obj.School = vObj.School;
obj.Degree = vObj.Degree;
obj.Fieldofstudy = vObj.Fieldofstudy;
obj.Grade = vObj.Grade;
obj.Activities = vObj.Activities;
obj.FromYear = vObj.FromYear;
obj.ToYear = vObj.ToYear;
obj.Description = vObj.Description;
obj.Description = vObj.Description;
userEducationService.insertUserEducation(obj);
return RedirectToAction("Index");
}
else
{
vObj.YearsInDropDown = clsCommonMethods.getYearsForDropDown();
return PartialView("~/Areas/MemberArea/Views/UserEducation/_UserEducationCreate.cshtml", vObj);
}
}
catch
{ return RedirectToAction("Index"); }
}
以下是我面临的一些问题:
我想在数据成功保存时更新索引视图,并希望在出现任何验证错误时显示包含错误消息的创建表单。
如果我将UpdateTargetId更改为“tblUserEducation”,它会更新索引页面上的新条目,但是当出现验证错误时,它不会在弹出窗口中显示创建页面。
这是我的ViewModel类:
public class UserEducationViewModel : IValidatableObject
{
public int Id { get; set; }
public string UserId { get; set; }
[Required]
public string School { get; set; }
[Required]
public string Degree { get; set; }
[Required]
[Display(Name = "Field of Study")]
public string Fieldofstudy { get; set; }
[Required]
public string Grade { get; set; }
public string Activities { get; set; }
[Required]
[Display(Name = "From Year")]
public Nullable<int> FromYear { get; set; }
[Required]
[Display(Name = "To Year")]
public Nullable<int> ToYear { get; set; }
public string Description { get; set; }
public virtual AspNetUser AspNetUser { get; set; }
public List<UserEducation> userEducationVm { get; set; }
public List<SelectListItem> YearsInDropDown { get; set; }
public IEnumerable<ValidationResult> Validate(ValidationContext validationContext)
{
if (ToYear < FromYear)
{
yield return new ValidationResult("To Year cannot be smaller than From year.", new[] { nameof(ToYear) });
}
}
}
答案 0 :(得分:0)
将Ajax.BeginForm()
替换为Html.BeginForm()
并使用jquery ajax()
方法提交表单,如果有错误,请让方法返回JsonResult
个错误。然后,如果有错误,您可以使用错误更新DOM,或者如果成功,只需根据表单控件中已有的值为新元素添加html(该方法需要返回的唯一额外数据)是您创建的对象的新ID。
您的表单将
@using (Html.BeginForm("Create", "UserEducation"))
{
.... // form controls etc as above
}
以及处理提交的脚本
var url = '@Url.Action("Create", "UserEducation")';
$('form').submit(function(e) {
e.preventDefault(); // cancel the default submit
if (!$(this).valid()) {
return; // exit if there are client side errors
}
var formData = $(this).serialize();
$.post(url, formData, function(response) {
if (response.success) {
var id = response.id;
// Build html for new item based on the values in the form
// See notes below
$('#userEducationModal').hide(); // Close the modal form
} else {
$.each(response.errors, function(index, item) {
// Find the corresponding element generated by ValidationMessageFor()
var placeholder = $('span[data-valmsg-for="' + item.propertyName + '"]');
var message = $('<span></span>').text(item.errorMessage);
placeholder.addClass('field-validation-error').removeClass('field-validation-valid').append(message);
}
}
});
});
你的控制器方法将是
[HttpPost]
public JsonResult Create(UserEducationViewModel vObj)
{
if (!ModelState.IsValid)
{
var errors = ModelState.Keys.Where(k => ModelState[k].Errors.Count > 0).Select(k => new { propertyName = k, errorMessage = ModelState[k].Errors[0].ErrorMessage });
return Json( new { success = false, errors = errors });
}
try
{
// Map the view model to the data model, save and return the new ID
return Json( new { success = true, id = obj.Id })
}
catch
{
// Not sure what you want to do here, but returning a friendly error message seems appropriate
}
}
要添加html,最简单的方法是在隐藏的div元素中添加“模板”,例如
<div id="template" style="display:none">
<!-- Repeat the same html that is in your foreach loop without the object values, but add class names so elements can be easily selected -->
<div class="col-xs-12">
<h5 class="school"></h5>
<div class="degree"></div>
....
</div>
如果您为包含这些类名的对象创建自定义DisplayTemplate
,那就更容易了,然后您可以用
foreach
循环
@Html.DisplayFor(m => m.userEducationVm)
将为集合中的每个项生成正确的html,然后添加
<div id="template" style="display:none">@Html.DisplayFor(m => m.NewUser)</div>
其中,属性NewUser
是视图模型中UserEducationViewModel
的默认实例。然后添加新html的代码变为
var clone = $('#template').clone();
// update the values based on the form controls
clone.find('.school').text($('#School').val());
...
// Append it to the DOM
tblUserEducation.append(clone.html);