SurfRay

Home Tech Blog Tech Talk Creating a custom field in SharePoint

Creating a custom field in SharePoint

E-mail Print PDF

In this post I will show how to create a new list field for storing data in a SharePoint list. There are a number of reasons to use custom fields, which includes storing custom objects in a type safe way and storing long lists where performance is essential.

Even though there exist easier ways to implement the functionality described in this post, the methods used is hoped to be useful for people creating their own custom fields.

Defining the problem

Let us imagine that a school consisting of a number of classes hires us to create a custom field which should store names and birthdays of students in a single class. The school will then have the possibility to create a list where one field identifies the class and the other field stores all the students’ names and birthdays.

Design

As we need to put all the student’s names and birthdays in one field, we need to create a custom field.

The most logical structure would be to store a list of object, where each object has name and birthday information. Then we can serialize the list with the normal XmlSerializer.

As we need to store a xml string the obvious choice is to base our field on either SPFieldText or SPFieldMultiLineText. As SPFieldText is limited to store 255 characters, the choice is obvious SPFieldMultiLineText.

Creating the solution and the project

If you do not already have the SharePoint add in for Visual Studio, download and install it.

Create a new empty SharePoint solution, by going to File -> New … -> New Project. Navigate to Visual C# -> SharePoint in the left pane. Choose the Empty template. Name it StudentField.

Right click the StudentField project and click Add New Item … Select the SharePoint category and select FieldControl. Name it StudentField.

Visual studio has created three files:

StudentField.Field.cs

This class contains the logic for storing our data

StudentField.FieldControl.cs

This class implements the web control used on the list for our field

fldtypes_StudentField.xml

This file contains overall properties of the field.

 

fldtypes_StudentField.xml

When opening the fldtypes_StudenField.xml, it will be a skeleton file. Right click the project file and choose Package. This will put values into the file:

 

StudentFieldField

StudentFieldField

StudentFieldField

Text

TRUE

56aa082b-0449-48ca-9bf1-b737700ba4ba

Notice the ParentType element; this needs to be changed from Text to Note as we will have a string longer than 255 characters. Also Change the TypeDisplayName to a friendly name.

StudentField.Field.cs

This file contains the class that controls the logic behind the scenes.

Again as we expect to have long strings change the inheritance so that the class inherits from to SPFieldMultiLineText.

GetValidatedString

This method contains the logic for serializing the data into Xml. When this is done SharePoint will take care of persisting the string returned to the database.

Let us start by looking at the code for GetValidatedString:

public override string GetValidatedString(object value)

{

List objectToSave = value as List;

 

if (objectToSave == null) throw new InvalidCastException(

string.Format("This field can only save objects of type {0}",

typeof(List).ToString()));

 

MemoryStream memoryStream = new MemoryStream();

XmlSerializer serializer = new XmlSerializer(typeof(List));

 

string xmlRepresentation = null;

 

try

{

serializer.Serialize(memoryStream, objectToSave);

memoryStream.Flush();

memoryStream.Position = 0;

StreamReader reader = new StreamReader(memoryStream);

xmlRepresentation = reader.ReadToEnd();

}

catch (Exception)

{ }

 

return xmlRepresentation;

}

This method will be called by the object to be persisted, in this case a string list. This is straight forward, using a XmlSerializer to serialize the data. Remark, that as we need a temporary stream we use a memory stream.

If the object passed to this method is not an implementation of the correct class, we will throw an exception.

GetFieldData

This method takes a string with the serialized data, and returns a deserialized object. Let’s jump right into the code:

public override object GetFieldValue(string value)

{

List students = null;

 

XmlSerializer serializer = new XmlSerializer(typeof(List));

 

MemoryStream memoryStream = new

MemoryStream(Encoding.Default.GetBytes(value));

 

try

{

students = (List)serializer.Deserialize(memoryStream);

}

catch (Exception)

{ }

 

return students;

}

This is straight forward; the only thing to notice is that a memory stream is used as temporary stream. Notice that an exception is thrown if the data passed to this method cannot be deserialized.

StudentField.Field.cs

This file contains a class that implements the web controls used to render the field in the list. An implementation will be shown in part 2 of this blog: for now we will just show the xml string:

public class StudentFieldFieldControl : BaseFieldControl

{

protected List _students = null;

public override object Value

{

get { return _students; }

set { _students = value as List; }

}

}

Student.cs

The student class is defined as follows:

public class Student

{

private string _name = null;

public string Name

{

get { return _name; }

set { _name = value; }

}

 

private DateTime _birthDay = DateTime.MinValue;

public DateTime BirthDay

{

get { return _birthDay; }

set { _birthDay = value; }

}

 

public Student()

{ }

 

public Student(String name, DateTime birthday)

{

_name = name;

_birthDay = birthday;

}

}

 

Using the field

I will briefly describe how to use this column from code.

Creating a new column

First create a Custom list named “MyList” (or use an existing list), then go to Settings -> Create Column. Set the Column name to “MyTestColumn” and select SurfRay Custom field as the type. Add it to the default view.

Now you can see that there is an extra column in your list.

Accessing the field from an application

Using the field from code is quite easy, as an example there is a sample windows application (which can be run from any Web front-end. The two things to notice are how to get data from the field:

SPList list = (new SPSite(_siteCollectionUrl)).RootWeb.Lists["MyList"];

 

foreach (SPListItem item in list.Items)

{

_students = item["MyColumn"] as List;

}

Here we are just taking the MyColumn field from the last row.

And how to put data into the field:

protected void SaveToList()

{

SPList list = (new SPSite(_siteCollectionUrl)).RootWeb.Lists["MyList"];

 

SPListItemCollection items = list.Items;

SPListItem itemToUpdate = null;

 

foreach (SPListItem item in items)

{

if (item["Title"].ToString() == _classTitle)

itemToUpdate = item;

}

 

if (itemToUpdate == null)

{

itemToUpdate = items.Add();

itemToUpdate["Title"] = _classTitle;

itemToUpdate["MyColumn"] = _students;

itemToUpdate.Update();

}

else

{

itemToUpdate["MyColumn"] = _students;

itemToUpdate.Update();

}

}

Here we are opening the RootWeb of a site collection on the url defined in the _siteCollectionUrl. We then try to find the item with the correct class name (_classTitle). If we did not find it we create a new row, else we are updating the row. Remember to call itemToUpdate.Update(), as this will commit the changes to the database.

 
Get Trial
Get Price Quote

Upgrading Ontolica 4.0 to Ontolica 2010

SurfRay’s commitment is to provide the best possible search solution for SharePoint. By continuing to refine our software and deliver improvements that delight and enable...

More:

How to index PDF files in SharePoint

Microsoft SharePoint does not index Adobe PDF files by default. Hence, additional steps are required to enable and perform indexing, to be able to search for the content ...
More: