Category Archives: Web Dev

PHP/Ruby on Azure World Tour

I’m thrilled and honored to be doing another speaking tour through Europe. I’m getting to visit a number of countries that I haven’t visited before and some old favorites. I’ll be speaking on PHP, Ruby and other non .NET technologies on Azure.

The talk that I’m going to be doing in most places is PHP/Ruby on Azure or Leveraging Azure with Non-Microsoft Languages:

Windows Azure is Microsoft’s Cloud Computing offering. It is more than a simple scalable hosting option as it is truly a platform as a service offering. This allows you to focus on your application rather than the configuring and managing your infrastructure whether you are writing C# or VB.NET or even languages such as PHP or Ruby which are first class citizens in Windows Azure. The Windows Azure Platform includes Windows Azure, which is the OS and hosting environment for web and background services, as well as non-relational storage, queues, and a blob storage for everything from videos to mountable virtual drives. Additionally, the Windows Azure Platform includes SQL Azure, a fully relational database as a service, and Windows Azure AppFabric for industry standards compliant identity management and a service bus for message passing.

But there remain the questions around why, when and how you should move to the cloud, especially if you are using PHP or Ruby. Should I put everything in Windows Azure? Do you have to convert everything you have to ASP.NET? Do you have to write code specifically for Windows Azure? What if my current applications depend on MySQL and/or memcached?

There’s a lot of good news here as it is relatively straight forward to get running in Windows Azure. Once your application is running, however, now you need to look at how to fully leverage the platform offerings architecting for the best usage of the different roles and the various aspects of the Windows Azure offerings such as the AppFabric and SQL Azure. This will help your application make the most efficient usage of CPU, bandwidth, storage and all of the things that cost in a cloud hosting scenario.

In this half day session, we will begin with the why of Windows Azure talking about when it makes sense to make a move and what the prudent migration paths are for your organization.  During this time we will tour the various aspects of Windows Azure. Then we’ll delve into the technical aspects of how to run your PHP/Ruby code on Windows Azure. Once we have that mastered, we will move onto leveraging the Windows Azure platform to its fullest.

The full schedule is as follows (and yes, this is a lot of countries in not very many days)

Feb. 21 – Dublin Ireland –

I love Ireland. I hope to someday live there. I spoke there about a year and a half ago on RIA and got to meet a few of the folk but mostly worked with Martha Rotter. I got to make a number of friends last time and I’m really looking forward to seeing them again.  

Feb 23 – Lisbon, Portugal – 

This is my first time to Portugal. I’m really looking forward to meeting the local DPE team (Luis Alves Martins and Sergio Martinho). I’m speaking at the university. it looks like a beautiful venue – I just wish that I had more time here to explore the local culture.

Feb 24 – Vienna, Austria – 

My brother has spent a lot of time in Austria but I’ve never been. I have met Mario Szpuszta back when he and I both spoke at JAOO in 2008 in Denmark. That was an awesome conference. I’ll also get to met Rolf Mistelbacher. Another thing I’m really excited about is that I’m going to spend enough time to actually see some of the city.

Feb 26 – London, UK – Keynoting PHPUK –

At PHP UK, I’m actually not talking about Azure. Rather I’m doing a keynote titled The Lost Art of Simplicity (Full slides on slideshare). This is actually the original reason that I’m coming to Europe in the first place. I’m honored to be asked to do the keynote and am beholden to Scott MacVicar for the invitation and to Johanna Cherry for making everything work smoothly.

March 2 – Stockholm, Sweden –

Check out this awesome venue – – it’s a 17th century building in downtown Stockholm. Really looking forward to hanging out in this space.

March 3 – Oslo, Norway – registration information coming soon

I’ve never been to Norway. I should have more information about this trip in the next day or so and I’ll update this post.


I’ve got all of the registration information for my Oslo stop.

Auditorium (ground floor)

Lysaker Torg 45

Lysaker Akershus 1366

Norge for all of the registration information.

Also, as a side note I’ve met a bunch of people from Norway while at the PHPUK conference and they’ve assured me that the polar plunge was decent training for my visit but I’d enjoy it regardless.

March 4 – Amsterdam, The Netherlands – PHP User Group

I haven’t actually met Bram Veenhof in person but  have been working with him over the past couple of years on a couple of things.I’ve been to Amsterdam several times but mostly just to the Airport and the Microsoft offices there, both of which are awesome. I’m thrilled this time to actually have a little time to explore the city.

March 5 – Brussels, Belgium –

I’ve been to Brussels once before and I’m really looking forward to going back. I’ve not get Katrien De Graeve and Rudy Van Hoe but are two of the other people that I’ve been working with closely over the past couple of years.

March 6,7 – Kilkenny, Ireland – hanging out and speaking at Wordcamp Ireland

Again, I love Ireland and hope to live there someday. I’ll be in Kilkenny at Wordcamp Ireland.

It’s going to be a lot of fun and I’m really hoping that there’s lots of good conversation. Please let me know via comments or via twitter if you’re able to make it to one of the sessions.

If you tweet about this – please use the hash tag #phpazuretour and #cityyourecomingto!

Above the Fold and how It Really Should be Used

Chicago 080I’ve come to realize that many web designers don’t understand what “Above the Fold” and how it really should be used. Above the Fold is an old print newspaper layout term for what’s on the top part of the page, the part that is displayed in the window at the newspaper stand. In web design, the term is used for the bits that the user can see without having to scroll. I’ve talked and ranted about this before as It’s point number 23 in 32 ways to keep your blog from sucking

<update>It was brought to my attention that it’s often not a web designer but rather an Information Architect or a Developer who is updating the layout on the page. Completely agreed and this is yet another reason that you should look for competent web designers for the layout and design of your page.</update>

What’s bringing it up now is that CX Partners recently blogged about The myth of the page fold: evidence from user testing | cxpartners and it concerned me a little. CX Partners does a lot of user testing and one of the things that they have tested for is whether or not the “Fold” mattered to users and out of 800 users, only 3 were unable to find content because they would have to scroll to find it. They are right, users are used to scrolling and are willing to do so if they know that there’s more content below. We just need to give them visual hints that there is more content that they will have to scroll to see. What they are trying to fight is the urge to put all of the content or at least all of the *important* content Above the Fold and design pages so that users do have to scroll. I’m on board with that fight. Cramming all of the content into cramped margins and smashing things together just so that it can be seen without scrolling is horrible design.

Here’s the part that concerns me as an old school print layout guy. There’s a fundamental miss on what the “Above the Fold” content is supposed to be used for in your layout whether it’s print or web design.

How does print layout treat above the fold?

The above the fold content is not meant to be the meat of the content or really even the most important content. It’s meant to be eye catching. It’s the lure for people to pick up the paper or magazine.

100th Anniversary of the Seattle P-I NewspaperWhen thinking about the fold in a newspaper, think about the old school newspaper dispenser with the top half of the top page displayed in the little window. There is a deliberate attempt to put a catchy photo and headline in that window so people buy the paper. Is that the best thing in the paper, not even close. That’s the picture that’s going to look good on someone’s coffee table when they toss down the newspaper.

New York 1st day. magazine standsOr better, think about the magazine stand and how there are potentially hundreds of magazines there and you need for yours to stand out enough that people will buy it. Think this through – what can they see in the magazine stand? Typically they can see the top edge of the magazine and part of the picture. I was amazed once when I was talking to a freelance sports photographer who told me that he’d net $40k-$60k for one photo if he could land the cover picture on Sports Illustrated. But it makes a ton of sense. This concept of trying to stand out on just a headline and a photo is not lost on the smart people at Sports Illustrated. The right picture could make far more than $40k worth of a difference on the stand.

How does this apply to web design?

Honestly, it’s the same exact concept. The fold or scroll line is the area of the page that people can see without having to scroll down the page. This area needs to catch people’s attention correctly because they may only be on your page for a few seconds. If you look at the statistics on any site that gets a decent amount of traffic and the average page view length is measured in seconds, not minutes.

When people are browsing through and they get a link from another site or from a search engine, what’s the first thing that they see? Imagine that as if they are glancing past your page among the potentially hundreds of others that they are looking past which is really not that much of a stretch because they are looking to see which pages are more likely to fit their needs than others. They may not be paying for your content but they are investing their time.

The problems come in two sizes. First, there are designs that try to shove as much content as they can into that above the fold area because there’s an assumption that if it’s not there, their users won’t see it. Second, there are other designs that completely shun the idea of scrolling and end up with these horrid wizard style pages where the user has to click through to see the next page and the next page and so on. Either of these are poor choices.

Back to the article for a moment – I really liked CX Partners’s “Design tips to encourage scrolling”. What was missing is the “How to hook them and keep them” bit.

Let’s look at Jeff Blankenburg’s blog for a good reference here.


You know exactly what you are going to get on his page. The disk in the middle, which is what most people see first cycles through all of the social networks that he frequents. The tweets across the top express his last several publically blasted thoughts while the little bird that flies around them draws eyeballs to them. The menu shows you that he’s delivering Code and Slides through this blog in addition to other posts. The RSS tag that hangs down and swings a little definitely captures the attention and draws people to subscribe. Finally, the title of the blog and the first blog post start drawing eyes down the page to see the meat of the content. But what real content is above the fold on Jeff’s blog? Honestly, there’s none. All of the real content is below the fold so the user has to scroll for it. Going back to the CX Partners post, that’s fine. Users know how to and are willing to scroll for content if they find the page interesting. The *only* thing that I dislike about his header is that it’s a fairly large chunk that takes 3-5 seconds to load the first time. This is a killer if the use
r is only on the page for 3 seconds.

Another great example is any Amazon product page. They have the picture of the product, average user rating and price right at the top. The product detail, related products, the actual reviews and all of the rest of the content is below the scroll line. Obviously, it’s successful for them.

Wrapping up…

Above the Fold is widely miss-understood. You need to realize that this critical section of the page is not about shoving as much content as you can the user. It’s about effectively giving the “Elevator” pitch on your site and getting that longer look that will likely involve scrolling down to see the real content.

Guard the above the fold content and keep it to the essential bits that will tell the user what your site is about rather than trying to give them everything in one big drink from the fire hose. Whenever anyone talks to you about moving a certain section of content above the fold, turn the question on them by asking them how that keeps people on the site over all.

Announcing the WebsiteSpark Program

image Building on the success of the DreamSpark and BizSpark program that we launched about 11 months ago Microsoft is now launching the WebsiteSpark program.

WebsiteSpark is designed for small web consultancies ranging in size from 1 to 10 people. With WebsiteSpark, you get a package of software specifically selected for a web consultancy to serve their customers better.

What does the program provide?

WebSiteSpark provides software licenses that you can use for three years at no cost.  Once enrolled, you can download and immediately use the following software from Microsoft:

  • 3 licenses of Visual Studio 2008 Professional Edition
  • 1 license of Expression Studio 3 (which includes Expression Blend, Sketchflow, and Web)
  • 2 licenses of Expression Web 3
  • 4 processor licenses of Windows Web Server 2008 R2
  • 4 processor licenses of SQL Server 2008 Web Edition
  • DotNetPanel control panel (enabling easy remote/hosted management of your servers)

The Windows Server and SQL Server licenses are for you to do both development and production work. Also, the production licenses can be leveraged in a couple of different ways. You can do 1 production server with 4 processors or 4 servers with 1 processor each. These servers can also be either dedicated hardware or virtualized offerings. If you want, you can throw the licenses on your own server with the “self-hosted” model or you can enroll with one of the hosters that have signed up as a Network Partner. As a Network Partner, they will pass the savings of the licenses on to you and only charge you for the infrastructure work. You can find all of the hosting network partners on the WebsiteSpark page.

But this program is not just about software. As part of the WebsiteSpark, the people that enroll are entered into the Microsoft Partner Program and into Microsoft Pinpoint. This will help result in customer referrals and more. There’s also 2 Microsoft professional support incidents per year and some free online training that will be provided. 

Who’s eligible for BizSpark?

WebSiteSpark is available to independent web developers and small web development companies.  The only two requirements to join the program are:

  1. Your company builds web sites and web application on behalf of others.
  2. Your company currently has less than 10 employees.

If you qualify and want to get signed up today, there are a couple of different paths.

You can always visit WebsiteSpark and sign up directly. During the enrollment, you can pick a network partner or you can pick one of your friends at Microsoft such as me as your contact to enroll and sign you up.

Or you can send mail to you can get a referral code quickly.  You can then use that code to enroll in the program on the WebsiteSpark website.  Once enrolled you can immediately download and use the software, as well as begin to participate in the network/partner opportunities.

If you run into any issues at all, email me at and I’ll help you out.

Some quick Q&A
  • What happens after the 3 years?

There is a $100 exit fee when you leave the program whether you leave at the end of 1 year or you leverage all three years. However, there’s no obligation to continue using any/all of the software once you exit the program. If you so wish, you can pay the $100 exit fee and wash your hands of the whole deal. Obviously, the play here is that at the end of the three years you will find our platform and tools valuable enough to purchase.

That said, there are some interesting incentives that are being put in place right now to help you with that decision. WebsiteSpark participants can optionally choose to purchase all of the software in the WebsiteSpark program via a $999/year package. And yes, that includes all of the software involved from the tools to the production licenses.  

Or you can just leverage the production licenses through a stellar $199 a year offer that includes both 1 Windows Web Server processor license and 1 SQL Server Web edition processor license.  You can buy the quantity you need of this package at $199/year each. 

  • What’s the role of the Network Partner?

Similar to the BizSpark program, the Network Partners are selected because they are active in supporting the ecosystem that the program is intended for. In the case of hosters it’s obvious. They host the websites that WebsiteSpark participants are building. There are others who work with the community in advisory roles and want to help out as mentors and coaches.

Couple of examples:

Cal Evans is another example of a great network partner as he’s working with PHP shops all over the world and helping them to be successful again as a mentor and as a coach. As a network partner, he is adding one more offering into the portfolio to help his mentees be successful.

Steve Smith from Nimble Pros who wanted to be involved as a network partner because he’s active in working with other consults to help them be successful through support, advice, mentoring and sometimes sub-contracting. He’s proven this by being a Microsoft Regional Director and an MVP for many years. His role as a network partner in the program only furthers that goal of helping the ecosystem.

Ben Henderson from Firefly Logic, Harper Reed from Threadless and John Alexander and Jeff Julian from Geeks With Blogs hold similar positions in the community as influential bloggers, coaches, mentors and advisors to many companies.


I’m really excited about WebsiteSpark because I remember when I was an independent consultant and then a partner at SRT Solutions getting our first dedicated server. It was a great feeling to have the freedom to do whatever we needed to do with the server from installing different types of software to configuring the redirects the way we wanted.

For more details – read Scott Guthrie’s blog post at Announcing the WebsiteSpark
Program – ScottGu’s Blog

Again, if you want to get involved, feel free to contact me at Either I can sign you up directly or get you in touch with the right network partner to help you in your situation.

Interesting Web Development Related Resources

Like so many thing that we do in our daily development, there’s a high probability that someone has already solved the problem if you know where to look. This is just a collection of resources that I’ve found useful over time. Honestly, I’m posting these here because I need them in one place so that I can find them easily…

JavaScript Resources

Like a lot of you, I’ve been doing JavaScript since 1996. I’ve been pretty geeked, however, with the recent (well, last 2-4 years) emergence of a ton of JavaScript frameworks that are making this work a lot easier.

imageThe first one to talk about it dojo. It’s one of the more mature ones that’s out there. I’ll be honest and say that it’s been a little while since I’ve used it because I’ve started using jQuery or Prototype more often. That said, dojo is one of the most complete frameworks out there. I do love it’s drag and drop support. It includes offline support and a whole lot more. Check out and play with some of it’s cool features at

Of course, any group that has a conference called is a winner in my book.

imageThe second toolkit is MochiKit. I love it’s tag line of “Making JavaScript Suck Less”. I first worked with MochiKit when I was playing around with TurboGears – a Python web application stack. What it’s really outstanding at is doing async work which is particularly useful in doing AJAX and other service based work. It’s interesting to note that Kevin Dangoor started Turbo Gears and then at some point later ended up working for SitePen who paid him to work on dojo. Check out demos of it in action at


Prototype is a slick relatively low level framework. What it does is extend the HTML DOM to include a lot of really useful features like element, class and css selectors. One of the useful things that it does is add a number of manipulations to the built in string class. This gives us startsWith, stripScripts, stripTags, isJSON, strip and a whole lot of other really useful functions.image By itself, Prototype’s useful but I have a hard time talking about it without mentioning and some of the other plugins. brings drag and drop support, animation frameworks a number of controls and makes it all really easy.

Check out demos of Prototype and working together at

imagejQuery is a fantastic and relatively light-weight framework that’s garnering a lot of new supporters recently. Honestly, I was happy with dojo and Prototype until I saw the Visual Studio Support for jQuery at which point I started playing with it.

I’m a convert. 🙂 Now, because it’s not as low level as Prototype, jQuery doesn’t have some things like the string manipulation, but overall I’m really pleased. I find that I have to write a lot less code to accomplish the same results. And very importantly, the jQuery Documentation is really good. Another really useful thing is that jQuery, being a really nice citizen, has built in support to make sure that it’s compatible with other JavaScript frameworks. Throw all of that in with intellisense in Visual Studio and it makes life easy.

There are also a ton of different plugins for jQuery that do everything from menus to rude string manipulation (not as good as Prototype but it’s a start).

Some of my favorite jQuery plugins in no particular order are:

AJAX History
Curvy Corners

image  ASP.NET AJAX is the last framework I’m going to talk about here not because there aren’t other frameworks but I haven’t used the others so I don’t really want to comment on them.

First, as the name does imply, what it does really well is AJAX stuff. One of the really powerful features is the JavaScript proxy generation.

<asp:ScriptManager ID="ScriptManager1" runat="server">
           <asp:ServiceReference Path="~/CustomersService.asmx" />

That allows you to call web services as if they were methods on an object.

function GetCustomerByCountry()
      var country = $get("txtCountry").value;
      InterfaceTraining.CustomersService.GetCustomersByCountry(country, OnWSRequestComplete);

function OnWSRequestComplete(results)
      if (results != null)

Second, despite the name, ASP.NET AJAX can work with more than just ASP.NET. There’s a project on CodePlex to generate the service proxies for PHP called PHP MS AJAX (which is a whole lot of capital letters…).

How do you choose?

There are a ton of different tests out there some of which you can look at the results, others of which you can actually run yourself…

Dojo vs JQuery vs MooTools vs Prototype Performance Comparison | Peter Velichkov’s Blog – Jan 19, 2009

Mootools Slickspeed Test

I like to see if there’s broad support so the project won’t go away, see if it’s actively being developed, what tooling is available, how easy the syntax is, how well it plays with others, what it brings to the table from a functionality standpoint and a whole lot more.

Really though, it comes down to your preferences. The good news is that it’s not the end of the world if you decide to switch frameworks.

My current JavaScript work is being done with a combination of jQuery for most of my client side work with ASP.NET AJAX doing my communications (and some of the controls) with a little bit of Prototype thrown in when I need to go lower level.

CSS Resources

I used to spend days getting exactly the right alignment in my HTML/CSS work. But as time has gone on, I’ve gotten more mature and realized that I don’t have to work that hard. Instead of me figuring out how to do the exact right layout should be, I’m starting to leverage the various CSS Frameworks that are out there – especially since there are so many new browsers and form factors out there from IE8 to Safari 4 to iPhone. I want a framework to

imageOne really simple CSS Framework is the 960 Grid System. It’s simple and gives you a lot of flexibility. The idea is that it breaks up the page into either 12 or 16 different columns and then lets you put in areas that spread across any number of those columns. This is a direct nod to the print industry which does exactly the same thing on paper. This gives you a tremendous number of possibilities from a simple two column layout to a really complicated layouts with multiple width columns and variety. Check it out, it’s simple and it works.

image  The downside of it is that it’s a fixed width layout so it’s not always the right choice. The good news, however, is that the project has been extended by Fluid 960 Grid System. imageThis adds JavaScript to the 960 Grid System to give is a much more dynamic layout that resized to your screen size. It also brings dynamic menus to the table. It’s JavaScript it based off of a project called MooTools

imageIf the you really don’t want to think that hard and the others don’t give you what you need tied up in a neat enough package, check out It’s simple to use web site gives you a preview of exactly the layout that you’re looking for and lets you download a zip file with a sample HTML and CSS inside.

imageAnd if that’s not enough and you really just need the design and all of the layout handed to you – check out It’s got a large number of Creative Commons licensed CSS templates and layouts.


I hope these resources are as useful to you as they are to me. I’ve banged my head against the wall a ton of times until I realized that someone else had already solved the problem and I can leverage their solution.

Adding Paging to the Simple Photo Gallery

Turn the pageOver my last handful of posts, Building a Simple Photo Gallery in ASP.NET MVC Framework, Returning Thumbnails With the MVC Framework and Adding Lighbox.js to the Simple Photo Gallery I’ve built a simple photo gallery on the ASP.NET MVC framework.

In this post, we’re going to continue that project by adding paging rather than showing all of the pictures on the one page.

Adding Paging to the Model with LINQ

Since we are simply using an XML file for the storage, we need to do the paging manually against our set of objects that we have in memory. This method works well any time you have client side caching as well.

public class ImageModel : List<Image>
    public ImageModel() : this(1, 10)

    private List<Image> GetAllImages()
        string imagesDir = HttpContext.Current.Server.MapPath("~/images/");
        XDocument imageMetaData = XDocument.Load(imagesDir + @"/ImageMetaData.xml");
        var images = from image in imageMetaData.Descendants("image")
                     select new Image(image.Element("filename").Value,
        TotalCount = images.Count<Image>();

        return images.ToList<Image>();

    public int TotalCount { get; set; }
    public int CurrentPage { get; set; }
    public int PageSize { get; set; }
    public ImageModel(int pageNum, int pageSize)
        CurrentPage = pageNum;
        PageSize = pageSize;

        var images = GetAllImages();

        this.AddRange(images.Skip((pageNum - 1) * 

Notice that I added a new constructor that takes as parameters page number and page size. This will allow us, from the controller, to control the action happening here. The next thing to notice is that the default constructor is now calling the new constructor passing in default parameters of 1 and 10. Notice that we’re starting with 1 instead of 0. This will make a ton more sense to the user and makes mapping the pages a lot simpler. Lastly, notice that we’re setting some parameters (TotalCount, CurrentPage and PageSize). We’ll use these in the view in a little bit.

If we run right now, we’ll only get the first 10 pictures. If you happen to be following along and coding this with me, go ahead and try it.

Adding the Custom Route

Next, we need to add a route to handle the page mechanism.

In the global.asax.cs file, in the method called RegisterRoutes add the following route.

    "ImagePaging",                                              // Route name
    "{controller}/Page{pagenumber}",                           // URL with parameters
    new { controller = "Home", action = "Page", pagenumber = "1" }  // Parameter defaults

Notice how the routes are built. It’s a series of url parts and named parameters. For example, the Page2 is going to pass in 2 as the selected pagenumber. We actually could have hard coded the whole path except for the page number.

Adding the Paging Action to the Controller

Now that we’ve got data routing to the an Action, we need to make sure that we’re handling it.

Turns out, this was the easiest piece of all.

public ActionResult Page(string pagenumber)
    ImageModel model = new ImageModel(int.Parse(pagenumber), 10);
    return View("index", model);

Notice that we are just creating the ImageModel leveraging our new constructor and passing it into a view. The view that we’re using is still the index view, which is the default. We don’t have to go build a new view for the paging, we just need to alter the data that we’re passing into our current view.

If you want, you can go test by browsing to /image/page2 and see what it shows.

Adding the Navigation Links

The last thing to do is to add the navigation links to the view. If you use the <% %> tags in any ASPX it runs on the server side. What this is actually doing is that the ASPX page is parsed and generated into code and compiled into a .NET assembly on the server side and the code inside the <% %> just gets copied into that generated code before it’s compiled. This means that the code that’s inside your brackets must match the language that you set at the top of the page.

<%if (ViewData.Model.TotalCount > ViewData.Model.PageSize){ %>
<div class="paging">
    <%if (ViewData.Model.CurrentPage > 1) { %>
        <%= Html.ActionLink("Back", 
"Page" +
(ViewData.Model.CurrentPage - 1).ToString(), "Image")%>&nbsp; <% }%> <%decimal numberOfPages =
decimal.Divide(ViewData.Model.TotalCount, ViewData.Model.PageSize); int lastPageNumber = (int)decimal.Ceiling(numberOfPages); for (int i = 1; i <= lastPageNumber; i++) { if (i != ViewData.Model.CurrentPage) { %> <%= Html.ActionLink(i.ToString(), "Page" + i.ToString(), "Image")%>&nbsp; <% } }%> <%if (ViewData.Model.CurrentPage < lastPageNumber) { %> <%= Html.ActionLink("Next",
"Page" + (ViewData.Model.CurrentPage + 1).ToString(), "Image")%> <% }%> <%=lastPageNumber%> </div> <% }%>

Notice that we’re using the properties set by back in the model here. There’s three different sections here. The first checks to see if we need a back button. The second loops over the pages and creates step links. And the third checks to see if we need a next button.

The navigation links in the view turned out to be the most complicated part of adding paging to the photo gallery.

Stay tuned to future posts for styling with CSS, adding a Silverlight front end and more.

Adding Lighbox.js to the Simple Photo Gallery

image In my previous two posts, Building a Simple Photo Gallery in ASP.NET MVC Framework and Returning Thumbnails With the MVC Framework, I built a simple photo gallery on the ASP.NET MVC framework. In this post we are going to start making this a little prettier. To start with, we are going to leverage an JavaScript project called Lightbox.js that’s released under the Creative Commons Attribution 2.5 License.

One cool part about it is that you can get a tremendous amount of functionality with little to no JavaScript coding on your own. It leverages a couple of different JavaScript libraries including Prototype and Scriptaculous. These do a lot of generic HTML Dom manipulation and visualization.

The result of leveraging Lightbox.js is that when you click on one of the thumbnails that we started showing in Returning Thumbnails With the MVC Framework the full sized picture will show in a really nice lightbox style effect.

First, you need to download the Lightbox.js project. It comes in a zip file that comes with a sample application. Unzip the contents into the appropriate folders. This means that the .js files go in your /scripts directors and the images and the css in the /content folder.

The cool part is that since you have the source to it all, rock on and modify it to your heart’s content. And we’re going to do a light modification right off the bat. We could have put the images from the Lightbox.js project in the /images folder but we’re already using that for something else so we put them in the /content folder. That means that you need to open up lightbox.js and change the directory of the loading and close images to point to the correct directory.

LightboxOptions = Object.extend({
    fileLoadingImage:        'content/loading.gif',
    fileBottomNavCloseImage: 'content/closelabel.gif',

That’s the only mod that we *need* to make at the moment. If you feel like it, you can fix the image paths in lighthouse.css as well.

#prevLink:hover, #prevLink:visited:hover { background: 
url(Content/prevlabel.gif) left 15% no-repeat; } #nextLink:hover, #nextLink:visited:hover { background:
url(Content/nextlabel.gif) right 15% no-repeat; }

The only thing left to do is update the Images/index view to take advantage of our new capabilities. There are two mods to make. First, we need to include links to the lightbox.css and the required 3 JavaScript files (prototype.js, scriptaculous.js and lighbox.js). Second, we need to add a rel=”lightbox” to the anchor tag around our picture.

<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" 
AutoEventWireup="true" CodeBehind="Index.aspx.cs"
Inherits="PhotoGalleryMVC.Views.Image.Index" %> <asp:Content ID="Content1" ContentPlaceHolderID="MainContent" runat="server"> <link rel="stylesheet" href="content/lightbox.css" type="text/css" media="screen" /> <script src="scripts/prototype.js" type="text/javascript"></script> <script src="scripts/scriptaculous.js?load=effects,builder" type="text/javascript"></script> <script src="scripts/lightbox.js" type="text/javascript"></script> <p><%= Html.ActionLink("Add your own image", "Upload", "Image")%></p> <% foreach (var image in ViewData.Model) { %> <span class="image"> <a href="/images/<%= image.Path %>" rel="lightbox">
img src="/image/thumbnail/<%= image.Path %>" />
a> <span class="description"><%= image.Description %></span> </span> <% }%> </asp:Content>

It’s that simple. This will render a really nice little lightbox effect on our images.

Stay tuned for future posts about styling the CSS, paging the pictures and a whole lot more.

Returning Thumbnails With the MVC Framework

In my last post, we put together a quick and simple photo gallery. This post will be building on that.

Depending on the size of your photo, however, it didn’t have the worlds greatest user experience. I’ll be playing with the CSS, JavaScript and a ton more over time. Today, however, I’m going to be just returning a thumbnail rather than the full picture to show in the view.

I don’t want to have to physically create each of the thumbnails so we’ll generate those dynamically on the fly.

Creating a Custom ActionResult

To return a given type of result, you have to return an ActionResult of that type. The types that are currently built in are View, Redirect, RedirectToAction, RedirectToRoute, Content, or Json. We need to create a specific action type that we’ll call the ThumbnailResult. It will be created with a virtual path to the picture that we need to show. When it’s executed, it will generate and return the thumbnail.

public class ThumbnailResult : ActionResult
    public ThumbnailResult(string virtualPath)
        this.VirtualPath = virtualPath;

    public string VirtualPath {get;set;}

    public override void ExecuteResult(ControllerContext context)
        context.HttpContext.Response.ContentType = "image/bmp";

        string fullFileName =
            context.HttpContext.Server.MapPath("~/images/" + VirtualPath);
        using (System.Drawing.Image photoImg =
            using (System.Drawing.Image thumbPhoto =
                photoImg.GetThumbnailImage(100, 100, null, new System.IntPtr()))
                using (System.IO.MemoryStream ms = new System.IO.MemoryStream())
                    thumbPhoto.Save(ms, System.Drawing.Imaging.ImageFormat.Jpeg);

Notice that we’ve set the HttpContext.Response.ContentType to “image/bmp”. This is critical for the browser to understand the data that it recieves.

Leveraging the Custom ActionResult

The next step is to add a method to the controller that will return the ThumbnailResult.

public ActionResult Thumbnail(string id)
    return new ThumbnailResult(id);

And lastly we need to update the view to leverage this new thumbnail action.

<a href=”/images/<%= image.Path %>“><img src=”/image/thumbnail/<%= image.Path %>” /></a>

When you run now, you should get the thumbnails instead of the full sized picture. However, you should still be able to click through to the actual picture. In an upcoming blogpost, we’ll change this to use lightbox.js.

Building a Simple Photo Gallery in ASP.NET MVC Framework

image I decided to create a simple photo gallery in the ASP.NET MVC framework. The fun part is that this level of application is really the new “Hello World”. It takes less time to build than the “Hello World” did back in the day.

In this post, I’ll walk you through the process of creating this simple photo gallery with the MVC framework.

First, let’s talk a little about what the ASP.NET MVC framework is. It’s a web framework built on .NET with the principles of the MVC architecture behind it.

The MVC Architecture

MVC architecture divides the responsibilities of an application into three main components – models, views, and controllers.

image“Models” are responsible for the the data access. The data is often times in a database but it doesn’t have to be. The model could be over an XML file or whatever other data store that you happen to use. By default the ASP.NET MVC framework uses the Entity Framework. However, it can work with any data access type that returns a set of objects that the view can access. Most of the time, this will be an ORM such as the Entity Framework, NHibernate or SubSonic. In our demo below we’re actually going to just be reading in an XML file from the disk.

“Views” are responsible for the actual user interface. Typically this is HTML but it could be XML, JSON or any other number types of display/service response. Most of the time, these displays/responses are built based on model data.

“Controllers” are responsible for the actual logic. It handles the end user interaction, manipulates the data in the model and decides which view to return to the user. Simple enough? 

Creating the ASP.NET MVC Framework Project

image I started out creating an ASP.NET MVC Web Application called PhotoGalleryMVC. There are a couple of very important things to notice in an ASP.NET MVC framework project.

First, look at the Global.asax and it’s code behind. It’s got a really important method called RegisterRoutes where you define your routes.

public static void RegisterRoutes(RouteCollection routes)

        new { controller = "Home", action = "Index", id = "" }


These routes define what happens when your application receives a request. The controller is a class and the action is a method on that class. The parts after that are parameters to the method. We’ll see more with this in a few moments.

The next thing is to notice the controllers. The default method that you get in the helper class is as follows:

public ActionResult Index()
    ViewData["Title"] = "Home Page";
    ViewData["Message"] = "Welcome to ASP.NET MVC!";

    return View();

This is the default action for the controller. It’s simply setting some properties on the View and then returning it. Notice that we’re not instantiating a copy of the view and setting properties directly on it. Instead, we’re staying with the very loosely coupled method of using a ViewDataDictionary called ViewData. This is a dictionary of items that both the view and the controller have access to.

Creating the ImageModel

The first thing I want to create is a way to get the images in the first place. Rather than creating a database, we’re going to simply use an XML file as our storage for our information about our images.

Create a folder called Images under the root of the project. This will be where we put the images.

As a file ImagesMetaData.xml in the images directory following the format below. Feel free to substitute your own data in for the data I have below…

<?xml version="1.0" encoding="utf-8" ?>
    <description>Paul playing Guitar Hero.</description>
    <description>Phizzpop Signin.</description>

Add a class called Image under the model folder. For now this will be really simple.

namespace PhotoGalleryMVC.Models
    public class Image
        public Image(string path, string description)
            Path = path;
            Description = description;
        public string Path { get; set; }
        public string Description { get; set; }

All this class provides for now is a holder for the image path and description. We’ll do more with this class in the future.

The next thing that we need to do is create a way to get those images from the disk. This will be in a class called ImageModel. To make this really simple, we will inherit from a generic list of Image. This gives us a lot of functionality already. What we need to add is a constructor that will retrieve the images from the disk.

namespace PhotoGalleryMVC.Models
    public class ImageModel : List<Image>
        public ImageModel()
            string imagesDir = HttpContext.Current.Server.MapPath("~/images/");
            XDocument imageMetaData = XDocument.Load(imagesDir + @"/ImageMetaData.xml");
            var images = from image in imageMetaData.Descendants("image")
                         select new Image(image.Element("filename").Value,

All this model is doing is reading in the XML file and creating a list of images based on that metadata.

Creating the Controller

The next step is to create the controller. Again, for the moment, this will be extremely simple. We’ll do more with it in the future.

namespace PhotoGalleryMVC.Controllers
    public class ImageController : Controller
        public ActionResult Index()
            return View(new ImageModel());

Notice that this is slightly different than the default controller as it’s passing in the ImageModel. We’ll have to create the View to accept it here in just a moment.

Creating the View

Now we need to add a folder to the hold our images view in the Views folder. Now to create the view in the Images view folder, right-click on the folder and select Add View. Name the view Index.

Now that we have our view, modify it’s declaration to accept the ImageModel class.

namespace PhotoGalleryMVC.Views.Image
    public partial class Index : ViewPage<ImageModel>

What this does is set up our view based on a generic ViewPage with ImageModel as it’s base.

And lastly we need to add the HTMLish stuff to do the actual display.

<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" 
AutoEventWireup="true" CodeBehind="Index.aspx.cs"
Inherits="PhotoGalleryMVC.Views.Image.Index" %> <asp:Content ID="Content1" ContentPlaceHolderID="MainContent" runat="server"> <% foreach (var image in ViewData.Model) { %> <span class="image"> <a href="images/<%= image.Path %>"><img src="images/<%= image.Path %>" /></a> <span class="description"><%= image.Description %></span> </span> <% }%> </asp:Content>

If you’ve ever done ASP Classic or PHP, this HTMLish stuff shouldn’t look too odd. If you strip out the HTML code, you’ve got a normal foreach loop written in C#. The bad news about this approach is that there’s a lot less controls, such as the datagrid and such, available to you. The good news is that you’ve got absolute control over the HTML that is produced.

You should notice, however, that we’re able to leverage master pages as we do in ASP.NET 2. This is great because it allows us to define our look and feel in a master page. There’s a great amount of flexibility and power in that.

Last step is that we need to add a tab on the main navigation to get to the images page. We do that in the /views/shared/site.master

<ul id="menu">
    <li><%= Html.ActionLink("Home", "Index", "Home")%></li>
    <li><%= Html.ActionLink("Images", "Index", "Image")%></li>
    <li><%= Html.ActionLink("About Us", "About", "Home")%></li>

Even though we’ve got few controls at out disposal, there are some interesting helpers such as this Html.ActionLink. This returns a link that points to the appropriate controller and action without us having to divine what that link should be based on the current routes. 

At this point, the application runs and shows really big pictures (assuming that you’ve put a few in the images folder in the first place).

Adding a New Picture

Now that we’ve got a few manually placed a few of the pictures in the folders and gotten them to display on the view, we need a way for the user to add their own pictures to the site. We’re going to do this one in reverse order where we create the view and work backwards from there.

Step one is that we need a new view and a way to get to it from the images page. We can accomplish that with a simple Html.ActionLink in the Image Index view.

    <p><%= Html.ActionLink("Add your own image", "Upload", "Image")%></p>

Now we need to create the view for the New action. Simply right click on the View folder and select Add|View. Name this view “Upload”.

In the view, we need to create a form that will do the post.

<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" 
AutoEventWireup="true" CodeBehind="Upload.aspx.cs"
Inherits="PhotoGalleryMVC.Views.Image.Upload" %>

form method=”post” action=”<%=Url.Action(“save”) %>enctype=”multipart/form-data”>
input type=”file” name=”file” />
    <input type=”submit” value=”submit” /> <br />
    <input type=”text” name=”description” />

It’s not the world’s prettiest form but it’s functional. Notice the action on the form tag. It’s using another helper called Url.Action. This maps to the same controller but a different action.

Now we need to add the upload and save action to the controller. The Upload action is very simple. It simply returns the Upload view. The Save is a little more complicated as it has to do the actual logic of getting the files and descriptions and putting those on the model.

namespace PhotoGalleryMVC.Controllers
    public class ImageController : Controller
        public ActionResult Index()
            return View(new ImageModel());

        public ActionResult Upload()
            return View();

        public ActionResult Save()
            foreach (string name in Request.Files)
                var file = Request.Files[name];

                string fileName = System.IO.Path.GetFileName(file.FileName);
                Image image = new Image(fileName, Request["description"]);

                ImageModel model = new ImageModel();
                model.Add(image, file);
            return RedirectToAction("index");

The important part here is that this controller is not actually doing the logic of saving out to the disk. This is important because it gives us the flexibility to alter the model switch from file based storage to a database and so on. This separation is key to the success of the architecture.

Last thing to do is alter the model to actually save out to the disk.

public void Add(Image image, HttpPostedFileBase file)
    string imagesDir = HttpContext.Current.Server.MapPath("~/images/");
    file.SaveAs(imagesDir + image.Path);

    XElement xml = new XElement("images",
            from i in this
            orderby image.Path
            select new XElement("image",
                      new XElement("filename", i.Path),
                      new XElement("description", i.Description))

    XDocument doc = new XDocument(xml);

    doc.Save(imagesDir + "/ImageMetaData.xml");

The LINQ makes creating the XML document really simple.

There are a lot of optimizations that could be done here such as storing off the model in memory and the like so that we’re not constantly reading/writing to the disk and the like. That’s not the point of this exercise. The point here is to work with the MVC framework.

At this point we’ve got a functioning image gallery with uploads and a view.

In my next post, I’ll alter this to serve up thumbnails and give a nicer user experience.