How to create a custom Infragistics EditableColumn

When I started using Infragistics, I found that there is a lot a developer can do with it, but it also has its limitation. The basics are pretty straight forward and you can do more than you know once you get to understand the concept behind it.

Using it for Warewolf development we ran into a situation where we needed to use the TextColumn in a different editable way. Infragistics XamGrid has two editable behaviors: DateColumn and ComboBoxColumn. I found it strange that the TextColumn is not considered an editable column and so had to ask for a new product to be added.

Infragistics Support

Infragistics Support reply to issues quite fast, but reading through similar issues, we found that they either have a solution or you need to opt for a new product. We had to decide if we could wait for a new product to be added or attempt creating our own, using the default TextColumn to make it work in our way. Their support is great, they get back to you whether they are able to resolve your issue or not. Reading the blog posted on their community blogs, you can see how easy it is to implement it your own way.

Infragistics EditorColumns

Taking a look at the default implementation of the TextColumn, notice that in order to start typing in the TextColumn, you need to click or double click, depending on the setting you applied, to actually edit the text. There is nothing wrong with this approach, but we needed a different option to work for us. (Image taken from Infragistics example).

Infragistics Editors Display Behaviors

 

I could not understand why a TextColumn would not be considered as an always editable column. From my personal point of view, I would not know if I was able to type in a textbox. Let’s look at the implementation.

Setting up the Custom Editable Column

Firstly, create a new TextColumn derived from the EditableColumn. I have changed the naming convention as preference to me and will be referring to a TextBoxColumn. Add an override method and return a new ColumnContentProviderBase.

public class TextBoxColumn : EditableColumn
{
public static readonly DependencyProperty TextBoxProperty =
DependencyProperty.Register("TextBox", typeof(string),
typeof(TextBoxColumn), new PropertyMetadata(null));
public string TextBox
{
get { return (string)GetValue(TextBoxProperty); }
set
{
SetValue(TextBoxProperty, value);
}
}
protected override ColumnContentProviderBase GenerateContentProvider()
{
return new TextColumnContentProvider();
}
}

Creating a Custom ColumnContentProviderBase

As mentioned in their blog,

The ColumnContentProviderBase exposes a number of virtual methods that the grid calls when it needs IU content for a columns cells or needs to resolve a value from an editable cell’.

I suggest using a break point in this section to understand the concept behind it, as this helped me understand.

public class TextColumnContentProvider : ColumnContentProviderBase
{
TextBox _textBox;
 
public override void AdjustDisplayElement(Cell cell)
{
_textBox.Width = cell.Column.ActualWidth;
_textBox.Height = cell.Row.MinimumRowHeightResolved;
base.AdjustDisplayElement(cell);
}
 
public TextColumnContentProvider()
{
_textBox = new TextBox();
_textBox.Style = Application.Current.TryFindResource("TextBoxStyle") as Style;
}
 
public override bool RemovePaddingDuringEditing {
get { return true; }
}
 
public override FrameworkElement ResolveDisplayElement(Cell cell, Binding cellBinding)
{
TextBoxColumn column = (TextBoxColumn) cell.Column;
 
cell.Control.Padding = new Thickness();
cell.Control.Cell.Control.Padding = new Thickness();
this._textBox.SetValue(TextBox.TextBoxProperty, column.TextBox);
this._textBox.SetBinding(TextBox.TextProperty, cellBinding);
_textBox.Width = cell.Column.ActualWidth;
_textBox.Height = cell.Row.MinimumRowHeightResolved;
return _textBox;
}
 
protected override FrameworkElement ResolveEditorControl(Cell cell, object editorValue, double availableWidth, double availableHeight, Binding editorBinding)
{
if (editorValue != null) this._textBox.Text = editorValue.ToString();
return this._textBox;
}
 
public override object ResolveValueFromEditor(Cell cell)
{
return _textBox.Text;
}
}

Override the Columns Display Element

If you add a break point in and follow the Cell style, you will notice the cell gives you all the properties needed to display your control. Creating a textbox, you need to set the textbox width to the Cell Column ActualWidth, and textbox height to Row MinimumRowHeightResolved. Add margins in this section if you want the textbox to display on its own. Since we are creating a new TextBox, there is no style implemented at this point, so we call the style at this point inside the constructor. One thing to note at this point is that the AdjustDisplayElement occurs from a load perspective, and the ResolveDisplayElement occurs when there are changes to the column.

Frontend Implementation

Let’s take a look at the Infragistics implementation to use the TextColumn and compare it to our own TextBoxColumn. The two are identical in the sense that it does exactly the same. The difference is that we can resolve the display elements to suit our needs, and not have all the default settings that come along with the Infragistics controls.

<ig:XamGrid.Columns>
<ig:TextColumn Key="Name" HeaderText="Name"></ig:TextColumn>
<ig:TextColumn Key="Value" HeaderText="Value"></ig:TextColumn>
</ig:XamGrid.Columns>
 
<ig:XamGrid.Columns>
<xamGrid:TextBoxColumn Key="Name" HeaderText="Name"></xamGrid:TextBoxColumn>
<xamGrid:TextBoxColumn Key="Value" HeaderText="Value"></xamGrid:TextBoxColumn>
</ig:XamGrid.Columns>

Conclusion

The end result we got was to show the textbox as an input field, instead of the user not knowing whether the field can be edited or not. Infragistics is powerful on its own, but if you run into a situation where you cannot find a solution and cannot wait for a new product to be added; there are ways to make it work for you.

If you would like to see our implementation, come check out the Warewolf project in GitHub.

FacebookTwitterLinkedInGoogle+RedditEmail

1 Comment

  1. Brian

    A powerful share, I just given this onto a cogeallue who was doing just a little evaluation on this. And he in actual fact bought me breakfast because I found it for him.. smile. So let me reword that: Thnx for the treat! But yeah Thnkx for spending the time to discuss this, I really feel strongly about it and love studying more on this topic. If potential, as you turn into experience, would you mind updating your weblog with extra details? It’s extremely helpful for me. Big thumb up for this blog post!

Leave A Comment?