1

I have created a custom field type that is using an ASCX to control what options are available for editing when viewed in the column settings. For some reason when I create this column, none of my custom values are saved. I was able to get a simpler version working using the PropertySchema settings in the FieldTypes xml file, but as soon as I switched to using an ASCX it stopped saving. Below is how I am attempting to do this, can anyone see what I am doing wrong?

Code behind for my MaskedInputFieldEditor.ascx.cs which is rendered correctly, appears to be trying to save, but does not retain any values entered when re-opened:

public partial class MaskedInputFieldEditor : UserControl, IFieldEditor
{
    protected void Page_Load(object sender, EventArgs e)
    {
    }

    public bool DisplayAsNewSection
    {
        get {return false;}
    }

    public void OnSaveChange(SPField field, bool bNewField)
    {
        MaskedInput customTypedField = (MaskedInput) field;
        customTypedField.Mask = tb_CustomMask.Text;
    }

    public void InitializeWithField(SPField field)
    {
        if (!Page.IsPostBack)
        {
            MaskedInput customTypedField = (MaskedInput)field;
            tb_CustomMask.Text = customTypedField.Mask;
        }
    }
}

When I step through the OnSaveChange code, everything has the appropriate values. Once it leaves the page and I go in to change the column settings all of the values I had entered (and that appeared to save) before, are empty in InitializeWithField. Can anyone see what I am doing wrong here?

1

3 Answers 3

2

I ran into this problem a few weeks ago and I found a very simple solution in the following post from Gunnar:

SharePoint: temporary solution for GetCustomProperty and SetCustomProperty errors

To see it in the context of an entire solution you can grab the source for my SharePoint reCAPTCHA solution from CodePlex: reCAPTCHA for SharePoint

5
  • Good call on Gunnar's post. That was proposed as a solution to my previous question on the matter (link in my comment on the question).
    – Stu Pegg
    Aug 16, 2011 at 13:04
  • 1
    Is this solution still valid for SharePoint 2010 if you are not using the PropertySchema? I was under the impression that the PropertySchema was where the CustomField values were defined. In this article: msdn.microsoft.com/en-us/library/bb802857.aspx they say that an ASCX Editor Control is, An editor control for the variable properties of a field type can be used, as an alternative to a PropertySchema Element (Field Types)... Emphasis on alternative to Aug 16, 2011 at 15:22
  • There are always alternative appoaches, it's a question of what's supported (...this is) and what works best for your specific situation (...this did).
    – Rob D'Oria
    Aug 16, 2011 at 15:40
  • Awesome, this worked. Nice job on reCAPTCHA for SharePoint! Helped a lot having your code to look at. Aug 18, 2011 at 4:57
  • Just to mention: Calling private or internal members can be dangerous, since they may be altered or become unavailable during a service pack or another update of SharePoint.
    – Matthias
    Aug 24, 2011 at 14:58
2

I was also facing this problem and I analyzed with a decompiler tool the creation of a custom field type with an editor control. The problem is that when the new column of your field type is created a new instance is created after setting the property of the field (Mask in your case). That's why your values are getting lost. You can observe this behavior when you debug and put a breakpoint in the Update method of your custom field type. I think, that this is a bug in SharePoint.

I solved this problem by using a static field marked with the ThreadStaticAttribute for the property I want to set in the custom field type class. This solution is a little bit unconventional but it works. I hope this can help you, too.

public class MyField : SPField
{
  [ThreadStatic]
  private static string newFieldMyValue;

  private string myValue;
  public string MyValue
  {
    get { return myValue; }
    set 
    { 
      // the field is new
      if (Id == Guid.Empty)
      {
        newFieldMyValue = value;    
      }
      myValue = value;
    }
  }

  public MyField(SPFieldCollection fields, string fieldName) : base(fields, fieldName)
  {
    Initialize();
  }

  public MyField(SPFieldCollection fields, string typeName, string displayName) : base(fields, typeName, displayName)
  {
    Initialize();
  }

  private void Initialize()
  {
    MyValue = Convert.ToString(GetCustomProperty(myValuePropertyName));
  }

  public override void Update()
  {
    SetCustomProperty(myValuePropertyName, MyValue);
    base.Update();
  }

  public override void OnAdded(SPAddFieldOptions op)
  {
    base.OnAdded(op);

    if (newFieldMyValue != null)
    {
      MyValue = newFieldMyValue;
      newFieldMyValue = null;
    }

    Update();
  }
}
1

Furuknap wrote on this very subject:

Custom Field Type Properties in SharePoint : Buggy or Not?

Essentially, the SPField you get in the OnSaveChange function is discarded at the end of the function. A new one is then created and associated with the list.

@Bender's Thread Local Storage method is mentioned by Furuknap, with more information here:

Creating a Windows SharePoint Services 3.0 Custom Field by Using the EntityPicker

And there's an MSDN Social discussion on the matter here:

Custom Field Type Properties

I've already added a comment to the MSDN documentation, as this is such a common issue:

IFieldEditor.OnSaveChange

2
  • Are these solutions still valid for SharePoint 2010 if you are not using the PropertySchema? I was under the impression that the PropertySchema was where the CustomFields were defined. In this article: msdn.microsoft.com/en-us/library/bb802857.aspx they say that an ASCX Editor Control is, "An editor control for the variable properties of a field type can be used, as an alternative to a PropertySchema Element (Field Types)..." Emphasis on alternative to Aug 16, 2011 at 15:23
  • @Abe: I'm afraid I've only ever used them in tandem myself. Looking at your code a bit closer, it seems the Mask property is your own, rather than being an SPField member. If your custom field class doesn't explicitly store that value somewhere then it'll be lost (even disregarding the OnSaveChange issue).
    – Stu Pegg
    Aug 16, 2011 at 16:19

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.