【问题标题】:Multiple forms in ASP.NET MVCASP.NET MVC 中的多个表单
【发布时间】:2009-05-05 00:18:19
【问题描述】:

上下文
假设我有:
在布局 Site.Master:

<div class="leftColumn">
    <asp:ContentPlaceHolder ID="MainContent" runat="server" />
</div>
<div class="rightColumn">
    <% Html.RenderPartial("_Login"); %>
    <asp:ContentPlaceHolder ID="SideContent" runat="server" />
</div>

登录部分视图如下:

<form action="/myApp/Account/Login" method="post">
    <input name="name" />Name<br />
    <input name="password" type="password" />Password<br />
    <button>Login</button>
</form>

是否可以只更新登录小部件表单,而不是整个内容页面?

【问题讨论】:

    标签: asp.net-mvc forms post


    【解决方案1】:

    如果您指的是 http 帖子,则只有通过表单内的提交按钮启动的帖子(也可以由 javascript 启动)才会发布到服务器。

    如果您的表单是嵌套的,那么这将不起作用。外部表单将始终发布到服务器。

    在下面的示例 HTML 中,单击第一个表单上的提交按钮不会将值从第二个表单发送到服务器。同样,单击第二个提交按钮不会发布第一个表单中的值。

    <html>
    ...
      <body> 
        <div>
    
          <form action="/Login/Login" method="post">
            <input type="text" name="username" value="" />
            <input type="text" name="passowrd" value="" />
            <input type="submit" name="login" value="Login" />
          </form>
    
    
          <form action="/Login/AdminLogin" method="post">
            <input type="text" name="username" value="" />
            <input type="text" name="passowrd" value="" />
            <input type="submit" name="login" value="Login Admin" />
          </form>
        </div>
    </body>
    </html>
    

    如果您只想更新/更改其中一个表单部分,那么不使用 javascript 并执行 javascript 发布(又名Ajax)就无法做到这一点。

    【讨论】:

    • 耶...尽管这个问题肯定不清楚,但这正是我想听到的:“如果您只想更新/更改表单部分之一,那么不,这不能完成不使用”。到目前为止,似乎没有一种干净的方法可以在 asp.net mvc 中实现所谓的小部件。 ://
    • 这不是 MVC 的限制 - 您只要求更新页面的一部分,因此您必须在客户端做一些事情(例如 AJAX/JS),因为所有 HTML 表单的定义都会改变提交时的页面。
    • 问题刚刚打了“流行”徽章标记。令人惊讶地看到我学到了多少。这么愚蠢的问题。 :D
    【解决方案2】:

    如果您构建一个接受 FormCollection 的控制器方法并且您的视图定义了两个表单,则返回的 formcollection 将使用表单 A 或表单 B 中的值进行填充。您可以检查 formCollection 并根据值分支您的逻辑其中。如果您希望非常明确,您可以在两种形式中出现相同的隐藏变量,其值可以帮助您做出选择。

    这是一种方法。我敢肯定有几种方法可以解决这个问题。

    【讨论】:

      【解决方案3】:

      如果你有两种简单的形式,你可以使用这种方法:

      您创建了两个不同的局部视图。

      @model CustomerInfoModel
      @using (Ajax.BeginForm("CustomerInfo", "Customer", new AjaxOptions { HttpMethod = "Post", OnBegin = "InfoLoading", OnComplete = "InfoCompleted" }, new { id = "info", @class = "form-horizontal" }))
          {
          <input type="text" class="form-control" name="Name" id="Name" value="@Model.Name" />
          <input type="email" class="form-control" name="Email" id="Email"  value="@Model.Email" />
          <button type="submit" id="save-info" class="btn-medium red">Save</button>
          }
      

      @model CustomerPasswordChangeModel
      @using (Ajax.BeginForm("CustomerPasswordChange", "Customer", new AjaxOptions { HttpMethod = "Post", OnBegin = "InfoLoading", OnComplete = "InfoCompleted" }, new { id = "change", @class = "form-horizontal" }))
      {
      <input type="password" class="form-control" name="OldPassword" id="OldPassword"  value="" />
      <input type="password" class="form-control" name="NewPassword" id="NewPassword"  value="" />
      <button type="submit" id="save-change" class="btn-medium red" autocomplete="off">Save</button>
      }
      

      在您的父视图中,

      @Html.Partial("CustomerInfo", Model.CustomerInfo)
      

      @Html.Partial("CustomerPasswordChange", Model.CustomerPasswordChange)
      

      在控制器中:

          [HttpPost]
          public ActionResult CustomerInfo([Bind(Include = "Name,Email")] CustomerInfoModel model)
          {
              if (ModelState.IsValid)
                  return new Json(new { success=true, message="Updated.", errors=null);
      
      // do you logic
      
              return new Json(new { success=false, message="", errors=getHtmlContent(ModelState.Values.SelectMany(v => v.Errors).ToList(), "ModelError"));
          }
      
          [HttpPost]
          public ActionResult CustomerPasswordChange([Bind(Include = "OldPassword,NewPassword")] CustomerPasswordChangeModel model)
          {
              if (ModelState.IsValid)
                  return new Json(new { success=true, message="Updated.", errors=null);
      
      // do you logic
      
              return new Json(new { success=false, message="", errors=getHtmlContent(ModelState.Values.SelectMany(v => v.Errors).ToList(), "ModelError"));
          }
      

      这会做你想做的事。

      注意:getHtmlContent 方法只是生成要在页面上显示的错误消息。没什么特别的。如果需要,我可以分享。

      【讨论】:

        【解决方案4】:

        你的问题不是很清楚。

        但据我所知,答案很可能是肯定的。您可以根据用户输入更新任何您想要的内容。

        【讨论】:

        • 我也不明白您在问什么...您能否编辑您的问题以提供更多背景信息。您的第一个“表单”格式错误,没有任何输入元素......它是做什么用的?我认为模型视图状态只更新它试图绑定的字段......?那是登录小部件还是登录页面?还是您对验证消息和验证突出显示有问题?我必须创建一些自定义 HTMLHelper 扩展来处理多种表单,但我真的不知道它们是否适用于这里,因为我不明白你的问题是什么......更多信息会有所帮助。
        • 真的很抱歉。英语也不是我的母语。我会尝试编辑问题。
        【解决方案5】:
        if(pass != true) 
        { 
         ViewData["Message'] = "Hey your login failed!"; Return View("Login") 
        }
        

        在浏览页面上

        <form action="/tralala/Account/Login" method="post"> 
          <input name="name" />Name<br /> 
          <input name="password" type="password" />Password<br /> 
        
          <button>Login</button> 
         <div style="color: red"><%=ViewData["Message"] %><div> 
        </form>
        

        【讨论】:

        • 你没有抓住重点。问题是 - 如果可能的话,如何只更新 1 个表单,而不是如何使用 ViewData 字典。
        • 对不起老兄,我一直在看你的问题,我不明白你在问什么。
        • 我只是想问一下,如果页面有 2 个
          元素,一次只能更新其中的一个,而不会触及另一个。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2014-08-15
        相关资源
        最近更新 更多