ASP.NET MVC:Razor中的自定义Html助手

时间:2010-11-18 15:52:08

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

与Razor一起使用时,我遇到了Html Helpers的困难。所述助手在MVC 2中与web表单视图引擎一起工作良好。但不是剃须刀。我在运行时得到的错误是:

Compiler Error Message: CS1502: The best overloaded method match for 'System.Web.WebPages.WebPageExecutingBase.Write(System.Web.WebPages.HelperResult)' has some invalid arguments

Source Error:


Line 1:  @using Wingspan.Web.Mvc;
Line 2:  @Html.IncrementalMenu(MenuBlock.Site)

展开显示详细的编译器输出显示:

d:\...\Views\Shared\MenuTop.cshtml(2,1): error CS1502: The best overloaded method match for 'System.Web.WebPages.WebPageExecutingBase.Write(System.Web.WebPages.HelperResult)' has some invalid arguments
d:\...\Views\Shared\MenuTop.cshtml(2,7): error CS1503: Argument 1: cannot convert from 'void' to 'System.Web.WebPages.HelperResult'

这向我表明剃刀不喜欢我的助手,IncrementalMenu,返回void(在MVC 2 web表单引擎视图中工作正常)。

我在编译时没有出现任何错误,尽管代码行(@ Html.IncrementalMenu(...))带有下划线的红色下划线:

Cannot implicitly convert type 'void' to 'object'

IncrementalMenu位于Wingspan.Web.Mvc名称空间中。它的签名如下:

public static void IncrementalMenu(this HtmlHelper html, MenuBlock menuBlock)
{
    // Uses an HtmlTextWriter to render a menu from the sitemap
}

如果我知道出了什么问题,我会被打击......

PS:

MenuBlock参数只是一个枚举,用于标识菜单应如何呈现。不要因为这很好而注意这一点。

3 个答案:

答案 0 :(得分:85)

你可以这样打电话给你的帮手:

@{ Html.IncrementalMenu(MenuBlock.Site); }

WebForms语法

<% Html.IncrementalMenu(MenuBlock.Site); %>

您只需调用您的方法,并忽略返回值(如果有)。

这样的代码需要返回值,并将返回值写入html流:

@Html.YourHelper()

Webforms语法:

<%: Html.YourHelper() %>

同样,如果结果值!= IHtmlString:

<%= Server.HtmlEncode(Html.YourHelper()) %>

答案 1 :(得分:49)

附录:

您可以使用@ Html.RenderPartial获得相同或类似的错误。在这种情况下,由于RenderPartial直接呈现给Response,因此不是字符串,需要在“Razor代码块”内编码:

@{
   Html.RenderPartial(...);
}

我怀疑这是微软在ASP.NET MVC中包含新Html.Partial的原因之一。由于Html.Partial确实返回一个字符串,所以可以写:

@Html.Partial

看起来好多了。鉴于Razor声明的目标之一是易于实现的,这很可能是正确的。

这也让我感觉更舒服。我知道返回一个字符串是什么,我一直这样做。但是“回到响应”每次我想都会需要更多的脑循环。

它符合最初微软在版本3中获得产品的古老格言.EG,Access 97.

这是令人沮丧的明喻。他们在版本4中搞砸了,即Access 2000 ......

答案 2 :(得分:22)

你的HTML助手应该返回代表html的MvcHtmlString,以便与Razor(以及其他不属于WebFormsViewEngine的视图引擎)一起正常工作

public static MvcHtmlString Label(this HtmlHelper html, string expression)
{
    return MvcHtmlString.Create("<label>" + expression + "</label>");
}