Well, this is my first post, so please be gentle. I have had this blog open for a while now, but didn’t want to lead off with the usual “who I am and why I’m here” stuff, so I’ve been waiting for the right topic to come along to blog about.
This morning, I found it.
I finally downloaded the latest Visual Web Developer (VWD from here) 2008 beta from Microsoft this morning and started using it, playing around with the new server controls for ASP.Net and so on. I normally use Visual Studio 2005 rather than VWD, but I had problems getting a clean download of that which didn’t have corrupted files after burning to CD. So, let me get to the meat of what my title brought you here for.
After reading Scott Guthrie’s excellent series on Linq and in particular the one on the <asp:LinqDataSource>, and building the example out myself, I was motivated to try out the new <asp:ListView> which he hints about at the end of that article. The bottom line is that this control will take the .Net community like the Gridview did back when 2.0 first came out. You heard it here first, and mark my words. I considered trying to grab the domain name ListViewGuy.com but thought better of it.
A little overview…
What is the ListView? Well, the best way I can describe it is that it’s a GridView that doesn’t force you into a table. It has all the paging, updating, inserting, deleting features of the GridView as well as the now familiar ItemTemplate, EditItemTemplate, AlternatingItemTemplate kinds of nested structures, BUT it confers no markup of its own, that’s entirely up to you as the developer. In short, it’s an asp:Repeater on GridViewSteroids.
Where’s my Elephant? (or, how ’bout an example, Raptor?)
OK, so an example is in order. Let’s say you want to do the unthinkable (ha!) and build semantically meaningful markup to, for example, have a contacts list. Let’s say I wanted to build a simple contact list, but I wanted to use a microformat to do it, rather than something I created on my own.
So to be a touch retro, I’ll use the Northwind db as my database for this, I’ll use a LinqDatasource to access that data over a Linq designer document (all that’s covered in Scott’s blog referenced above, so I’ll skip it). Suffice to say that my DBML diagram looks like this:
Yeah, simple, I know.
Anyway, so I’m going to go with a simple hCard microformat to represent each of these guys:
<div class=”fn org”>/*Organization Name*/</div>
<span class=”fn n” lang=”en”>
<span class=”given-name”>/*first name*/</span>
<span class=”additional-name”>/*middle name*/</span>
<span class=”family-name”>/*last name*/</span>
<div class=”street-address”>/*Full street addr.*/</div>
<abbr class=”region” title=”/*State name*/”>/*state abbreviation*/</abbr> <span class=”postal-code”>/*zip*/</span>
<div>Phone: <span class=”tel”>/*telephone*/</span></div>
<div>Email: <span class=”email”>/*email addr*/</span></div>
Ok, so that’s how I want to represent one contact. A list of contacts, to me, would be an ordered list. Why an ol? well, b/c I plan on enabling paging and sorting, which means that it has an ordered structure to it. So, planning is done, onto the actual implementation! Starting with an open project in VWD 2k8 with .Net framework level set to 3.5, I do the following.
- Add LinqDataSource. Simply put, open my toolbox, double click on the LinqDataSource and it adds it to the page. To make it easy, I even used their Configure Datasource wizard (one of the smart tags in Design or Split view) to point it at the Contacts data object, to name it ContactsDatasource, and to enable Insert, Delete, and Update. Otherwise I took the defaults.
- Add a ListView. Again, keeping it simple, I just dropped a Listview from the toolbox over to the page. I am going to go into the markup now to show you how easy it is, even without wizards (though their wizards are pretty cool). So, to begin I add in the base tag information:
<asp:ListView id=’ContactsList’ DataKeyNames=’ContactID’ InsertItemPosition=’LastItem’ DataSourceID=’ContactDatasource’ runat=’server’><
Straightforward and simple, just like the basic GridView tag. The main thing that’s new here is the InsertItemPosition, and that simply refers to where the option to insert a new data item will go, where that template will go in the flow of the list, either first or last.
- Add the Layout Template. The Layout template specifies what the container tags will look like, and also if you want to have anything before or after it. this is a page-level thing, so if you have paging set up, then the LayoutTemplate is where you’ll put your pager control.
<ol id="itemContainer" runat="server"></ol>
<div><asp:datapager ID="DataPager1" runat="server">PreviousPageText=”Previous”ShowFirstPageButton=”True” ShowLastPageButton=”True” />
<asp:nextpreviouspagerfield ButtonType="Button" FirstPageText="First"
</LayoutTemplate>So, what we’re showing here is the layout of essentially each ‘page’ of data. I want an ordered list, so I make an ol with the ID of itemContainer. As near as I can tell that id is required for the control to key off of. The datapager is a new control which sends paging commands to the datasource control to get the datasource to fetch the next page of data. In this case, I used one of their out of the box impllementations, but this control also supports a templated control which means you can certainly roll your own if you like.
- Add an ItemTemplate. Just like the .net 2.0 databound controls, the ListView has a number of templates depending on what you’re trying to do. I’m just going to show the ItemTemplate today, b/c I’m running out of gas on the typing here, but basically in the item template you put whatever markup and Evals that you want to make the information lay out the way you wanted to. Here’s where my microformat comes into play:
<div class=”fn org”><%# Eval(“CompanyName”) %></div>
<span class=”fn n” lang=”en”><%# Eval(“ContactName”) %></span>
<div class=”street-address”><%# Eval(“Address”) %></div>
<span class=”locality”><%# Eval(“City”) %></span>, <abbr class=”region”><%# Eval(“Region”) %></abbr><span class=”postal-code”><%# Eval(“PostalCode”) %></span></div>
<div class=”country-name”><%# Eval(“Country”) %></div>
<div>Phone: <span class=”tel”><%# Eval(“Phone”) %></span></div>
<asp:Button ID=”EditButton” runat=”server” CommandName=”Edit” Text=”Edit” />
<asp:Button ID=”DeleteButton” runat=”server” CommandName=”Delete” Text=”Delete” />
This should look familiar to you if you’ve ever worked with a Repeater or DataList, but the key difference is that you also get built-in paging support as well as the automatic alternating item support and insert, delete, edit functionality.
I have to say that I planned on doing the whole thing in one shot, but it’s gotten pretty long. We’ll call this part 1, then and I’ll move onto part 2 at a later date. I’ll say in conclusion that I’m already a pretty big fan of this control. It’s nice and lightweight in terms of coding time and markup, and really allows a developer the kind of flexibility that he or she needs in developing apps these days.