ASP.NET MVC 3 Razor - 为EditorFor添加类

时间:2011-01-01 22:59:31

标签: asp.net-mvc asp.net-mvc-3 razor

我正在尝试将一个类添加到输入中。

这不起作用:

@Html.EditorFor(x => x.Created, new { @class = "date" })

16 个答案:

答案 0 :(得分:177)

Html.EditorFor添加一个类是没有意义的,因为在其模板中你可以有许多不同的标签。因此,您需要在编辑器模板中分配类:

@Html.EditorFor(x => x.Created)

并在自定义模板中:

<div>
    @Html.TextBoxForModel(x => x.Created, new { @class = "date" })
</div>

答案 1 :(得分:140)

从ASP.NET MVC 5.1开始,可以向EditorFor添加一个类(原始问题指定了ASP.NET MVC 3,并且接受的答案仍然是考虑到的最佳答案)。

@Html.EditorFor(x=> x.MyProperty,
    new { htmlAttributes = new { @class = "MyCssClass" } })

请参阅: What's New in ASP.NET MVC 5.1, Bootstrap support for editor templates

答案 2 :(得分:101)

您无法为通用EditorFor设置类。如果你知道你想要的编辑器,你可以直接使用它,在那里你可以设置类。您无需构建任何自定义模板。

@Html.TextBoxFor(x => x.Created, new { @class = "date" }) 

答案 3 :(得分:36)

您可以使用:

@Html.EditorFor(x => x.Created, new { htmlAttributes = new { @class = "date" } })

(至少在ASP.NET MVC 5中,但我不知道ASP.NET MVC 3是怎么回事。)

答案 4 :(得分:29)

我有同样令人沮丧的问题,我不想创建一个应用于所有DateTime值的EditorTemplate(我的UI中有时候我想要显示时间而不是jQuery UI drop-日历)。在我的研究中,我遇到的根本问题是:

  • 标准的 TextBoxFor 帮助器允许我应用自定义类的“日期选择器”来渲染不显眼的jQuery UI日历,但TextBoxFor不会在没有时间的情况下格式化DateTime,因此导致日历渲染失败。
  • 标准 EditorFor 会将DateTime显示为格式化字符串(使用[DisplayFormat(ApplyFormatInEditMode = true, DataFormatString = "{0:dd/MM/yyyy}")]等适当属性修饰时,但不允许我应用自定义“日期 - 选择器“class。

因此,我创建了具有以下好处的自定义HtmlHelper类:

  • 该方法自动将DateTime转换为jQuery日历所需的ShortDateString(如果时间存在,jQuery将失败)。
  • 默认情况下,帮助程序将应用所需的htmlAttributes来显示jQuery日历,但如果需要,可以覆盖它们。
  • 如果日期为null,则ASP.NET MVC会将日期1/1/0001作为值。

此方法用空字符串替换它。

public static MvcHtmlString CalenderTextBoxFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty>> expression, object htmlAttributes = null)
{
    var mvcHtmlString = System.Web.Mvc.Html.InputExtensions.TextBoxFor(htmlHelper, expression, htmlAttributes ?? new { @class = "text-box single-line date-picker" });
    var xDoc = XDocument.Parse(mvcHtmlString.ToHtmlString());
    var xElement = xDoc.Element("input");
    if (xElement != null)
    {
        var valueAttribute = xElement.Attribute("value");
        if (valueAttribute != null)
        {
            valueAttribute.Value = DateTime.Parse(valueAttribute.Value).ToShortDateString();
            if (valueAttribute.Value == "1/1/0001")
                valueAttribute.Value = string.Empty;
        }
    }
    return new MvcHtmlString(xDoc.ToString());
}

对于那些想要了解查找具有date-picker类装饰的对象的JQuery语法然后呈现日历的人,这里是:

$(document).ready(function () {
    $('.date-picker').datepicker({ inline: true, maxDate: 0, changeMonth: true, changeYear: true });
    $('.date-picker').datepicker('option', 'showAnim', 'slideDown');
});

答案 5 :(得分:15)

可以通过AdditionalViewData提供类或其他信息 - 我使用它来允许用户基于数据库字段(propertyName,editorType和editorClass)创建表单。

基于您的初始示例:

@Html.EditorFor(x => x.Created, new { cssClass = "date" })

并在自定义模板中:

<div>
    @Html.TextBoxFor(x => x.Created, new { @class = ViewData["cssClass"] })
</div>

答案 6 :(得分:8)

没有任何EditorFor覆盖允许您传入一个匿名对象,该对象的属性会以某种方式作为属性添加到某个标记上,尤其是对于内置编辑器模板。您需要编写自己的自定义编辑器模板,并将所需的值作为附加的viewdata传递。

答案 7 :(得分:2)

使用jQuery,您可以轻松完成:

$("input").addClass("class-name")

这是您的输入标记

@Html.EditorFor(model => model.Name)

对于DropDownlist,你可以使用这个:

$("select").addClass("class-name")

对于下拉列表:

@Html.DropDownlistFor(model=>model.Name)

答案 8 :(得分:2)

@Html.EditorFor(m=>m.Created ...) 

不允许为文本框传递任何参数

这是您应用属性的方法。

@Html.TextBoxFor(m=>m.Created, new { @class= "date", Name ="myName", id="myId" })

答案 9 :(得分:1)

您可以创建相同的行为,创建一个名为DateTime.cshtml的简单自定义编辑器,将其保存在Views / Shared / EditorTemplates中

@model DateTime

@{
    var css = ViewData["class"] ?? "";
    @Html.TextBox("", (Model != DateTime.MinValue? Model.ToString("dd/MM/yyyy") : string.Empty), new { @class = "calendar medium " + css});
}

并在您的观看中

@Html.EditorFor(model => model.StartDate, new { @class = "required" })

请注意,在我的示例中,我正在编写两个css类和日期格式。当然,你可以改变这一点。 您也可以对其他html属性执行相同操作,例如readonly,disabled等。

答案 10 :(得分:1)

我使用CSS属性选择器的另一个解决方案来获得你需要的东西。

指出您知道的HTML属性,并将其放入您想要的相对样式中。

如下所示:

input[type="date"]
{
     width: 150px;
}

答案 11 :(得分:1)

无需为MVC 4创建自定义模板。使用 TextBox 而不是 EditFor 此处不支持特殊的html属性,仅支持MVC 5. TextBox是应该支持MVC 4,我不知道其他版本。

@Html.TextBox("test", "", new { @id = "signupform", @class = "form-control", @role = "form",@placeholder="Name" })

答案 12 :(得分:1)

虽然问题针对的是MVC 3.0,但我们发现MVC 4.0中仍然存在问题。 MVC 5.0现在本身包含htmlAttributes的重载。

我被迫在我目前的工作地点使用MVC 4.0,并且需要为JQuery集成添加一个css类。我使用一种扩展方法解决了这个问题...

扩展方法:

using System.Linq;
using System.Web.Mvc;
using System.Web.Routing;
using System.Xml.Linq;

namespace MyTest.Utilities
{
    public static class MVCHelperExtensionMethods
    {
        public static MvcHtmlString AddHtmlAttributes(this MvcHtmlString input, object htmlAttributes)
        {
            // WE WANT TO INJECT INTO AN EXISTING ELEMENT.  IF THE ATTRIBUTE ALREADY EXISTS, ADD TO IT, OTHERWISE
            // CREATE THE ATTRIBUTE WITH DATA VALUES.

            // USE XML PARSER TO PARSE HTML ELEMENT
            var xdoc = XDocument.Parse(input.ToHtmlString());
            var rootElement = (from e in xdoc.Elements() select e).FirstOrDefault();

            // IF WE CANNOT PARSE THE INPUT USING XDocument THEN RETURN THE ORIGINAL UNMODIFIED.
            if (rootElement == null)
            {
                return input;
            }

            // USE RouteValueDictionary TO PARSE THE NEW HTML ATTRIBUTES
            var routeValueDictionary = new RouteValueDictionary(htmlAttributes);

            foreach (var routeValue in routeValueDictionary)
            {
                var attribute = rootElement.Attribute(routeValue.Key);

                if (attribute == null)
                {
                    attribute = new XAttribute(name: routeValue.Key, value: routeValue.Value);
                    rootElement.Add(attribute);
                }
                else
                {
                    attribute.Value = string.Format("{0} {1}", attribute.Value, routeValue.Value).Trim();
                }
            }

            var elementString = rootElement.ToString();
            var response = new MvcHtmlString(elementString);
            return response;
        }
    }
}

HTML标记用法:

@Html.EditorFor(expression: x => x.MyTestProperty).AddHtmlAttributes(new { @class = "form-control" })

(确保在剃刀视图中包含扩展方法的命名空间)

<强>说明: 我们的想法是注入现有的HTML。我选择使用XDocument.Parse()使用Linq-to-XML解析当前元素。我将htmlAttributes作为类型object传递。我利用MVC RouteValueDictionary来解析传入的htmlAttributes。我合并它们已经存在的属性,或者添加一个新属性(如果它还不存在)。

如果XDocument.Parse()无法解析输入,我放弃所有希望并返回原始输入字符串。

现在我可以使用DisplayFor的好处(适当地渲染货币等数据类型),但也能够指定css类(以及任何其他属性)。可以帮助您添加data-*ng-*(Angular)等属性。

答案 13 :(得分:0)

你也可以通过jQuery做到这一点:

$('#x_Created').addClass(date);

答案 14 :(得分:0)

我只需要在一个页面上设置一个文本框的大小。模型上的编码属性和创建自定义编辑器模板都是过度的,所以我只是用@ span标记包装@Html.EditorFor调用,该标记调用了一个指定文本框大小的类。

CSS类声明:

.SpaceAvailableSearch input
{
    width:25px;
}

查看代码:

<span class="SpaceAvailableSearch">@Html.EditorFor(model => model.SearchForm.SpaceAvailable)</span>

答案 15 :(得分:0)

在MVC3 RAzor中将类应用于@Html.EditorFor()的最佳方法是

@Html.EditorFor(x => x.Created)


<style type="text/css">

#Created
{
    background: #EEE linear-gradient(#EEE,#EEE);   
    border: 1px solid #adadad;
    width:90%;
    }
</style>

它会将以上样式添加到您的EditorFor()

适用于MVC3。