简体   繁体   English

用于字段的ASP.NET MVC内联帮助器

[英]ASP.NET MVC inline helper for fields

I need a generic inline helper to show fields. 我需要一个通用的内联帮助器来显示字段。

Here is what I have currently: 这是我目前的情况:

@helper DisplayField(Func<MyModel, string> field)
{
    if (string.IsNullOrWhiteSpace(field(Model)) == false)
    {
        <div class="row"> @field(Model) </div>     
    }
}

Usage: 用法:

@DisplayField(m => m.Name)
@DisplayField(m => m.PhoneNumber)

I have no idea how to show Label(DisplayAttribute) inside of a helper. 我不知道如何在帮助器中显示Label(DisplayAttribute)。 Please help. 请帮忙。

At the top of your page, add in a using for System.Linq.Expressions, eg. 在页面顶部,添加for for System.Linq.Expressions,例如。

@using System.Linq.Expressions

(or add this namespace in web.config). (或在web.config中添加此命名空间)。

Then to create the helper, it would look something like: 然后创建帮助器,它看起来像:

@helper DisplayField(Expression<Func<MyModel, string>> field)
{
    @Html.LabelFor(field)
    @Html.DisplayFor(field)
}

You can add extra logic in there to check for empty value etc. You may be better off creating an HtmlHelper though, that way you can use generic type arguments rather than "MyModel" and "string" as above. 你可以在那里添加额外的逻辑来检查空值等。你可能最好创建一个HtmlHelper,这样你可以使用泛型类型参数而不是上面的“MyModel”和“string”。 When I last tried it was not possible to add generic type arguments to an inline helper, eg. 当我上次尝试时,无法将内联类型参数添加到内联帮助程序,例如。 the following is not possible, unless this feature has since been added: 以下是不可能的,除非这个功能已经添加:

@helper DisplayField<TModel, TValue>(Expression<Func<TModel, TValue>> field)
{
    @Html.LabelFor(field)
    @Html.DisplayFor(field)
}

So, to get the generic method, you would use a custom HtmlHelper. 因此,要获得泛型方法,您将使用自定义HtmlHelper。 To do this: 去做这个:

  1. Create a file like the following: 创建如下文件:

     using System; using System.Linq; using System.Linq.Expressions; using System.Web; using System.Web.Mvc; using System.Web.Mvc.Html; namespace MvcApplication1.HtmlHelpers { public static class HtmlHelpers { public static MvcHtmlString DisplayFieldFor<TModel, TValue>( this HtmlHelper<TModel> helper, Expression<Func<TModel, TValue>> field) { var labelString = helper.LabelFor(field); var displayString = helper.DisplayFor(field); return MvcHtmlString.Create( labelString.ToString() + displayString.ToString()); } } } 
  2. In your page, the usage of such a thing would be: 在您的页面中,这样的事情的用法将是:

     @Html.DisplayFieldFor(m => m.Name) @Html.DisplayFieldFor(m => m.PhoneNumber) 

etc. You may need to check your usings on your page or add the namespace for the HtmlHelper into web.config. 您可能需要检查页面上的使用情况或将HtmlHelper的名称空间添加到web.config中。

@David_001 provided a very elegant MVC-solution for this; @ David_001为此提供了一个非常优雅的MVC解决方案; I leave my answer here as it describes the inner mechanism and might be helpful if you need to solve a problem that is not covered by the MVC out of the box helpers. 我在这里留下我的答案,因为它描述了内部机制,如果您需要解决MVC开箱即用助手未涵盖的问题,可能会有所帮助。

Change the parameter type from Func<MyModel, string> to Expression<Func<MyModel, string>> . 将参数类型从Func<MyModel, string>更改为Expression<Func<MyModel, string>> This way, you receive a dynamic expression in the method that you can analyze instead of the static delegate you receive in the current form. 这样,您可以在方法中接收动态表达式,而不是在当前表单中收到的静态委托。
You can retrieve the value of the field like this: 您可以像这样检索字段的值:

var compExpr = field.Compile();
var value = compExpr.DynamicInvoke(Model);

You can access the member and its attributes that is returned by the dynamic expression like this: 您可以访问动态表达式返回的成员及其属性,如下所示:

var memberAccExpr = (System.Linq.Expressions.MemberAccessExpression)field.Body;
var attr = (DisplayAttribute)memberAccExpr.Member.GetCustomAttributes(typeof(DisplayAttribute), false).FirstOrDefault();

I tested it roughly in a C# project (not MVC), so I can't say whether it works in Razor; 我在C#项目(不是MVC)中大致测试过,所以我不能说它是否在Razor中有效; but I'm sure you can also move your code to a normal class. 但我相信你也可以把你的代码转移到正常的类。
Please note that you loose some type safety with this approach as a caller can provide a variety of dynamic expressions to the method. 请注意,使用此方法可以避免某种类型的安全性,因为调用者可以为该方法提供各种动态表达式。 So you should take this into account if you analyze the expression in order to find the attribute. 因此,如果分析表达式以便查找属性,则应考虑到这一点。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM