PANVEGA’s Blog

DotNet Development, SharePoint Customizing, Silverlight, MS Infrastructure and other tips and tricks

Introduction in SharePoint Field Types

Posted by PANVEGA on March 28, 2007

DeeThis is the first post of some of theme I am going to write about this topic, and I will use it to introduce in the concept of the custom field types.

In MOSS, and for any list, we can create columns based on a great number of different field types, that let us to work with the information in many different ways. But, some times, we could need something more adapted.

They allow you to create your own subclasses of the existing SharePoint field types. You can control pretty much every aspect of the fields behavior. Things such as how the field is displayed/rendered in the SharePoints interface, how the data is formatted when it gets stored in the field, validation, and all kinds of other cool stuff.

To create a custom field type, you can extend a default Windows SharePoint Services field type by defining a custom field type and control for displaying the field, and then adding a field type definition to register the field type and its control.

Windows SharePoint Services offers the ability to create custom field types, based on the robust set of base field types it provides. These custom fields can include custom data validation, custom field rendering, and custom field property rendering and processing.

Visual Studio Extensions for Windows SharePoint Services 3.0 provides support for creating SharePoint field types through the Field Control project item.

Visual Studio Code Project:

Visual Studio adds two Microsoft Visual C# code files to the project: Field.FieldControl.cs and Field.Field.cs. The Field.Field.cs file contains code that defines a class that by default is derived from the SPFieldText class and that overrides the FieldRenderingControl property.

The generated implementation of this property returns an instance of the Visual Studio–generated Field.FieldControl field control class that is defined in LogoField.FieldControl.cs. The Field.FieldControl class implements the rendering, validation, and processing support provided by the field control.

You can create a Class Library project that defines custom classes for the field type and the control, copy the DLL of your project to the global assembly cache (GAC), and then add an XML file containing a definition that references the DLL to Local_Drive:\\Program Files\Common Files\Microsoft Shared\web server extensions\12\TEMPLATE\XML.

In this cases, we can take advantage of this feature, that is not only present at MOSS, but in the previous version too, but as I am working on MOSS .

The power of the custom field types is that, they let us not only to define how the information is saved, but how it is showed to the end user, and how he works with it, and really, they don’t have a complex development.

Default generated VS Template MyCustomField.Field.cs Example:

namespace MS.Samples.SharePoint.CustomFieldType
{
    public class MyCustomFieldControl : SPFieldText
    {
        public MyCustomFieldControl (SPFieldCollection fields, string fieldName)
            : base(fields, fieldName)
        {}
        public MyCustomFieldControl (SPFieldCollection fields, string typeName, string displayName)
            : base(fields, typeName, displayName)
        {}

        public override BaseFieldControl FieldRenderingControl
        {
            get
            {
                BaseFieldControl fieldControl = new myCustomFieldControl(this);
                fieldControl.FieldName = InternalName;
                return fieldControl;
            }
        }
    }
}

The example above defines a custom field for displaying MyCustomFieldControl that derives from the SPFieldText class. The example overrides the FieldRenderingControl property to call a custom MyCustomFieldControl constructor that is defined in the next example.

Example of the Field.FieldControl.cs

private ListBox listBox;
private HtmlTable table;

protected override void CreateChildControls()
{
    base.CreateChildControls();
    this.table = new HtmlTable();
    HtmlTableRow row = new HtmlTableRow();
    table.Rows.Add(row);
    HtmlTableCell cell = null;

    if (this.ControlMode == SPControlMode.Edit ||
        this.ControlMode == SPControlMode.New)
    {
        cell = new HtmlTableCell();
        cell.ColSpan = 2;
        cell.Attributes["class"] = "ms-formdescription";
        cell.InnerText = "Choose a logo:";
        row.Cells.Add(cell);
        row = new HtmlTableRow();
        cell = new HtmlTableCell();

        // Create a logo selector listbox.
        this.listBox = new ListBox();
        this.listBox.Rows = 12;

        // Get the list of logo images from the Logos picture library
        // and add them to the listbox.
        SPSite site = SPContext.GetContext(this.Context).Site;
        SPDataSource dataSource = new SPDataSource();
        dataSource.List = site.RootWeb.Lists["Logos"];

        this.listBox.DataSource = dataSource;
        this.listBox.DataTextField = "Title";
        this.listBox.DataValueField = "Name";
        this.listBox.DataBind();

        // Get the current value of the field.
        string currentValue = (string)this.ItemFieldValue;
        if (currentValue != null && currentValue != string.Empty)
        {
            this.listBox.SelectedValue = currentValue;
        }
        else if (this.listBox.Items.Count > 0)
        {
            this.listBox.SelectedIndex = 0;
        }

        // Add the script that updates the preview image when a new
        // item is selected in the lisbox.
        this.listBox.Attributes["onchange"] =
            "document.all.imgLogoPreview.src = '/logos/' + " +
            "this.options[this.selectedIndex].value;";

        cell.Controls.Add(this.listBox);
        row.Cells.Add(cell);
        table.Rows.Add(row);
    }

    cell = new HtmlTableCell();
    LiteralControl literalControl = new LiteralControl();
    string logo = null;
    object logoObject = this.ItemFieldValue;

    if (logoObject != null)
    {
        logo = (string)logoObject;
    }
    if (logo == null || logo == string.Empty)
    {
        logo = this.listBox.SelectedValue;
    }

    literalControl.Text =
        "<img id='imgLogoPreview' src='/logos/" + logo + "'></img>";
    cell.Controls.Add(literalControl);
    row.Cells.Add(cell);
    base.Controls.Add(table);
}

public override void UpdateFieldValueInItem()
{
    this.EnsureChildControls();
    try
    {
        this.Value = this.listBox.SelectedValue;
        this.ItemFieldValue = this.Value;
    }
    catch
    {
        ;
    }
}

protected override void Render(HtmlTextWriter output)
{
    this.table.RenderControl(output);
}

The preceding code assumes that the top-level Web site of the site collection contains a picture library named Logos that contains image files. For the field control to retrieve and display the list of logos, this library must exist and contain image files. For more information about creating picture libraries in Windows SharePoint Services, see Working with SharePoint picture libraries on Microsoft Office Online.

To have a small panoramic view, we can say the custom field types are only:

  • A field type definition (from an .xml).
  • Web user controls (as many .ascx as we need to render the data in the SharePoint web pages).
  • The code behind (from a .dll).

Information field type definition xml:

A field type definition is an XML file named on the pattern fldtypes*.xml that is deployed to the C:\Program Files\Common Files\Microsoft Shared\web server extensions\12\TEMPLATE\XML. The field types that ship with Windows SharePoint Services 3.0 are located in the FLDTYPES.XML file.

A field definition file contains the information that Windows SharePoint Services needs to correctly render the field, including its column header, on a list view page (such as AllItems.aspx). It also typically provides information used to render the field on the view list item page (such as DispForm.aspx).

The name and description of the field type, as it appears on such UI pages as the Customize [list] page, the New Site Column, and the Create Column pages, is also configured in the field type definition. Most importantly, the definition contains information about the assembly that contains the compiled field type.

here is an example of an advancend fielt type definition

Defines the actual Collaborative Application Markup Language (CAML), HTML, and script that Windows SharePoint Services 3.0 can use, as an alternative to a rendering template control (.ascx file), to render the field type in the UI.

here you get more Information

<FieldType>
    <Field Name="TypeName">USAddress</Field>
    <Field Name="ParentType">MultiColumn</Field>
    <Field Name="TypeDisplayName">US Address</Field>
    <Field Name="TypeShortDescription">US Address(12345 NE 123 St. Redmond, WA 98052)
    </Field>
    <Field Name="UserCreatable">TRUE</Field>
    <Field Name="FieldTypeClass">
      AdventureWorks.FieldTypes.USAddressField, AdventureWorks.FieldTypes,
      Version=1.0.0.0,Culture=neutral,PublicKeyToken=90734cc53324b79c
    </Field>
    <PropertySchema>
      <Fields>
        <Field Name="DefaultCity" DisplayName="Default City"
          MaxLength="50" DisplaySize="15" Type="Text">
          <Default>Redmond</Default>
        </Field>
        <Field Name="DefaultState" DisplayName="Default State"
          MaxLength="2" DisplaySize="2" Type="Text">
          <Default>WA</Default>
        </Field>
        <Field Name="DefaultZip" DisplayName="Default Zip" MaxLength="5"
          DisplaySize="5" Type="Text">
          <Default>98052</Default>
        </Field>
      </Fields>
    </PropertySchema>
    <RenderPattern Name="DisplayPattern">
      <Switch>
        <Expr><Column/></Expr>
        <Case Value="">
        </Case>
        <Default>
          <Column SubColumnNumber="0" HTMLEncode="TRUE"/>
          <HTML><![CDATA[<BR>]]></HTML>
          <Column SubColumnNumber="1" HTMLEncode="TRUE"/>
          <HTML><![CDATA[, &nbsp;]]></HTML>
          <Column SubColumnNumber="2" HTMLEncode="TRUE"/>
          <HTML><![CDATA[ &nbsp;]]></HTML>
          <Column SubColumnNumber="3" HTMLEncode="TRUE"/>
          </Default>
      </Switch>
    </RenderPattern>
  </FieldType>

The above example defines a display rendering pattern for a custom field type that inherits from the MultiColumn type. The field is used to store American addresses.

The first subcolumn stores the street address. This is followed by an HTML line break. The next subcolumn stores the city name and it is followed by a comma and a space. The third subcolumn stores the state and, following a space, the last subcolumn stores the postal code. The patterns are very useful if you wanna give each view a custom preparted layout design or different filed access permissions.

here you see the columns from the DisplayPattern

deep dive into the field type xml options in this post

And deploy it, it isn’t much more complicated.

  • Visual Studio Build menu, click Deploy Solution. Visual Studio builds the assembly for the field control and generates the necessary configuration files for the solution’s deployment. It then deploys the solution to the SharePoint site.
  • The field type definition file must to be copied to the server folder “\%Program Files%\Common Files\Microsoft Shared\web server extensions\12\TEMPLATE\XML“.
  • The user controls to “\%Program Files%\Common Files\Microsoft Shared\web server extensions\12\TEMPLATE\CONTROLTEMPLATES“.
  • And the DLL to the GAC. Or if we prefer, because for debugging seems better, we can copy it to the IIS directory “\%Inetpub%\wwwroot\bin“. The only problem of this is that then, the scope of the DLL will be only the scope of this directory, and probably we will not be able to use it in all the sites of a farm.

As easy as that. To the changes take effect it’s only needed to recycle the sites have installed the field, or if we don’t want to think very much, we can just perform an IISRESET.

Summray:

  1. In a text editor, create a CAML field type definition file in \TEMPLATE\XML that specifies the custom field type and control that you created in the previous procedure.
  2. Add the CAML file to Local_Drive:\\Program Files\Common Files\Microsoft Shared\web server extensions\12\TEMPLATE\XML.
  3. At a command prompt, type iisreset to reset Internet Information Services (IIS).
  4. In the root Web site of a site collection, create a picture library named “logos” to contain the image files to use for company logos.
  5. In a view of the list to which you want to add the custom field type, click Settings, and then click Create Column.
  6. On the Create Column page, add the field type to the view, which in the previous example is called My Company Logo.
  7. Edit existing items or create items in the list to specify company logos, which are displayed in all three control modes and in the list view.

The key VS developement steps include:

  1. Creating an empty SharePoint application project in Visual Studio.
  2. Adding a SharePoint field control to the project.
  3. Adding functionality to the field control.
  4. Building and deploying the custom field type to a SharePoint site.
More Introductions:
Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

 
%d bloggers like this: