in SharePoint, SharePoint 2007

SharePoint: Creating a custom field

In SharePoint, a site column is a reusable column definition, or template, that you can assign to multiple lists across multiple SharePoint sites. Site columns are associated to a particular Data Type. This Data Type is called a Field. For example, when you create a site column, you are also prompted to select the type of information, which is nothing but a Data Type or a Field.

creating-site-column

Sometimes, it is necessary for us to create our own custom field that does not conform to the field types included in SharePoint by default. Something like this:

custom-field-site-column

How do we do that?

All you have to do is – create a custom field which would result in creating a Field Class, Field Control and Field Type Definitions

image

The Field Class should inherit from any of the SPField classes shown above in the diagram.

The Field Control should have Field Rendering Control and a Field Rendering Template.

The Field Type Definitions is a XML file which contains some information about the custom field.

Custom Field Class – CustomField

Below is a custom field class which inherits SPFieldChoice

public class CustomField : SPFieldChoice
{
    public CustomField(SPFieldCollection fields, string fieldName) :

                                                                    base(fields, fieldName) { }

    public CustomField(SPFieldCollection fields, string typeName, string displayName) :

                                                                    base(fields, typeName, displayName) { }

    public override BaseFieldControl FieldRenderingControl

    {
        get
        {
            BaseFieldControl fieldControl = new CustomFieldControl();
            fieldControl.FieldName = InternalName; return fieldControl;
        }
    }
}

As you can see in the above code, it does nothing but creates a custom field control to render our custom field.

Field Rendering Template – CustomFieldControl.ascx

<SharePoint:RenderingTemplate Id="CustomFieldTemplate" runat="server" >    
    <Template> 
        <asp:CheckBox ID="YesNoCheckBox" runat="server"  Text="Yes/No" />    
    </Template>
</SharePoint:RenderingTemplate>

This is going to render a simple ASP.NET CheckBox

 Field Rendering Control – CustomFieldControl.cs

The name of the field rendering control should be same as the name of the field rendering template(ascx) name and must inherit from BaseFieldControl.

public class CustomFieldControl : BaseFieldControl
{
#region Member Variables
protected CheckBox YesNoCheckBox;
private string _value;
#endregion
#region Overridden Methods
#endregion
#region Private Methods
#endregion
}

The basic template(with our example’s member variables) code block is shown above. The member variables are nothing but the controls that we created in the field rendering template.

The field control class can be considered as the code behind for the field rendering template.

To make our custom field work, we first need to render the template and display our checkbox.

#region Overridden Methods
protected override void CreateChildControls()
{
if (Field == null && this.ControlMode == SPControlMode.Display)
{   return;  }
base.CreateChildControls();
FindDisplayControle();
}
#endregion
#region Private Methods
private void FindDisplayControle()
{
YesNoCheckBox = (CheckBox)TemplateContainer.
FindControl(DefaultValues.YesNoCheckBoxName);
if (DisplayLiteral == null || YesNoCheckBox == null)
throw new ConfigurationErrorsException("Error: Cannot load the controls!");
}
#endregion

The code block finds the checkbox from our template container (field rendering template).

So, how is the value persisted?

We do that ‘magic’ by overriding the Value property

#region Overridden Methods
public override object Value
{
get
{
EnsureChildControls();
SetValue();
return _value;
}
set
{
EnsureChildControls();
_value = value.ToString();
LoadCheckBox();
}
}
#endregion
#region Private Methods
private void LoadCheckBox()
{
if(!string.IsNullOrEmpty(_value))
{
YesNoCheckBox.Checked = _value=="Yes";
}
}
private void SetValue()
{
_value = YesNoCheckBox.Checked ? "Yes" : "No";
}
#endregion

Looks very simple, isn’t it 🙂

One last thing to do is to tell SharePoint our default template name and display template name, which is nothing but the name of our field rendering template

#region Overridden Methods
protected override string DefaultTemplateName
{
get
{
return DefaultValues.RenderingTemplateName;
}
}
public override string DisplayTemplateName
{
get
{
return DefaultValues.RenderingTemplateName;
}
}
#endregion

Field Type Definitions – fldtypes_<custom-field>.xml

We now need to create a field type definition. The field type definition file is an XML file whose name is prefixed by fldtypes_ followed by a name. It is important that we follow this convention. Our field type definition for our custom field is called as fldtypes_customfield.xml

<fieldtypes>
<FieldType>
<Field Name="TypeName">CustomField</Field>
<Field Name="TypeDisplayName">Custom Field</Field>
<Field Name="TypeShortDescription">Custom field</Field>
<Field Name="ParentType">Note</Field>
<Field Name="FieldTypeClass">Chaks.Samples.SharePoint.CustomField,
Chaks.Samples, Version=1.0.0.0,
Culture=neutral,
PublicKeyToken=****************
</Field>
<Field Name="UserCreatable">TRUE</Field>
</FieldType>
</fieldtypes>

You can read more about custom field type definitions here

 

Deploying

1) Place the .dll into the GAC

2) Copy the fldtypes_customfield.xml into 12hive->TEMPLATE->XML

2) Copy the CustomFieldControl.ascx into 12hive->TEMPLATE->CONTROLTEMPLATES

( It is always recommended to use STSDEV or WspBuilder for SharePoint projects. That makes your deployment (and development) very easy )

You can download the files below:

 

Write a Comment

Comment

Time limit is exhausted. Please reload the CAPTCHA.

  1. how to create a custom field with a custom editor to get properties from the user while creating the column? Do you’ve any example for that?

    Regards
    Raghavendra

  2. Could be great article if it would be possible to find source files somewhere. Otherwise I can’t make this code work.

    Regards,
    Ugis