[英]MVC 5 - How can I map an object to an Action when that object is a property of the view model for the page?
I have a login view model defined as such. 我有这样定义的登录视图模型 。
public class LoginViewModel
{
[Required]
public String Username { get; set; }
[Required]
[DataType(DataType.Password)]
public String Password { get; set; }
/// <summary>
/// The default constructor.
/// </summary>
public LoginViewModel()
{
}
}
And my master page takes a base view model defined as: 我的母版页采用定义为的基本视图模型 :
public abstract class CommonViewModel
{
#region Properties
public LoginViewModel LoginModel { get; set; }
#endregion
#region Functions
/// <summary>
/// The default constructor.
/// </summary>
public CommonViewModel()
{
}
#endregion
}
In master layout I have a login form . 在主布局中,我有一个登录表单 。 This form is laid out as such.
这种形式是这样布置的。
<form id="login-form" method="post" action="@Url.Action("Login", "Account")">
<div class="form-element">
@Html.LabelFor(m => m.LoginModel.Username, Resources.MasterPageStrings.LoginUsername, new { @class = "login-form-label" })
@Html.TextBoxFor(m => m.LoginModel.Username, new
{
@class = "login-form-input login-form-input-common required",
@autofocus = String.Empty,
@placeholder = Resources.MasterPageStrings.LoginUsername
})
</div>
<div class="form-element">
@Html.LabelFor(m => m.LoginModel.Password, Resources.MasterPageStrings.LoginPassword, new { @class = "login-form-label" })
@Html.TextBoxFor(m => m.LoginModel.Password, new
{
@class = "login-form-input login-form-input-common required",
@placeholder = Resources.MasterPageStrings.LoginPassword,
@type = "password"
})
</div>
<div class="form-element">
@Html.LabelFor(m => m.LoginModel.RememberMe, Resources.MasterPageStrings.LoginRememberMe, new { @class = "login-form-label" })
@Html.CheckBoxFor(m => m.LoginModel.RememberMe, new
{
@class = "login-form-input login-form-input-common",
@placeholder = Resources.MasterPageStrings.LoginRememberMe
})
</div>
<div class="form-element">
<input type="submit" class="login-form-submit login-form-input-common" value="@Resources.MasterPageStrings.LoginLoginLabel">
</div>
</form>
When I submit to the account controller, I don't have the login view model mapped. 当我提交给帐户控制器时,我没有映射登录视图模型。
/// <summary>
/// Logs the user into the application.
/// </summary>
/// <param name="model">The login view model uses to login.</param>
/// <returns>The view you were trying to get to.</returns>
[HttpPost]
[AllowAnonymous]
[Route("Login")]
public async Task<ActionResult> Login(Models.ViewModels.Common.LoginViewModel model)
{
}
The view model is always the default empty values of null for username and password. 视图模型始终是用户名和密码的默认空值null。 How can I get the login model to map in the account controller login action?
如何获取登录模型以映射到帐户控制器登录操作中?
I can't map to the common view model as I get an error that I can't instantiate an abstract class. 由于出现无法实例化抽象类的错误,因此无法映射到通用视图模型。
the reason why you are receiving null
is because you are sending the data based on the model of the view which is CommonViewModel
, if you take a property 收到
null
的原因是,如果您采用的是属性,则基于基于CommonViewModel
模型的CommonViewModel
发送数据
@Html.TextBoxFor(m => m.LoginModel.Password, new
{
@class = "login-form-input login-form-input-common required",
@placeholder = Resources.MasterPageStrings.LoginPassword,
@type = "password"
})
and if you see the rendered html
the name will be LoginModel.Password
but in the action you are trying to get LoginViewModel
which has no property LoginModel.Password
并且如果您看到
rendered html
则名称将为LoginModel.Password
但是在操作中,您尝试获取没有属性LoginModel.Password
LoginViewModel
so your action should be 所以你的动作应该是
[HttpPost]
[AllowAnonymous]
[Route("Login")]
public async Task<ActionResult> Login(CommonViewModel model)
{
var loginmodel= model.LoginModel; //here you can access the properties like loginmodel.Password
}
Update 更新资料
another solution is to name the Html Helpers
same as the name of properties
of LoginViewModel
so your view will be 另一个解决方案是将
Html Helpers
的名称与LoginViewModel
的properties
名称相同,这样您的视图将
<form id="login-form" method="post" action="@Url.Action("Login", "Account")">
<div class="form-element">
@Html.Label("Username", Resources.MasterPageStrings.LoginUsername, new { @class = "login-form-label" })
@Html.TextBox("Username", new
{
@class = "login-form-input login-form-input-common required",
@autofocus = String.Empty,
@placeholder = Resources.MasterPageStrings.LoginUsername
})
</div>
<div class="form-element">
@Html.Label("Password", Resources.MasterPageStrings.LoginPassword, new { @class = "login-form-label" })
@Html.TextBox("Password", new
{
@class = "login-form-input login-form-input-common required",
@placeholder = Resources.MasterPageStrings.LoginPassword,
@type = "password"
})
</div>
<div class="form-element">
@Html.Label("RememberMe", Resources.MasterPageStrings.LoginRememberMe, new { @class = "login-form-label" })
@Html.CheckBox("RememberMe", new
{
@class = "login-form-input login-form-input-common",
@placeholder = Resources.MasterPageStrings.LoginRememberMe
})
</div>
<div class="form-element">
<input type="submit" class="login-form-submit login-form-input-common" value="@Resources.MasterPageStrings.LoginLoginLabel">
</div>
</form>
and your action will be 你的动作将是
[HttpPost]
[AllowAnonymous]
[Route("Login")]
public async Task<ActionResult> Login(Models.ViewModels.Common.LoginViewModel model)
{
}
Try to change your Login action so that it takes a CommonViewModel instead of a LoginViewModel. 尝试更改您的Login操作,以使其使用CommonViewModel而不是LoginViewModel。
Or better pratice, separate the code for the view into a partial view, set model of that view to LoginViewModel and render the partial like this : 或者更好的做法是,将视图的代码分成部分视图,将该视图的模型设置为LoginViewModel,然后像这样呈现部分视图:
@Html.RenderPartial("_LoginView", Model.LoginModel )
(assuming that the model type on your base view is CommonViewModel) (假设基本视图上的模型类型为CommonViewModel)
Partial View was made for this kind of situation. 针对这种情况进行了部分查看。 Create a partial view and paste your login HTML.
创建局部视图并粘贴您的登录HTML。 Keep the model of partial view as LoginViewModel and render it in the master page.
将部分视图的模型保留为LoginViewModel并将其呈现在母版页中。 That's it!
而已!
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.