HTML5ify your ASP.NET MVC 3 applications

Tags: HTML, HTML5, ASP.NET, ASP.NET MVC, Visual Studio 2010

Some newly released tools for Visual Studio 2010 including Service Pack 1, the MVC 3 Tools update, and the Web Standards Update introduce the first wave of HTML5 support for ASP.NET development, so that means you can start taking advantage of HTML5's new features in your ASP.NET MVC applications today.

Where to get the new HTML5 goodies.

Service Pack 1

VS 2010 SP1 now allows you to set HTML5 support as a project-wide setting to include HTML5 validation. SP1 also provides some HTML5 Intellisense for elements and attributes. You can see the complete list of features, bug fixes, and enhancements at KB 983509.

MVC 3 Tools Update.

The MVC 3 Tools Update touts support for HTML5 semantic markup, updated jQuery scripts, and includes Modernizr scripts for HTML5 feature detection. You can download the MVC 3 Tools update, as well as view the complete set of documentation at the Tools Update download page.

Web Standards Update for Visual Studio 2010

Though not an official part of Visual Studio 2010, but instead found at the MSDN code gallery, the Web Standards Update adds a great deal of HTML5 element support. Since it's available for download as an extra, you can use it until more features rolled into Visual Studio officially, and get a head start on HTML5.

Validate HTML5 with Visual Studio 2010

After turning on HTML5 validation in Visual Studio, you can test your views to ensure HTML5 compliance. Choose the Tools | Options from the menu to open the VS options dialog then navigate to the Text Editor | HTML | Validation tab.

image

Setting HTML5 as the target for validation will help you create more robust, HTML5 sites easily, but you still need to stay up to date with the standards to do so.

Make Web Standards a staple in Visual Studio

Of course, since the HTML5 specification isn't complete, no IDE, browser, or any software can claim to support 100% of the HTML5 feature set (or related CSS/API/ECMA) at this time, but that doesn't mean that vendors can't start working on specific feature support now, and continue to do so as new the W3C working groups formalize the specs.

321712274

Below is a list of over 30 supported HTML5, CSS, and API features that are now part of Visual Studio via the Web Standards update.

HTML5

API

CSS3

Video & related tags
Audio & related tag
Semantic Markup
Drag & Drop support
Accessibility standard WAI-ARIA
Microdata
Schema.org & SEO
Geolocation
Web Storage
2D Transforms
3D Transforms
Animations
Background & Borders
Basic Box Model
Basic UI
Behavior
Color
Flexible Box Layout
Fonts
Hyperlink Presentation
Line
Lists
Marquee
Media Queries
Multi Column
Namespaces
Paged Media
Presentations Levels
Ruby
Selectors
Speech
Syntax
Template Layout
Text
Transition

HTML5 support in Visual Studio starts with new project templates that take advantage of HTML5 semantic markup.

MVC 3 goes semantic

The MVC 3 Tools Update shows off Visual Studio's semantic side by incorporating semantic markup right into the ASP.NET MVC project templates. When you start a new project in ASP.NET MVC 3, you'll notice a new checkbox asking if you would like to use HTML5 semantic elements.

SNAGHTML2dd9ebd

I'll have some semantic markup, please!

The option to use HTML5 semantic markup enhances the standard MVC project templates in the following ways:

  • Modifies the Layout Page to use semantic markup, i.e., <header>, <footer>, and other elements
  • Modifies CSS to style semantic markup

The code sample below is from the default layout page, _Layout.cshtml, which demonstrates the use of HTML5 semantic markup.

Of course, HTML support starts with the (finally!) easy to remember <!DOCTYPE> tag. The newly redefined <!DOCTYPE> element supports all HTML up to and including version 5, so you can use it in all your views without worry, regardless of which HTML elements they contain.

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8" />
    <title>@ViewBag.Title</title>
    <link href="@Url.Content("~/Content/Site.css")" rel="stylesheet"  type="text/css" />
    <script src="@Url.Content("~/Scripts/jquery-1.5.1.min.js")" type="text/javascript"></script>
    <script src="@Url.Content("~/Scripts/modernizr-1.7.min.js")" type="text/javascript"></script>
</script>
</head>
<body>
    <div class="page">
        <header>
            <div id="title">
                <h1>My MVC Application</h1>
            </div>
            <div id="logindisplay">
                @Html.Partial("_LogOnPartial")
            </div>
            <nav>
                <ul id="menu">
                    <li>@Html.ActionLink("Home", "Index", "Home")</li>
                    <li>@Html.ActionLink("About", "About", "Home")</li>
                </ul>
            </nav>
        </header>
        <section id="main">
            @RenderBody()
        </section>
        <footer>
        </footer>
    </div>
</body>
</html>

The <header>, <nav>, <footer>, and <section> elements replace the previous structural <div> elements of the page, as semantic markup in the page now defines the structure and page layout instead. You'll find new CSS styling for these semantic elements in the default CSS file for the project.

MVC 3 <3's CSS3

Visual Studio project templates now include styling for HTML5 semantic markup in the \Content\Site.css file. Both HTML5 and standard markup styling are present in the CSS file, to work nicely with pages that might still use <div> tags for page structure/layout. Specific CSS selector prefixes such as -moz and -webkit target all major browsers as well, making cross browser compatibility a cinch.

Below is a snippet from the Site.css file showing both semantic structure and styling as well as some new CSS features like the border-radius. The code at the bottom of the following sample also demonstrates cross browser CSS by using -moz and -webkit prefixes.

.page {
    width: 90%;
    margin-left: auto;
    margin-right: auto;
}
 
header, #header {
    position: relative;
    margin-bottom: 0px;
    color: #000;
    padding: 0;
}
 
header h1, #header h1 {
    font-weight: bold;
    padding: 5px 0;
    margin: 0;
    color: #fff;
    border: none;
    line-height: 2em;
    font-size: 32px !important;
    text-shadow: 1px 1px 2px #111;
}
 
#main {
    padding: 30px 30px 15px 30px;
    background-color: #fff;
    border-radius: 4px 0 0 0;
    -webkit-border-radius: 4px 0 0 0;
    -moz-border-radius: 4px 0 0 0;
}
 
footer, 
#footer {
    background-color: #fff;
    color: #999;
    padding: 10px 0;
    text-align: center;
    line-height: normal;
    margin: 0 0 30px 0;
    font-size: .9em;
    border-radius: 0 0 4px 4px;
    -webkit-border-radius: 0 0 4px 4px;
    -moz-border-radius: 0 0 4px 4px;
}

More modern MVC 3 development with Modernizr.

Modernizr is a JavaScript library that offers cross-browser HTML feature detection. Feature detection, rather than browser detection, gives you a more granular way to determine what abilities browsers have. Modernizr also helps your views gracefully degrade if a browser doesn't support a particular feature.

Since Modernizr is a JavaScript library, you'll find these versions of the library in the \Scripts folder of your MVC 3 project.

  • modernizr-1.7.js - Standard library for development
  • modernizr-1.7.min.js - Minimized library for production

You don't even need to reference the Modernizr library, as Visual Studio has done this for you in the project's _Layout.cshtml, as shown here.

<script src="@Url.Content("~/Scripts/modernizr-1.7.min.js")" type="text/javascript"></script>

However, the minified script file size is 10k, and you can trim it down by asking Modernizr to give you files that contain only the code for the features you want to detect at the Modernizr Downloads page. Using this tool, you can trim down the size to a few bytes of data, so it's a huge benefit for the performance of a production application.

Detecting features with Modernizr takes little programming effort:

if (Modernizr.canvas)
{ // code to use <canvas> element } 
else 
{ // code to use other elements } 

There's just no easier way to do feature detection! Just query the HTML5, CSS3, or other feature you're looking for by accessing it as a property on the Modernizr object. And that's it! Modernizr takes care of all the fuss with feature detection and has boiled it down to a simple if/else statement. If you're interested in the details of just how Modernizr does this, see the Modernizr docs.

Summary

There's no longer any excuse not to start working with these new HTML5 features! There's lots of new Visual Studio components as well as MSDN Gallery downloads that can help you HTML5ify your sites, today.

19 Comments

  • David Padbury said

    Nice work! Quick suggestion - you'll probably want to order those css properties with vendor prefixes the other way around. Ideally you want the std version "border-radius" below "-webkit-border-radius" so the browser will use the standard behaviour if it's supported. More info: http://css-tricks.com/7361-ordering-css3-properties/.

  • Brian said

    Is it possible to edit the default layout created for this. For example this:-


    <div id="title">
    <h1>My MVC Application</h1>
    </div>

    should really simply be:-

    <h1>My MVC Application</h1>

    Reduntant elements are not to my taste.

  • Panos said

    MVC3 brings the .Net platform to a whole new level. When working with HTML5, CSS3 and MVC3 it feels like a perfect match. With the additions of cool tools like modernizer and the web standards update, development is done smoothly and fast!

  • Rachel said

    Brian,

    That should be no problem removing <divs> - but check to make sure the layout will be the same or modify the CSS behind it.

    This post was pointing out how <div>'s are currently, frequently, used.

  • Brian said

    Thanks Rachel. My point was that if you wrap only one element in a div then that div is uneccessary and not semantic as you are introducing an element that has no semantic meaning other than to wrap the element.

    Wrapping a div around a h1 is the perfect example as you can omit the div and style the h1. The div is completely superfluous. My question about the template generated is simply because it would be nice not to have to edit it every time.

    Microsoft have an annoying tendancy to jump on bandwagons and not follow through. Generating a properly semantic template would be fulfilling the stated aim. Just as producing a table with thead/tbody etc. in mvc index views or not wrapping label/input pairings in forms with pointless divs would also be better suited to a more semantic outlook. A bare scaffold should be produced and the developer can add wrapping elements if needed not the other way round imo.

    Meh I'm just a commenter with an opinion on the interweb. At the end of the day I'll figure out how to make the generated layout suit me.

  • Rachel said

    Brian,

    I'll pass your comments along to the team. Yes, going purely semantic would be better as the default template.

  • Matt said

    Worth noting too, that you need to have Modernizr or some other shim library referenced if you're going to be using the new elements available in HTML5.

  • William Burgeson said

    I'm just downloading MVC 3 now, looks pretty awesome (as you say over the pond), one thing which concerns me about HTML5 is the lack of support for it in ... Microsoft Internet Explorer < 9. Therefore it wouldn't seem practical to have markup which uses these new tags, for sites which target the greatest number of users :(. Although there are js libraries out there which can convert IE < 9 to support HTML5, ideally a page should render without js.
    Is there a way to customise the razor views to specifically target browsers, in a similar way to how localisation works (home.cshtml, home.IE.cshtml) or something like that?

  • Rachel said

    William,

    If you target specific browsers the code will be much harder to maintain going forward.

    Use modernizr with yep/nope http://yepnopejs.com/
    So yes, using a JS lib is the way to go.

    Also, check out the docs/code at silk.codeplex.com. This is a project that demonstrates the use of exactly your scenario, weighing gracefully degrading vs progressive enhancement.

  • shawn z said

    Cutting and pasting that does not work in MVC3. To get the extension to work, I had to create a class file:
    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Web;
    using System.Web.Mvc;

    namespace incMvcSite.Classes {
    public static class HtmlPrefixScopeExtensions {
    public static IDisposable BeginHtmlFieldPrefixScope(this HtmlHelper html, string htmlFieldPrefix) {
    return new HtmlFieldPrefixScope(html.ViewData.TemplateInfo, htmlFieldPrefix);
    }

    private class HtmlFieldPrefixScope : IDisposable {
    private readonly TemplateInfo templateInfo;
    private readonly string previousHtmlFieldPrefix;

    public HtmlFieldPrefixScope(TemplateInfo templateInfo, string htmlFieldPrefix) {
    this.templateInfo = templateInfo;

    previousHtmlFieldPrefix = templateInfo.HtmlFieldPrefix;
    templateInfo.HtmlFieldPrefix = htmlFieldPrefix;
    }

    public void Dispose() {
    templateInfo.HtmlFieldPrefix = previousHtmlFieldPrefix;
    }
    }
    }
    }
    In the Razor (.cshtml) file, I added the following:
    @using incMvcSite.Classes
    @using(Html.BeginHtmlFieldPrefixScope("Permission")) {

    Permission

    // The Html.EditorFor's would go here...

    }
    Notice the using to bring me extension class into scope. That allows the second using line to work.
    Now the problem is that when posting back, the object is not updated. In my controller, I used a second parameter to specify my prefix:
    TryUpdateModel(modelUser.Permission, "Permission");
    This added the prefix to all field in the HTML, and the TryUpdateModel loaded the object with prefixed control names. Now you can properly namespace your controls for embedded edit lists, and for partial views of models with the same property names.

    Shawn Zernik
    Internetwork Consulting

  • Rachel said

    Shawn Z,
    the code here isn't meant to be copied and pasted, as it's just sample code to demonstrate how you can use HTML5 in Visual Studio - and it's nowhere near a complete sample, or I would have a download.

    Having said that, you don't need to go through the code that you have to get the basic functionality at work here (considering the same VS & environment)

  • Deepak said

    the code here isn't meant to be copied and pasted, as it's just sample code to demonstrate how you can use HTML5 in Visual Studio - and it's nowhere near a complete sample, or I would have a download.

Add a Comment