Problem
I have a very handy Html helper menu written for WebFormViewEngine views. This engine allows your helpers to return void and still be able to use:
@Html.Theseus
This is great for my helper because it can display a menu using HtmlTextWriter, which displays the output stream directly.
In Razor views, however, Html helpers are expected to return a value (usually MvcHtmlString) that is added to the output. Little difference, big consequence.
There is a way around this, as GvS pointed out to me (see ASP.NET MVC 2 on MVC 3: HTML Custom Helpers in a Razor ) as follows
If the helper returns void, do the following:
@{Html.Theseus;}
(Essentially, you just call the method, not visualize it in the form). A.
While still neat, this is not quite the same as @ Html.Theseus. So that...
My code is complex, but it works very well, so I can not go through the main changes, i.e. replace HtmlTextWriter with another author. The code snippet is as follows:
writer.AddAttribute(HtmlTextWriterAttribute.Href, n.Url);
writer.AddAttribute(HtmlTextWriterAttribute.Title, n.Description);
writer.RenderBeginTag(HtmlTextWriterTag.A);
writer.WriteEncodedText(n.Title);
writer.RenderEndTag();
if ((currentDepth < depth) || (depth < 0))
{
if (hasChildNodes)
{
writer.AddAttribute(HtmlTextWriterAttribute.Class, "Level" + currentDepth.ToString());
writer.RenderBeginTag(HtmlTextWriterTag.Ul);
BuildChildMenu(currentDepth + 1, depth, n, writer);
writer.RenderEndTag();
}
}
It would not be fun to write with TagBuilders. In its current form, it displays any menu, including Incremental Navigation, as described in 4guysfromrolla:
Implementing Incremental Navigation Using ASP.NET
Parameters:
I think I could return an empty MvcHtmlString, but this is pretty much a hack definition ...
- TagBuilder , StringBuilder, .., StringBuilder MvcHtmlString. , - ...
:
:
HtmlTextWriter StringBuilder, , MvcHtmlString ( HtmlString)?
, ...
PS:
HtmlTextWriter , , , TagBuilder.