7

我正在编写一个自定义验证集,它将在 div 上显示所有缺少的元素。我希望能够使用一个自定义@Html.BeginForm()方法来写出那个 div,但我真的不知道从哪里开始,因为这个坚果比写出标签或字符串的 html 扩展更难破解(表单封装了数据/控件并}在最后关闭)。

我查看了内置BeginForm()方法的元数据版本,它对我没有多大帮助。本质上,我只是想尽可能地扩展该方法,并让它写出将在 JavaScript 中显示/隐藏MvcHtmlString的 a 。div

最终我苦苦挣扎的地方是弄清楚如何编写这个具有开头和结尾组件的自定义助手。

@using(Html.BeginForm())
{
...

}

我希望能够做这样的事情:

@using(Html.VBeginForm())
{
...

}

并让它呈现我的额外 html

编辑:从下面的建议中添加代码

public class VBeginForm : IDisposable
{
    private readonly HtmlHelper _helper;
    public VBeginForm(HtmlHelper htmlHelper, string areaName)
    {
        _helper = htmlHelper;
        var container = new TagBuilder("form");
        container.GenerateId(areaName);
        var writer = _helper.ViewContext.Writer;
        writer.Write(container.ToString(TagRenderMode.StartTag));
    }

    public void Dispose()
    {
        _helper.ViewContext.Writer.Write("</form>");
    }
}
4

2 回答 2

6

HtmlHelper您需要为打印到的类编写扩展方法helper.ViewContext.Writer

该方法应返回IDisposable在其Dispose方法中打印结束标记的一个。

于 2011-06-17T14:38:03.410 回答
4

SLaks 的答案是正确的,但缺少一些额外的信息。

如果你想使用传统的(不是不显眼的)客户端验证,你需要提供一个 formContext,并给它一个 id,这样客户端验证才能工作。在他的解释中,这部分是缺失的。

实现这一点的最简单方法是使用返回MvcForm类的实例,该实例创建formContext并实现IDisposable接口。

在这个实现中,我需要提供表单的 id:

public static MvcForm BeginFormDatosAdicionales(this HtmlHelper htmlHelper, 
   string id, ..., IDictionary<string, object> htmlAttributes = null)
{
  TagBuilder form = new TagBuilder("form");
  // attributes
  form.MergeAttributes(htmlAttributes);
  // action
  string formAction = ...;
  form.MergeAttribute("action", formAction);
  // method
  FormMethod method = ...;
  form.MergeAttribute("method", HtmlHelper.GetFormMethodString(method), true);
  // id
  form.MergeAttribute("id", id);

  // writes the form's opening tag in the ViewContext.Writer
  htmlHelper.ViewContext.Writer.Write(form.ToString(TagRenderMode.StartTag));

  // creates an MvcForm (disposable), which creates a FormContext, needed for
  // client-side validation. You need to supply and id for it
  MvcForm theForm = new MvcForm(htmlHelper.ViewContext);
  htmlHelper.ViewContext.FormContext.FormId = form.Attributes["id"];

  // The returned object implements IDisposable, and writes the closing form tag
  return theForm;
  }

当然,这可以根据您的特定情况进行定制。如果您只想在绝对必要时为您的表单提供一个 id,请检查以下条件:

bool idRequired = htmlHelper.ViewContext.ClientValidationEnabled
&& !htmlHelper.ViewContext.UnobtrusiveJavaScriptEnabled;

在这种情况下,您必须小心为页面中的每个表单创建不同的 Id。例如,您可以添加一个整数后缀,该后缀可以存储在 HttpContext.Items 中,并在每次生成新 Id 时递增。这确保在单个页面中所有生成的 id 都是不同的。

HttpContext.Current.Items["lastFormId"]
于 2013-07-31T09:04:26.397 回答