Elton Stoneman

  Home  |   Contact  |   Syndication    |   Login
  120 Posts | 0 Stories | 3601 Comments | 0 Trackbacks

News

Archives

Post Categories

[Source: http://geekswithblogs.net/EltonStoneman]

Keeping up the fluent work, I've put together a fluent interface which wraps the framework HtmlTextWriter. For ASP.NET MVC, this makes generating HTML in extension methods to HtmlHelper safer than string.Format() and more readable than HtmlTextWriter:

public static string Image(this HtmlHelper helper, string imageRelativeUrl, string altText)

{

return FluentHtmlTextWriter.Begin()

.WriteTag(HtmlTextWriterTag.Img)

.WithAttribute(HtmlTextWriterAttribute.Src, GetImageUrl(imageRelativeUrl))

.WithAttribute(HtmlTextWriterAttribute.Alt, altText)

.End();

}

The equivalent using HtmlTextWriter is:

public static string Image(this HtmlHelper helper, string imageRelativeUrl, string altText)

{

StringBuilder htmlBuilder = new StringBuilder();

HtmlTextWriter writer = new HtmlTextWriter(new StringWriter(htmlBuilder));

 

writer.AddAttribute(HtmlTextWriterAttribute.Src, GetImageUrl(imageRelativeUrl));

writer.AddAttribute(HtmlTextWriterAttribute.Alt, altText);

writer.RenderBeginTag(HtmlTextWriterTag.Img);

writer.RenderEndTag();

writer.Flush();

 

return htmlBuilder.ToString();

}

Unlike the framework writer, you're not constrained to specify attributes in any particular order, and tags which aren't nested can be written with a single WriteTag(), rather than BeginTag() and EndTag() calls. The writer copes with multi-level tag hierarchies - this sample builds a Superfish CSS menu:

FluentHtmlTextWriter writer = FluentHtmlTextWriter.Begin();

 

writer.BeginTag(HtmlTextWriterTag.Ul)

.WithAttribute(HtmlTextWriterAttribute.Id, "menu.Name")

.WithAttribute(HtmlTextWriterAttribute.Class, "sf-menu sf-vertical");

.BeginTag(HtmlTextWriterTag.Li)

.BeginTag(HtmlTextWriterTag.A)

.WithAttribute(HtmlTextWriterAttribute.Class, "sf-with-ul")

.WithAttribute(HtmlTextWriterAttribute.Href, "#")

.WithValue("Link 1")

.WriteTag(HtmlTextWriterTag.Span)

.WithAttribute(HtmlTextWriterAttribute.Class, "sf-sub-indicator")

.WithValue("»")

.EndTag()

.EndTag()

.EndTag();

 

string html = writer.End();

Assert.AreEqual("<ul id=\"menu.Name\" class=\"sf-menu sf-vertical\">\r\n\t<li><a class=\"sf-with-ul\" href=\"#\">Link 1<span class=\"sf-sub-indicator\">&#187;</span></a></li>\r\n</ul>",

html);

The HtmlTextWriter equivalent is unthinkable.

Patrik Hägne has an alternative fluent HtmlTextWriter implementation, which is nicely put together, but I wanted slightly different functionality. Firstly I wanted to get the HTML string from the writer directly, without needing to instantiate a StringBuilder and StringWriter. Secondly I wanted minimal new code – Patrik uses a separate class to manage writing attributes, and has specific functions for known tag types. Thirdly, I didn't really like Patrik's syntax, with the need to specify the tag type when you write an end tag – and when tags aren't nested, I wanted to write them in a single unit:

string html = FluentHtmlTextWriter.Begin()

.WriteTag(HtmlTextWriterTag.Span)

.WithAttribute(HtmlTextWriterAttribute.Id, "id_span")

.WithValue("contents_span")

.End();

Assert.AreEqual("<span id=\"id_span\">contents_span</span>", html);

My version is on MSDN Code Gallery here: FluentHtmlTextWriter. It works by building up a list of actions when you start writing a tag, and flushing them in the correct order to an internal HtmlTextWriter when you start writing the next tag. When you call End() it flushes the internal writer and outputs its contents. An alternative constructor lets you write directly to an output stream, in which case you can Flush() the writer and don't need to call End().

The current implementation only deals with basic tag, attribute and style functionality, and doesn't include optional HTML encoding overloads. It's only 75 lines of code, and extending it should be trivial.

There is a negligible performance hit in using FluentHtmlTextWriter – running the image tag generation code above 20,000 times on my dev machine, the fluent version takes between 0.01and 0.02 seconds longer than the framework version (on average 0.07 seconds compared to 0.05).

  • Share This Post:
  • Share on Twitter
  • Share on Facebook
  • Share on Technorati
posted on Thursday, September 10, 2009 7:32 PM

Feedback

# re: FluentHtmlTextWriter 4/14/2010 8:58 PM Nick Harrison
This looks very interesting. I have downloaded the source and am anxious to pour over it. Thanks for posting.

# re: FluentHtmlTextWriter 6/11/2010 6:06 AM scrapbook pages56
Really its one of the fabulous post and I just like to say you,its very informative blog which I like a lot.Thanks a lot.

# re: FluentHtmlTextWriter 8/30/2010 5:46 AM USANA_478
Hey I just got through with the pages, I should say Pretty nice work done there.Thanks for sharing your ideas!!I really appreciate it!Keep blogging.

# re: FluentHtmlTextWriter 10/8/2010 8:26 AM pain management
Having written articles that require this much work.I am very happy with your post. Some things in here I have not thought about before.Thanks for the share!Waiting for your next upcoming post.

# re: FluentHtmlTextWriter 10/25/2010 3:21 PM firewall rule audit
The latest release of MvcContrib predates FluentHtml, so it’s not in any binary download. You must get the source and build it. There is a file “ClickToBuild.bat” in the trunk which puts the binaries in the “build” folder.

# re: FluentHtmlTextWriter 11/1/2010 7:28 PM Usana Vitamins
Good information - I found it helpful

# re: FluentHtmlTextWriter 11/11/2010 4:57 AM Christian Woman
I really enjoy participating in this community and see which other people in your industry are getting Shoutouts.

# re: FluentHtmlTextWriter 12/14/2010 12:53 AM compare exchange rates
thanks mate. look forward to more of the same.

# re: FluentHtmlTextWriter 12/14/2010 12:54 AM ufo videos
really? I didn't realise it was so simple!

# re: FluentHtmlTextWriter 5/13/2011 11:41 PM free home phone service
thanks for this

# re: FluentHtmlTextWriter 5/13/2011 11:43 PM Weekly options
great information

# re: FluentHtmlTextWriter 6/5/2011 12:32 AM Londons Escorts
Incredible article :-) London Indian escorts

Post A Comment
Title:
Name:
Email:
Website:
Comment:
Verification: