9/20/12

MVC WebGrid Helper


If you are using Razor views and need to build a grid to show data, you can leverage the WebGrid  HTML helper. This helper can let us build a grid with several features like custom styles, sorting, paging and AJAX reload.   

This helper is found in the System.Web.Helpers.dll which should be configured automatically when using WebMatrix. If you are using Visual Studio 2010 MVC 3 projects with Razor views, you may need to install a NuGet package by entering this command in the Package Manager Console (Tools->Library Package Manager)

Install-Package RazorGenerator.Templating

That command should add the reference automatically.

The Model:

For the purpose of this article, we will be using a simple model with a few properties. 

public class Item
{     
    public int Id{get;set;}
    public string Name{get;set;}
    public string Description{get;set;}
}

We will create a list of items that we can show on the grid:

List<Models.Item> items = new List<Models.Item>();
items.Add(new Models.Item{Id=1,Name="Prod1",Description="one"});
items.Add(new Models.Item{Id=2,Name="Prod2",Description="two"});
items.Add(new Models.Item{Id=3,Name="Prod3",Description="three"});
items.Add(new Models.Item{Id=4,Name="Prod4",Description="four"});
 
Now that we have the model ready with a few records, we can work on showing the data on the grid.

Basic Grid:

To build a basic grid, we just need to instantiate the grid and pass the model in the constructor:

WebGrid grid = new WebGrid(items);

On the view, we just need to add this mark-up:

@grid.GetHtml()

We can now run the application and load the view. The grid on its simplest form looks like this:


This is just a basic HTML table with not much style, but the WebGrid helper provides several other features that can allow us to customize the way it renders. For example, if you need to control the number of pages, you can change the instantiation to look like this:

WebGrid grid = new WebGrid(items, rowsPerPage:2);

The view now renders a paging control on the footer of the grid, and it shows two records per page.


We should now control the way the columns are displayed. This can be done by adding columns to the grid to specify the columns order, the field to bind and the header label.


@grid.GetHtml(
       columns:grid.Columns(
             grid.Column("Id", "Item Id"),
             grid.Column("Name", "Name"),
             grid.Column("Description", "Description")
       )
      )

After making this change, we can now refresh the page, and the grid should look this way:



Grid and Styles:

We should now try to improve the design with some CSS changes. The WebGrid helper allows us to add a class names to style the table, header, footer, row and alternating row elements. We first add these CSS styles:

.gridTable {margin: 5px;padding: 10px;border: 1px #c8c8c8 solid;border-collapse: collapse;min-width: 550px; background-color: #fff;color: #fff;}
.gridHead th{font-weight: bold;background-color: #030D8D;color: #fff;padding: 10px}
.gridHead a:link,.gridHead a:visited,.gridHead a:active,.gridHead a:hover {color: #fff;}
.gridHead a:hover {text-decoration:underline;}
.gridTable tr.gridAltRow{background-color: #efeeef;}
.gridTable tr:hover{background-color: #f6f70a;}
.gridAltRow td{padding: 10px;margin: 5px; color: #333;}
.gridRow td{padding: 10px;color: #333;}
.gridFooter td{padding: 10px; background-color: #c7d1d6;color: #999;font-size: 12pt;text-align: center;}
.gridFooter a{font-weight: bold;color: #333; border: 1px #333 solid;}

We can now apply the styles to the grid by associating the grid elements to our CSS class names as listed below:

@grid.GetHtml(
       tableStyle: "gridTable",
       headerStyle: "gridHead",
       footerStyle:"gridFooter",
       rowStyle:"gridRow",
       alternatingRowStyle: "gridAltRow",
       columns:grid.Columns(
             grid.Column("Id", "Item Id"),
             grid.Column("Name", "Name"),
             grid.Column("Description", "Description")
       )
      )

We refresh the page, and our grid now looks like this:




That is much better. You can also notice that the paging control has been improved with better fonts and button style. We added a hover style to the rows as well. This allows us to highlight the rows as the cursor moves over them.


The grid by default provides sorting capability. If we click on the headers, we can see how the data is sorted. We added a style to the header labels to underline the selected header when the cursor hovers over the label.

AJAX Reload:

One more thing to notice is that when we sort or click to another page, the whole page refreshes.  We can prevent a page reload by using AJAX.  To achieve this, we first need to wrap the grid markup with a DIV element as follows:

<div id="gridContent">
  
    @grid.GetHtml(
       tableStyle: "gridTable",
       headerStyle: "gridHead",
       footerStyle:"gridFooter",
       rowStyle:"gridRow",
       alternatingRowStyle: "gridAltRow",
       columns:grid.Columns(
             grid.Column("Id", "Item Id"),
             grid.Column("Name", "Name"),
             grid.Column("Description", "Description")
       )
      )
 </div>

When we instantiate the grid, we need to set the AJAX parameter ajaxUpdateContainerId with the id of our div:

WebGrid grid = new WebGrid(items, rowsPerPage:2, ajaxUpdateContainerId: "gridContent");

Refresh the page, we can now try to sort or click to another page, and we can notice that there is no page post back as only the grid reloads. There are additional features that we did not cover on this post, but I hope I was able to provide a bit more insight on how to use the WebGrid helper.



9/8/12

What is the difference between ObjectSet and EntityCollection?


When working with the Entity framework, you may see that there are two types of collection created, ObjectSet and EntityCollection. Many of us get a bit confused as of why there are two types of collections and about their use. I will try to describe my understanding of their differences:

ObjectSet Definition from MSDN:

public class ObjectSet<TEntity> : ObjectQuery<TEntity>,
        IObjectSet<TEntity>, IQueryable<TEntity>, IEnumerable<TEntity>,
        IQueryable, IEnumerable 
where TEntity : class

ObjectSet provides access to entities/tables of a database.  ObjectSet is IQueryable which means that when you use this reference with a LINQ query, the expression is changed to the SQL expression for the provider (i.e. Entity classes mapping to SQL Server). This is how LINQ works for the LINQ to Entities expressions to be able to select records from the database.

EntityCollection Definition from MSDN:

public sealed class EntityCollection<TEntity> : RelatedEnd, 
        ICollection<TEntity>, IEnumerable<TEntity>, IEnumerable, IListSource 
where TEntity : class

EntityCollection is a collection type which represents “many” entities. When we use LINQ to query an EntityCollection, we are using LINQ to Objects to retrieve the “in-memory” objects in the collection, and no query is executed in the database.  The records for this collection are the ones associated to a main entity as a property and are loaded using the Load method which uses an ObjectSet to load the records from the database. Look at this pseudocode:

VehicleMake: IQueryable{                //represents the ObjectSet
        VehicleModels:IEnumerable      //represents an EntityCollection populated by Load()
}

VehicleModels:IQueryable{// ObjectSet which gets the records from the database
}

When the collection is a property is an EntityCollection.

I hope this is able to help some of you.

9/3/12

Wireframe a Mobile Application


When designing a mobile application, one of the first activities should be to wireframe the application first. This allows us to define the application views, navigation and the user interaction.

What is a wireframe?

This is the design process of the application in which you can create rough sketches of how the application should look and behave. This allows us to identify any possible design issues early in the process. The corrections can be made on the sketch which has less impact than to try to correct software already written. The goal should be that all your application requirements should be met and that the user interface should be consistent, intuitive, balanced and readable.

Application Views

These are the pages/screens of your application. The idea is to understand what the application should offer to the user and identify how many views are needed to deliver the feature set. When defining the view, we need to have a plan for the following elements:

Header

The header displays application information like title and icons, and it is displayed in all the views.  It is also used to provide a Back and/or home navigation button to allow the navigation back to the previous page.

Theme

The theme is the combination of color that you want on your application. The colors are used on the different elements like headers, footers, controls, content panels and fonts.

Design/Layout

This determines the look of your application. You may want an application with icons, sliding images or list views on the main page.  You also need to define how you want the layout of the labels, input controls and buttons. Place your elements with enough padding and alignment to create a balanced layout. This is the most difficult aspect of the design. You need to be creative and be able to define something that is appealing and intuitive to the users. The key is to also be consistent with your design in all the views. Maintain the same look and feel in all the views. 

Fonts

Make sure the fonts that you select are clearly visible and with enough padding between other elements to provide a balance and easy to read interface.

Footer

The footer is also displayed in all the views. It is used to provide quick actions to the users like a toolbar. It is also often used to show promotional or copyright information to the user. The footer is a context driven element. It may display controls or information that is just relevant to the current view.


Navigation

This is very important on any application. You need to provide users with the ability to know where they are in the application and how they can get to another location in a very intuitive way. The user should be able know how to get back to previous views without much effort or just click back to the main page. The transitions between views should have the same effect in the entire application. You should select sliding, popup or any other effect that lets the user know that a new view is in transition. The key is to be consistent and maintain the same effect. 

User Interaction

First minute of usage is important. If the user finds your application easy to use, he will probably explore more and navigate to other pages to see what other features are available.  The application should load quickly, so the user is not left waiting for too long. Here we need to make sure that we choose user interface elements that are intuitive for the user to interact with.


Conclusion

There are several tools on the internet that can let you create a wireframe for free. Just search for one in one of your favorite search engines. If you like, you can also just use a pencil and paper and then scan your sketches.

I hope I was able to provide some ideas on what to consider when building wireframes for your next mobile applications. If you follow these tips, I am sure you will find that your next design will adjust easy to changes.