Dynamic Data and Field Templates - Your First FieldTemplate *** UPDATED *** (original) (raw)

  1. The Anatomy of a FieldTemplate.
  2. Your First FieldTemplate.
  3. An Advanced FieldTemplate.
  4. A Second Advanced FieldTemplate.
  5. An Advanced FieldTemplate with a GridView.
  6. An Advanced FieldTemplate with a DetailsView.
  7. An Advanced FieldTemplate with a GridView/DetailsView Project.

We’ll create a simple FieldTemplate that displays an enumeration as RadioButtonList.

Create Database and Table

We will need a database to run against so in Solution Explorer create a new ASP.Net folder App_Data in the root of the website and create a new Database in there called Animals. Now create a new table called Pets with the following columns.

Pets Table

Figure 1 – Pets Table

Create the Enumeration Type

///

/// My not very exhaustive set of animals /// public enum AnimalType { Budgie, Cat, Dog, Gerbil, Hamster, Lizard, Mouse, Parrot, Rat, Snake }

public enum Gender // Added { Male = 0, Female = 1 }

Listing 1 – AnimalType & Gender ***UPDATED***

Create the Model

Add a new Linq to SQL to the App_Code folder and and call it Animals. Copy the Pets table to it. Now we need to set the type of the Pets.Type to AnimalTypes and also do the same for the sex column setting its type to Gender.

Setting the Pets.Type to AnimalType enum

Figure 2 - Setting the Pets.Type to the AnimalType enum

Save the and Close the Model.

In the same class file as the enums add your metadata.

using System.ComponentModel.DataAnnotations; using System.ComponentModel;

[MetadataType(typeof(PetMetaData))] public partial class Pet { public class PetMetaData { [UIHint("Enumeration")] public object Animal { get; set; }

    [UIHint("Enumeration")]
    public object sex { get; set; }
}

}

Listing 2 – Pet metadata ***UPDATED***

Creating a New FieldTemplate

Expand the DynamicData folder and right-click on the FieldTemplates folder, choose Add New Item… and choose Web User Control from the list of items. Give it the name Enumeration_Edit.ascx

Change the base class that the user control inherits from System.Web.UI.UserControl to System.Web.DynamicData.FieldTemplateUserControl. and a new using System.Web.DynamicData. Change the class name to Enumeration_EditField from DynamicData_FieldTemplates_Enumeration_Edit in both the ascx and code behind files.

<%@ Control Language="C#" AutoEventWireup="true" CodeFile="Enumeration.ascx.cs" Inherits="**Enumeration**_EditField" %>

Listing 3 – Enumeration_Edit.ascx

using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.Web.UI; using System.Web.UI.WebControls; using System.Web.DynamicData;

public partial class Enumeration_EditField : System.Web.DynamicData. FieldTemplateUserControl {

}

Listing 4 – Enumeration_Edit.ascx.cs code behind

The UserControl is now ready for us to add our code to make it show a DropDownList control populated with AnimalTypes.

Building Our Custom FieldTemplate

Add a DropDownList to the UserControl leave it as DropDownList1 and switch to the code behind.

In the code behind body of the class type protected override On and as you type On you will notice the auto-complete intellisense offer you some options use the arrow keys to select OnDataBinding and hit the tab key (but not too hard or you will break your keyboard :D).

‌auto-complete intellisense

Figure 3 - Auto-Complete Intellisense

Now you should have:

public partial class Enumeration_EditField : System.Web.DynamicData.FieldTemplateUserControl { protected override void OnDataBinding(EventArgs e) { base.OnDataBinding(e); } }

Listing 5 – OnDataBinding event handler

I mentioned the above because I think it’s really neat smile_teeth.

Note: When overriding OnDataBinding be sure to call the base class's OnDataBinding method so that registered delegates receive the event.

After the base.OnDataBinding(e); line we need to add our code to populate the DropDownList.

<%@ Control Language="C#" AutoEventWireup="true" CodeFile="Enumeration_Edit.ascx.cs" Inherits="Enumeration_EditField" %>

<asp:DropDownList runat="server" ID="DropDownList1" CssClass="droplist" **OnDataBound** **="DropDownList1_DataBound"**>

Listing 6 – Finished Enumeration_Edit.ascx note the OnDataBound

using System; using System.Web.UI; using System.Web.UI.WebControls;

public partial class Enumeration_EditField : System.Web.DynamicData.FieldTemplateUserControl { protected override void OnDataBinding(EventArgs e) { // When overriding OnDataBinding be sure to call the base class's // OnDataBinding method so that registered delegates receive the event. base.OnDataBinding(e);

    // get a data bindable list of permissions for the DDL
    var enumList = Enum.GetValues(Column.ColumnType);

    DropDownList1.DataSource = enumList;
    DropDownList1.DataBind();
}

protected override void ExtractValues(System.Collections.Specialized.IOrderedDictionary dictionary)
{
    dictionary[Column.Name] = ConvertEditedValue(DropDownList1.SelectedValue);
}

protected void DropDownList1_DataBound(object sender, EventArgs e)
{
    // make sure we are in edit mode
    if (Mode == DataBoundControlMode.Edit)
    {
        // try to get an item in the list that matched the FieldValueString
        ListItem item = DropDownList1.Items.FindByValue(FieldValueString);
        if (item != null)
        {
            // if we get the value set the drop down list to FieldValueString
            DropDownList1.SelectedValue = FieldValueString;
        }
    }
}
// This is one of those needed things I think it allows
// access to the actual control through Controls property
public override Control DataControl
{
    get
    {
        return DropDownList1;
    }
}

}

Listing 7 – Finished Enumeration_Edit.ascx.cs

Now we need an Enumeration.ascx file for this FieldTemplate all we need is to create a copy of the Text.ascx FieldTemplate control.

<%@ Control Language="C#" CodeFile="Enumeration.ascx.cs" Inherits="EnumerationField" %>

<asp:Literal runat="server" ID="Literal1" Text="<%# FieldValueString %>" />

Listing 8 – Enumeration.ascx

using System.Web.UI;

public partial class EnumerationField : System.Web.DynamicData.FieldTemplateUserControl { public override Control DataControl { get { return Literal1; } } }

Listing 9 – Enumeration.ascx.cs

This blatant copy if the Text.ascx FieldTemplate is due to the fact that our enumeration types don’t have a direct conversion to text and so don’t automatically drop through to the Text.ascx FieldTemplate.

Now we can edit and view our data.

Note: And yes I know that there is an Enumeration control in the Dynamic Data Futures and it doesn’t need the UIHint, but I just wanted something that was not too trivial :D