ONDotNet.com    
 Published on ONDotNet.com (http://www.ondotnet.com/)
 See this if you're having trouble printing code examples


What's New in Beta 2: Web Parts Revisited

by Jesse Liberty
06/13/2005

I've been working with Whidbey (.NET 2005) for a little over a year. During that time, I've come to have enormous respect for the engineers at Microsoft, and I do believe that .NET 2005 (2.0) is a great improvement over 1.x. That said, the beta has had a bit of a hard time settling down, and so many of the earlier columns I wrote (and that others wrote) about Whidbey are, at best, a bit out of date (and some are badly broken).

This column will revisit, fix, and expand on one of my favorite 2.0 features: Web Parts.

Before we begin, however, let me note that Microsoft has published a few articles about features they had hoped to get into beta 2, but that didn't make it, including an excellent article titled " Features Postponed in ASP.NET 2.0." In addition to what is listed on that page, however, other features simply changed, or disappeared.

One breaking change, for example, is that the IEnumerable interface now extends the non-generic IEnumerable interface.

public interface IEnumerable<T> : IEnumerable

The net result is that in order to implement the interface you must include a non-generic GetEnumerator method. Since the signatures for the generic and the non-generic GetEnumerator methods are identical, you must implement the non-generic form explicitly:


IEnumerator IEnumerable.GetEnumerator()
{
	throw new NotImplementedException();
}

There are a few other breaking changes here and there that make moving to beta 2 from the CTP an adventure, but one of the more significant, to me, is the change to how Web Parts work. The key change here is that the Web Part Page Menu is now removed, and thus you must supply that functionality yourself. This article will walk you though creating a Web Part Page and will expand on my previous article to show you how to add a catalog and an editor menu to give your users even greater control over your page.

To begin, please download the WebPartsBeta2Starter kit and use that as the starting point for this article. This starter kit assumes you have already installed SQL Express on your local machine, and set it up to support personalization (see my previous column on personalization for details). You start with a single login account: jliberty. The password is Liberty! (that is an exclamation point [bang] at the end of my last name).

Note: In beta 2, Microsoft implemented the System.Web.UI.WebControls.CreateUserWizard.PasswordRegularExpression property, which defaults to the following "strong" password requirements: it must be at least six characters long, and must include at least one element each from three of the four types of characters: English upper case, English lower case, Arabic numerals, and special characters. (See " Strong Password Enforcement" for more information.)

The first step is to open the starter kit and make sure it works. Log in and you should see a screen very much like Figure 1:

Starter Kit Running
Figure 1.

You'll create a new page, WebPartsDemo, and a link to that page for the logged in user. To begin, modify Welcome.aspx and add a third hyperlink within the LoggedInTemplate:


<LoggedInTemplate>
   Welcome
   <asp:LoginName ID="LoginName1" runat="server" />
   <br />
   <asp:HyperLink ID="HyperLink2" NavigateUrl="CreateAccount.aspx" 
      runat="server">Create User</asp:HyperLink>
   <asp:HyperLink ID="HyperLink3" NavigateUrl="ManageRoles.aspx" 
      runat="server">Manage Roles</asp:HyperLink>
   <asp:HyperLink ID="HyperLink4" NavigateUrl="WebPartsDemo.aspx" 
      runat="server">Web Parts</asp:HyperLink>
</LoggedInTemplate>

You are now ready to create the WebPartsDemo.aspx page.

Creating Zones

A page that uses Web Parts is divided into zones: areas of the page that can contain content and controls that derive from the Part class (Part controls). They can also contain consistent UI elements (header and footer styles, border styles, etc.) known as the chrome of the control. For this example, you'll arrange your zones in a table (to make layout easier). Here are the steps:

  1. Create a new page called WebPartsDemo.aspx.
  2. Open the WebParts section of your Toolbox, and drag a WebPartsManager onto your page from the WebParts panel in the toolbox. (The job of the WebPartsManager is to track and coordinate all of the web part controls on the page. It will not be visible when the page is running.)
  3. Add a new table, with two rows and three columns. Rearrange the columns so that they are not of even size.
  4. Drag a WebPartZone into each of the six table cells. Each WebPartZone will have a default name (e.g., "WebPartZone6") and a default heading. You can easily modify either or both of these properties in the properties window. Your page should now look like Figure 2:

Laying out the zones
Figure 2.

Adding Controls To Zones

Set the HeaderText property on the first zone to News. Drag a Label control into the zone; it should now look like Figure 3:

Label As Web Part
Figure 3.

The <asp:label> web control does not have a title attribute, but because it is now wrapped in a Web Part control, which does have a title attribute, you can set the title (though you will confuse Intellisense). To see this at work, switch to Source view and modify the label as shown:


<asp:Label 
Runat="server" Title="Today's News" ID= 
"Label1"><br />Thousands die. Thousands more die at eleven.</asp:Label>

While you are in Source view, set the label's text to "Thousands die. Thousands more die at eleven."

Switch back to Design view, set the page title to "Web Parts," and then drag a ListBox control into WebPartZone3. Click on the list box, and then on its smart tag and Edit Items to open the ListItems Collection Editor. Add a few items to the list box. Back in Source view, set the Title property to "Our Sponsors." Run the application, log in as jliberty, and your page should look more or less like Figure 4:

Two Web Zones displayed
Figure 4.

Minimizing and Restoring

Click on the Minimize tag and a menu appears allowing you to minimize or close the Web Part, as shown in Figure 5:

Minimize or Close
Figure 5.

If you choose Minimize, the Web Part is minimized to its title, and the Minimize tag offers the choices of Restore or Close. If you stop the application, then restart and log back in and return to the page, it will still be minimized (personalization at work).

Enabling Editing and Layout Changes

In order to edit the contents of zones or move controls from one zone to another, you need to be able to enter Edit and Design mode. To do so, you will create a new user control, called DisplayModeMenu.ascx, that will allow the user to change modes among Browse, Edit, and Design, as shown in Figure 6:

Display Mode Menu
Figure 6.

Add a new user control named DisplayModeMenu.ascx to your project, and in the content file add the following code:


<div>
  <asp:Panel ID="Panel1" runat="server" 
    Borderwidth="1" 
    Width="230" 
    BackColor="lightgray"
    Font-Names="Verdana, Arial, Sans Serif" >
    <asp:Label ID="Label1" runat="server" 
      Text=" Display Mode" 
      Font-Bold="true"
      Font-Size="8"
      Width="120" />
    <asp:DropDownList ID="ddlDisplayMode" runat="server"  
      AutoPostBack="true" 
      EnableViewState="false" 
      Width="120"
      OnSelectedIndexChanged="ddlDisplayMode_SelectedIndexChanged" />
  </asp:Panel>

This creates a panel that contains a drop-down list and sets the event handler for when the selected item changes. To implement the event handler, you'll add code to the code-behind page DisplayModeMenu.ascx.cs:


using System;
using System.Data;
using System.Configuration;
using System.Collections;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;

public partial class DisplayModeMenu : System.Web.UI.UserControl
{
   // Use a field to reference the current WebPartManager control.
   WebPartManager webPartManager;

   public void Page_Init( object sender, EventArgs e )
   {
      Page.InitComplete += new EventHandler( InitComplete );
   }

   // when the page is fully initialized
   public void InitComplete( object sender, System.EventArgs e )
   {
      webPartManager = WebPartManager.GetCurrentWebPartManager( Page );

      String browseModeName = WebPartManager.BrowseDisplayMode.Name;

      foreach ( WebPartDisplayMode mode in
        webPartManager.SupportedDisplayModes )
      {
         String modeName = mode.Name;
         if ( mode.IsEnabled( webPartManager ) )
         {
            ListItem listItem = new ListItem( modeName, modeName );
            ddlDisplayMode.Items.Add( listItem );
         }
      }
   }

   // Change the page to the selected display mode.
   public void ddlDisplayMode_SelectedIndexChanged( object sender,
     EventArgs e )
   {
      String selectedMode = ddlDisplayMode.SelectedValue;

      WebPartDisplayMode mode =
       webPartManager.SupportedDisplayModes[selectedMode];
      if ( mode != null )
      {
         webPartManager.DisplayMode = mode;
      }
   }

   // Set the selected item equal to the current display mode.
   public void Page_PreRender( object sender, EventArgs e )
   {
      ListItemCollection items = ddlDisplayMode.Items;
      int selectedIndex =
        items.IndexOf( items.FindByText( webPartManager.DisplayMode.Name ) );
      ddlDisplayMode.SelectedIndex = selectedIndex;
   }
}

To use your nifty new control, open the WebPartsDemo page in design mode and make a space between the WebPartManager and the table that contains your zones. Drag the DisplayModeMenu.ascx file from the Solution Explorer right onto your page. Hey! Presto! Visual Studio registers your control in the WebPartsDemo.aspx page.


<%@ Register Src="DisplayModeMenu.ascx" TagName="DisplayModeMenul" TagPrefix="uc1" %>

It also places the control on the page (you can verify this in Source view if you don't trust me. It's okay, I don't mind. People are so suspicious these days. I'll just wait here while you check. Don't mind me, I can keep busy ...).

Before testing this, drag an Editor Zone into the lower right-hand cell in the table (if there is already something in that cell, delete it) and then drag an AppearanceEditorPart and a LayoutEditorPart onto the Editor Zone. To make the Editor Zone stand out, click on its smart tab and choose AutoFormat and then Professional. Your page should look like Figure 7.

Editor Zone Added
Figure 7.

Moving a Part

Run the application. When you log in and go to the Web Parts page, you are in Browse mode. Use the DisplayModeMenu drop-down menu to switch to design mode, and all of the zones (except the editing zone) appear. You can now click on any Web Part (e.g., "Today's News") and drag it to any zone, as shown in Figure 8.

Moving Web Parts
Figure 8.

Editing A Part

Click on the drop-down menu and choose Edit. Nothing much happens, but click on the drop down tag on one of the web part controls. A menu appears that now includes Edit, as shown in Figure 9.

Edit Menu
Figure 9.

When you select Edit from this menu, the Edit Zone you added earlier appears, allowing you to edit the appearance of the web part, as shown in Figure 10.

Editor Zone Working
Figure 10.

 

Adding Parts from a Catalog

You can provide your users with a catalog of web parts that they can assign to the various zones on their page. This allows the user to pick the information of particular interest (stock quotes, weather, news, etc.) and virtually hand-craft the look and feel of the page. To do so, open WebPartsDemo.aspx in Source view and find Zone 4. Remove it from the cell so that the cell is empty. Switch to Design view and drag a CatalogZone control into newly empty cell. Click on the zone, and in the properties window set the HeaderText property to Catalog Zone. Drag a DeclarativeCatalogPart control into the zone, as shown in Figure 11.

Adding A Declarative Catalog Part
Figure 11.

Click the smart tag on the DeclarativeCatalogPart and select Edit Templates. From the standard tab of the toolbox, drag on a Calendar and a File Upload control. Switch to Source view and find the catalog zone. Within the <WebPartsTemplate> element, add a Title attribute to both the Calendar and the File Upload controls.


<asp:CatalogZone ID="CatalogZone1" runat="server">
   <ZoneTemplate>
      <asp:DeclarativeCatalogPart ID="DeclarativeCatalogPart1" runat="server">
         <WebPartsTemplate>
            <asp:Calendar ID="Calendar1" runat="server" title="Calendar" />
            <asp:FileUpload ID="FileUpload1" runat="server" title="Upload Files" />
         </WebPartsTemplate>
      </asp:DeclarativeCatalogPart>
   </ZoneTemplate>
</asp:CatalogZone>

Run the application. Drop down the display mode menu and notice that the Catalog mode has been added, as shown in Figure 12.

Display Mode with Catalog
Figure 12.

When you click on Catalog, the newly added catalog zone is exposed. You may select one of the controls and decide which zone to place it in, as shown in Figure 13.

Using the Catalog Zone
Figure 13.

Once you've picked your control and the zone to add it to, click Add and the control instantly appears in the designated zone.

ASP.NET 2.0: A Developer's Notebook

Related Reading

ASP.NET 2.0: A Developer's Notebook
By Wei-Meng Lee

Jesse Liberty is a senior program manager for Microsoft Silverlight where he is responsible for the creation of tutorials, videos and other content to facilitate the learning and use of Silverlight. Jesse is well known in the industry in part because of his many bestselling books, including O'Reilly Media's Programming .NET 3.5, Programming C# 3.0, Learning ASP.NET with AJAX and the soon to be published Programming Silverlight.


Return to OnDotNet.com

Copyright © 2009 O'Reilly Media, Inc.