Разделение двух форм в одном виде в ASP.Net MVC - PullRequest
5 голосов
/ 05 июня 2009

Я объединил представление создания учетной записи и представление входа в систему в одном представлении. Так что это представление с двумя формами, но они смешиваются, когда я отправляю. Если я пытаюсь войти в систему и появляется сообщение об ошибке:

Html.ValidationSummary()

обе формы получают ошибку. И я начал переименовывать поля в loginPassword, createPassword, потому что в противном случае, когда я отправляю и пароль отсутствует, он помечается как отсутствующий с обеих сторон.

Как можно разделить эти две формы, чтобы они могли работать независимо в одном представлении / странице?

Ответы [ 5 ]

5 голосов
/ 05 июня 2009

Ах да, я должен был сделать именно это раньше. Я нашел способ установить флаг в ViewData, детализируя, какая форма была опубликована, а затем я создал свой собственный метод расширения для ValidationSummary.

Код сейчас не со мной, поэтому я постараюсь сделать для него сейчас воздушный код, очевидно, это просто концепция того, как это сделать, поэтому примите его за чистую монету.

Для начала я бы использовал ту же настройку, которую предложил tvanfosson для его EntryPageModel.

Просмотр - примечание Html.MyValidationSummary

<% using(Html.BeginForm("NewAccount", "Account")) %>
<% { %>
    <%= Html.MyValidationSummary("NewAccountForm") %>

    <%= Html.TextBox("NewAccount.FirstName") %>
    <%= Html.TextBox("NewAccount.LastName") %>
    <%= Html.TextBox("NewAccount.Email") %>
    <%= Html.Password("NewAccount.Password") %>
    <%= Html.Password("NewAccount.ConfirmPassword") %>
<% } %>

<% using(Html.BeginForm("Login", "Account")) %>
<% { %>
    <%= Html.MyValidationSummary("LoginForm") %>

    <%= Html.TextBox("Login.Email") %>
    <%= Html.Password("Login.Password") %>
<% } %>

Контроллер - примечание ViewData ["PostedForm"]

public class Account : Controller
{
    private EntryPageModel _viewModel;

    public ActionResult NewAccount(FormCollection formValues)
    {
        try
        {
            //binding and validation for _viewModel.NewAccount
        }
        catch
        {
            ViewData["PostedForm"] = "NewAccountForm";
            return View("RegisterAndLogin", _viewModel);
        }
    }

    public ActionResult Login(FormCollection formValues)
    {
        try
        {
            //binding and validation for _viewModel.Login
        }
        catch
        {
            ViewData["PostedForm"] = "LoginForm";
            return View("RegisterAndLogin", _viewModel); //You'll want to pass in a model
        }
    }
}

Пользовательское расширение HTML

namespace System.Web.Mvc
{
    public static class HtmlExtensions
    {
        public static string MyValidationSummary(this HtmlHelper html, string formName)
        {
            if (!string.IsNullOrEmpty(html.ViewData["PostedForm"])
                && (html.ViewData["PostedForm"] == formName))
            {
                return html.ValidationSummary();
            }

            return "";
        }
    }
}

HTHS, Charles

3 голосов
/ 05 июня 2009

Мне пришлось столкнуться с той же проблемой. Я обнаружил, что нет способа отделить сообщения проверки с помощью встроенного ValidationSummary (). Вот два предложения:

  1. Поместите сводку проверки в область, где она может применяться к обеим формам. Например, если формы входа в систему и регистрации расположены рядом, поместите сводку проверки в делитель, центрированный над обеими формами. Я нашел пример этого стиля на странице входа Махало .
  2. В соответствующих методах действия контроллера добавьте что-то в ViewData, указав, какое действие было вызвано. В представлении будет ValidationSummary для каждой формы, но каждая будет отображаться условно на основе того, что вы добавили в ViewData.

В любом случае поля формы должны иметь уникальные имена.

Я пошел с решением № 1, потому что был удовлетворен тем, как мне удалось заставить его выглядеть. Но если вам нужно, чтобы сводка проверки появлялась в двух разных местах в зависимости от того, какая форма была отправлена, перейдите с # 2.

2 голосов
/ 05 июня 2009

Входные элементы нуждаются в разных именах / идентификаторах, даже если они находятся в разных формах. Если у них нет разных имен, он будет запускать логику проверки для каждого элемента управления, поскольку он совпадает на основе имени элемента управления. Я думаю, что вы на правильном пути, изменив имена, чтобы различать их.

Я бы настроил его на составную модель, возможно, чтобы вы могли сделать что-то вроде (обратите внимание, это не полностью):

<%= Html.TextBox( "Login.Name" ) %>
<%= Html.TextBox( "Login.Password" ) %>


<%= Html.TextBox( "NewAccount.Name" ) %>
<%= Html.TextBox( "NewAccount.Password" ) %>
<%= Html.TextBox( "NewAccount.ConfirmPassword" ) %>

На стороне сервера используйте параметр префикса для подшивки

public ActionResult Login( [Bind(Prefix="Login")]AccountModel model )
{
    ...
}

И ваша модель будет выглядеть так:

public class AccountModel
{
      public string Name { get; set; }
      public string Password { get; set; }
      public string ConfirmPassword { get; set; }
}

public class EntryPageModel
{
     public AccountModel Login { get; set; }
     public AccountModel NewAccount { get; set; }
}
0 голосов
/ 05 июня 2009

Я не уверен, есть ли способ разделить ValidationSummary ().

Для ваших форм вы можете создавать классы моделей, с которыми будете связываться, с различными полями. Это не принесет вам много пользы от того, что вы уже получили.

0 голосов
/ 05 июня 2009

Если формы публикуются в совершенно разных действиях, то ваш ModelStateDictionary должен содержать только ошибки, которые были предоставлены вызванным действием.

Можете ли вы разместить соответствующий код?

...