类的DisplayTemplate的默认输出

时间:2017-06-29 14:56:02

标签: asp.net-mvc display-templates

我们正在构建一个类库,为视图模型提供某些结构化类型,例如: InlineImage。

当与@ Html.DisplayFor(...)一起使用时,我需要能够为这样的实例定义默认的HTML输出,基本上......

  • 当/Views/DisplayTemplates/InlineImage.cshtml可用时,请使用该模板
  • 如果不可用,则应输出默认

然而......

  • 当我只覆盖该类的ToString()时,它会给我正确的输出,但它会得到HTML编码

我发现通过将[DisplayFormat(HtmlEncode = false)]添加到CLASS

来分析我能够禁用编码的MVC源代码

但是...属性不是以类为目标,所以我通过将它包装到我添加到类中的另一个属性来破解它。这很讨厌,但至少有效:)

我的代码目前看起来像这样:

[AttributeUsage(AttributeTargets.Class)]
class DisableHtmlEncodeAttribute : DisplayFormatAttribute
{
    public DisableHtmlEncodeAttribute()
    {
        HtmlEncode = false;
    }
}

[DisableHtmlEncode]
internal class InlineImage : IInlineImage
{
    public string AltText { get; set; }

    public string Src { get; set; }


    public override string ToString()
    {
        return $"<figure><img src=\"{Src}\" alt=\"{AltText}\"></figure>";
    }
}

它适用于默认显示,但在文件系统中提供显示模板时,不使用它。可能是因为一些东西因为数据注释而削减了它。

我已经尝试了其他类似的方法:

  • 将第一个属性与Html数据注释一起使用
  • 将display属性与Html数据注释一起使用
  • 实施IHtmlString

但框架似乎只检查类本身的元数据,但在这种情况下不检查其属性。而且IHtmlString完全被忽略了。

我正在寻找任何提示如何从类库中为给定类提供默认显示模板,只需将标准显示模板放置到视图文件夹即可覆盖。

1 个答案:

答案 0 :(得分:1)

事实证明,我比我想象的更接近,并且在最后一次试验中我使它发挥作用。

这个技巧类似于我对DisableHtmlEncode属性的处理,但是使用了UIHint属性。通过这种方式,您可以明显地告诉引擎将显示模板应用于类,并且它比Format属性更强。

以下是提供默认HTML标记功能的最终代码,当在FS中提供显示模板时,它使用该模板:

[AttributeUsage(AttributeTargets.Class)]
class DisableHtmlEncodeAttribute : DisplayFormatAttribute
{
    public DisableHtmlEncodeAttribute()
    {
        HtmlEncode = false;
    }
}

[AttributeUsage(AttributeTargets.Class)]
class UseDisplayTemplateAttribute : UIHintAttribute
{
    public UseDisplayTemplateAttribute(string uiHint)
        : base(uiHint)
    {
    }
}

[DisableHtmlEncode]
[UseDisplayTemplate("InlineImage")]
internal class InlineImage : IInlineImage
{
    public string AltText { get; set; }

    public string Src { get; set; }

    public override string ToString()
    {
        return $"<figure><img src=\"{Src}\" alt=\"{AltText}\"></figure>";
    }
}

我对黑客行为并不是特别自豪,但正如他们所说的那样,如果它起作用,那就太愚蠢了。

如果有人有更好的想法,请分享......