Defining Columns for a Silverlight DataGrid
This post has been updated to work with the RTW version of the Silverlight 2 DataGrid. The code examples are not guaranteed to work with previous Beta versions of the DataGrid. Read more about the features that the Silverlight 2 DataGrid has to offer... |
If you read my last post, you might have noticed how easy it is to get a Silverlight DataGrid up and running with the AutoGenerateColumns feature. Something else you might have noticed is that if you don't like the default column choices it is sort of hard to change them. Not to fear however since there are two ways to get more control. One way is to use the AutoGeneratingColumn event (we'll talk about this in a different post) but the easiest way, and the topic of our discussion today, is by using the Columns collection.
The Columns Collection and You
The Columns Collection is your ticket to controlling the DataGrid's column order, appearance, and even what controls they use to represent data in their cells. It enables you to have a concrete instance for each column that you define unlike auto generation that simply fills the column collection for you.
Before we dive into using the Columns collection though, it is useful to know what you can put in it.
DataGrid Column Types
- DataGridTextColumn - When you think of a standard column in a DataGrid, you probably picture something that looks a lot like a DataGridTextColumn. This column is the default and uses a TextBlock to display its data, and a TextBox to allow editing of its data.
- DataGridCheckBoxColumn - The DataGridCheckBoxColumn is the first out of box custom column type. It provides a read-only CheckBox for displaying a boolean or nullable boolean value, and a normal CheckBox to allow editing of that value. This column derives from DataGridBoundColumn and serves as a sample for building your own column types. We'll walk through the process of building your own column types in a future post.
- DataGridTemplateColumn - If the DataGrid was a movie, the DataGridTemplateColumn would be the star. It is the most versatile column but, like most prima donnas, takes the most work to get up and going. Once it is going though there is pretty much no limit to what it can do.
Using the Columns Collection
First we need to get our project back to where we ended last time. Go ahead and follow the steps 1 and 2 here.
If you followed steps 1 & 2 from the previous post, your DataGrid should look something like this:
<data:DataGrid x:Name="dg"></data:DataGrid>
(If yours looks different because you did step 3, don't worry since it won't affect this walk through. The one exception is that you need to change IsReadOnly back to False.)
Also, in the code behind file for Page.xaml you should be setting the source to a List<Data> where Data is the custom business object you created.
Now that we are all on the same page lets start playing with the Column collection.
Since auto generation is no longer needed, go ahead and set AutoGenerateColumns to False.
<data:DataGrid x:Name="dg" AutoGenerateColumns="False"></data:DataGrid>
Now add the Columns collection, and add a Text column in it bound to the "FirstName" property.
<data:DataGrid x:Name="dg" AutoGenerateColumns="False">
<data:DataGrid.Columns>
<data:DataGridTextColumn Header="First Name"
Binding="{Binding FirstName}" />
</data:DataGrid.Columns>
</data:DataGrid>
The code above is doing a few things:
- It creates the Columns collection using the <data:DataGrid.Columns> tag.
- Inside that collection it creates a new DataGridTextColumn
- The content that you see in the column header is set to "First Name" using the Header property
- The column is data bound to the FirstName property using the Binding property. Notice that since the DataContext of the DataGrid is its ItemsSource collection a Source does not need to be specified.
Side Note: Some of you might be wondering why we use Binding here instead of a string like DisplayMemberPath. The thinking behind this decision was that a binding gives you a lot more control of what ends up being shown. It allows the use of converters, and leaves the door open for the addition of validation, and formatters.
If you run this you should see something like this:
In addition to the Header and Binding properties, you can also customize the column through properties such as:
Column Properties:
- CanUserResize - Determines if this column can be resized. In regards to its relationship with the DataGrid property CanUserResizeColumns, false always wins.
- CanUserReorder - Determines if this column can be reordered with other columns. In regards to its relationship with the DataGrid property CanUserReorderColumns, false always wins.
- CanUserSort - Determines if this column can be sorted. In regards to its relationship with the DataGrid property CanUserSortColumns, false always wins.
- IsReadOnly - Determines if this column can be edited. In regards to its relationship with the DataGrid property IsReadOnly, true always wins.
- Width - Sets the width of the column. Setting this value overrides the DataGrid ColumnWidth property.
- MinWidth - Sets the minimum width for this column.
- Visibility - Hides or shows this column
- ElementStyle - The property used to style the display element for a column. (In the case of the TextBox Column the display element is the TextBlock)
- EditingElementStyle - The property used to style the editing element for a column. (In the case of the TextBox Column the display element is the TextBox)
TextBox Column Specific Properties:
- FontFamily - Sets the FontFamily property on both the TextBlock and TextBox.
- FontSize - Sets the FontSize property on both the TextBlock and TextBox.
- FontStyle - Sets the FontStyle property on both the TextBlock and TextBox.
- FontWeight - Sets the FontWeight property on both the TextBlock and TextBox.
- Foreground - Sets the Foreground property on both the TextBlock and TextBox.
CheckBox Column Specific Properties:
- IsThreeState - Sets the IsThreeState property on the CheckBoxes
Lets now finish off the columns that we used to have by adding two more DataGridTextBoxColumns and a DataGridCheckBoxColumn bound to "LastName", "Age", and "Available".
<data:DataGrid x:Name="dg" AutoGenerateColumns="False" >
<data:DataGrid.Columns>
<data:DataGridTextColumn Header="First Name"
Binding="{Binding FirstName}" />
<data:DataGridTextColumn Header="Last Name"
Binding="{Binding LastName}" />
<data:DataGridTextColumn Header="Age" Width="50"
Binding="{Binding Age}" />
<data:DataGridCheckBoxColumn Header="Available"
Binding="{Binding Available}" />
</data:DataGrid.Columns>
</data:DataGrid>
Now when you run the application you have the same output as the auto generation, except now you control the order, what the header says, and you can set properties. For instance in the code above the width of the Age column is set to 50 instead of the usual Auto.
Unleashing the Template Column
Now that we have recreated the auto generated DataGrid from before let's add some new functionality, specifically a column that can be bound to a DateTime. To do this we can either create a new column type, or just use a template column. Since we only plan on using this column once, let's use a template column.
First let's add something for this column to bind to. Going back to your Data class, add the following property:
C#
public DateTime Birthday{ get; set; }
VB
Private _birthday As DateTime
Property Birthday() As DateTime
Get
Return _birthday
End Get
Set(ByVal value As DateTime)
_birthday = value
End Set
End Property
Also we need to update the Page.xaml code behind to initialize the new property:
C#
public Page()
{
InitializeComponent();
List<Data> source = new List<Data>();
int itemsCount = 100;
for (int i = 0; i < itemsCount; i++)
{
source.Add(new Data()
{
FirstName = "First",
LastName = "Last",
Age = i,
Available = i % 2 == 0 ,
Birthday = DateTime.Today.AddYears(-i)
});
}
dg.ItemsSource = source;
}
Public Sub New()
InitializeComponent()
Dim Source As List(Of Data) = New List(Of Data)
Dim ItemsCount As Integer = 100
For index As Integer = 1 To ItemsCount
Source.Add(New Data() With _
{ _
.FirstName = "First", _
.LastName = "Last", _
.Age = index, _
.Available = (index Mod 2 = 0) , _
.Birthday = DateTime.Today.AddYears(-index) _
})
Next
dg.ItemsSource = Source
End Sub
Now that the data is there we can bind to it. Going back to the Page.xaml file add a DataGridTemplateColumn to the Columns collection right after the "Available" column.
xmlns:basics="clr-namespace:System.Windows.Controls;
assembly=System.Windows.Controls"
<data:DataGrid x:Name="dg" AutoGenerateColumns="False" >
<data:DataGrid.Columns>
<data:DataGridTextColumn Header="First Name"
Binding="{Binding FirstName}" />
<data:DataGridTextColumn Header="Last Name"
Binding="{Binding LastName}" />
<data:DataGridTextColumn Header="Age" Width="50"
Binding="{Binding Age}" />
<data:DataGridCheckBoxColumn Header="Available"
Binding="{Binding Available}" />
<data:DataGridTemplateColumn Header="Birthday">
<data:DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding Birthday}" Margin="4"/>
</DataTemplate>
</data:DataGridTemplateColumn.CellTemplate>
<data:DataGridTemplateColumn.CellEditingTemplate>
<DataTemplate>
<basics:DatePicker
SelectedDate="{Binding Birthday, Mode=TwoWay}" />
</DataTemplate>
</data:DataGridTemplateColumn.CellEditingTemplate>
</data:DataGridTemplateColumn>
</data:DataGrid.Columns>
</data:DataGrid>
Warning: Be sure to add the DatePicker from the ToolBox so the basics namespace and associated reference to System.Windows.Controls is added for you.
What's going on in the code above:
- A DataGridTemplateColumn is being added to the Columns collection with its header being set to "Birthday".
- The CellTemplate property, which takes a DataTemplate, is being used to define the UI that cells in the column will use to display the data.
- In this instance, the content of that DataTemplate is a TextBlock that has its Text property bound to the "Birthday" property on the Data Item. Once again notice that no binding source is necessary since the default DataContext of a Template column's contents is the data item that it will be representing.
- In addition to the CellTemplate the DataGridTemplateColumn's CellEditingTemplate property is also being set. This property is also a DataTemplate and defines the UI that cells in the column will display during edit mode.
- In this instance, the content of the CellEditingTemplate's DataTemplate is a DatePicker control that has its SelectedDate property also bound to the "Birthday" property.
- Notice that its binding has the Mode property set to TwoWay. This is crucial to make sure that any changes made to this property at runtime will be pushed back into the data source. Note that you do not need to set the Mode when you are using the DisplayMemberBinding property in column types other than DataGridTemplateColumn because the columns themselves take care of this.
When you run this you should see a new column in your DataGrid that uses a TextBlock to display a date, and then switches to a DatePicker during edit mode to provide a richer input experience.
(If your DataGrid still has all of the properties set from Step 3 of the last post you need to set IsReadOnly back to False if you want to be able to see the DatePicker in edit mode)
Using Value Converters
This column is pretty much exactly what we want, but there is a finishing touch missing. If you look at the text, it has an annoying 12:00:00 AM after each date. Since we only care about the date itself and not the time, let's reformat this string to the short date format that matches what is shown in the DatePicker.
Add a new class to your Silverlight project and name it "DateTimeConverter". Then add:
C#
using System.Windows.Data;
using System.Globalization;
public class DateTimeConverter: IValueConverter
{
public object Convert(object value,
Type targetType,
object parameter,
CultureInfo culture)
{
DateTime date = (DateTime)value;
return date.ToShortDateString();
}
public object ConvertBack(object value,
Type targetType,
object parameter,
CultureInfo culture)
{
string strValue = value.ToString();
DateTime resultDateTime;
if (DateTime.TryParse(strValue, out resultDateTime))
{
return resultDateTime;
}
return value;
}
}
VB
Imports System.Windows.Data
Public Class DateTimeConverter
Implements IValueConverter
Public Function Convert(ByVal value As Object, _
ByVal targetType As System.Type, _
ByVal parameter As Object, _
ByVal culture As System.Globalization.CultureInfo) _
As Object _
Implements System.Windows.Data.IValueConverter.Convert
Dim DateValue As DateTime = value
Return DateValue.ToShortDateString()
End Function
Public Function ConvertBack(ByVal value As Object, _
ByVal targetType As System.Type, _
ByVal parameter As Object, _
ByVal culture As System.Globalization.CultureInfo) _
As Object _
Implements System.Windows.Data.IValueConverter.ConvertBack
Dim StrValue As String = value.ToString()
Dim ResultDateTime As DateTime
If DateTime.TryParse(StrValue, ResultDateTime) Then
Return ResultDateTime
End If
Return value
End Function
End Class
If you look at the code, a converter is a class that implements IValueConverter and as part of that provides two methods: Convert and ConvertBack. These two methods are where you can perform your custom logic, in this case parsing a DateTime to and from a short date string format.
Now that you have your reusable converter class you can use it in data binding.
Back in your Page.xaml add a local xmlns. To do this add the following in the UserControl tag next to the other xmlns declarations:
xmlns:local="clr-namespace:_____________"
Where the _________ is the name of your Application. IntelliSense should provide the correct syntax as an option in the dropdown. Next add the converter to your UserControl as a static resource.
<UserControl.Resources>
<local:DateTimeConverter x:Key="DateConverter" />
</UserControl.Resources>
Finally use the converter in the TextBox's binding in the DataGridTemplateColumn.
<TextBlock
Text="{Binding Birthday, Converter={StaticResource DateConverter}}"
Margin="4"/>
Now when you run the application, the text will be formatted in the manner that the converter specified.
Comments
Anonymous
March 27, 2008
This might be a little off-topic... Does the Silverlight DataGrid supports group headers? i.e. a cell above a determined number of headers that spans the combined width of the headers it groups together. When one of the headers in the group is resized, the group header follows and adapts itself to the new "combined width". Thanks in advance!Anonymous
March 27, 2008
Hi Scott, Nice post you have here, I'am waiting for your next post using "RowDetailsTemplate" , I am personally having difficulty to get reference control in <DataTemplate> under <RowDetailsTemplate> where I can use somewhere in my code Thanks for your attention
- Malky
Anonymous
March 27, 2008
The comment has been removedAnonymous
March 29, 2008
Scott Guthrie lists a number of posts and videos about the Silverlight 2.0 DataGrid in March 28th LinksAnonymous
March 30, 2008
Dan Wahlin's latest articles, Cheryl at Silverlight SDK on SL2, WS, and WCF, Sam Landstrom on usingAnonymous
March 31, 2008
Very nice article. However, it and nearly every other article or blog entry I have seen concerning the DataGrid, as well as ALL the documentation, assume that you will be constructing your grid in XAML. My experience in the industry is that I am far more likely to need to create one dynamically. Could you provide some examples of that? I just finished importing your source code and altering it in order to solve a problem of mine, it was so bad. I could sure use some examples.
- Jody
Anonymous
April 01, 2008
If you read my <a href="http://blogs.msdn.com/sAnonymous
April 01, 2008
I'll be using this page to link to Silverlight 2 articles and posts (both ones I write as well ones byAnonymous
April 14, 2008
Now that you know the basics of the Silverlight DataGrid and how to specify the Columns in XAML , youAnonymous
April 21, 2008
Great post/series. Thank you. Any thoughts on how I can conditionally format some columns, like positive numbers in green and negative numbers in red. Thanks again for great posts.Anonymous
April 21, 2008
Hi Vinod, You can coditionally format the contents of your columns by using a converter. To do this you would need to use a template column (for beta 1) since you cannot databind to properties on DataGridColumns just yet. What you are going to want to do is databind the property you want to conditionally change, probably in your case either the Foreground or Background property, to the value with a converter that takes positive numbers and returns a green Brush, and negative numbers and returns a red Brush. Hope this helps! -ScottAnonymous
April 21, 2008
Scott, It works great (data binding the property) Thanks for your help.
- Vinod
Anonymous
May 20, 2008
NowthatyouknowthebasicsoftheSilverlightDataGridandhowtospecifytheColumnsinXAML,you...Anonymous
May 21, 2008
Like many others, I jumped on to Silverlight 2.0 to create an internal application for my company. But, I couldn't produce an useful app since there is no Combobox control I can use in a DataGrid column. There are some examples in the web using Javascript or combining it with a textbox, button and listbox. I need a column in the Datagrid to have Combobox, like WinForm datagrid. It is disappointing hvaing the combobox control.Anonymous
May 30, 2008
Hi Kumar, I can't comment on the status of a first party ComboBox, however if you are able to find a control that serves your purposes, you can create a ComboBox column using a template column. If instead you want to pair up a ListBox, Button, PopUp, and TextBox you can do that as well since even though my sample above only has a single DatePicker in the template, you can use any DataTemplate as complicated as you want to define the contents of a cell. Hope this helps. -ScottAnonymous
June 04, 2008
DefiningColumnsforaSilverlightDataGridAnonymous
June 04, 2008
DefiningSilverlightDataGridColumnsatRuntime NowthatyouknowthebasicsoftheSilverlightD...Anonymous
June 06, 2008
Hi, If i add some editable control to CellEditingTemplate (for example WatermarkedTextBox), after entering "Edit mode" focus is not on my editable control, and i have to click on this control to edit. Is there any solution to make editable control focused after entering cell in edit mode?Anonymous
June 10, 2008
Hi Scott, Using the great reply you gave to Vinod, I've had a colour coded cell working in a datagrid using a converter returning one of six brushes when given a number (0 - 5). Worked/looked great in beta 1 but, having moved to beta 2 it's now failing during the page InitializeComponent LoadComponent with a method access exception on the converter module (called ColourAlerts) with System.MethodAccessException: Tams.ColourAlerts..ctor() at System. Reflection. MethodBase. PerformSecurityCheck I've gone through the beta 2 datagrid breaking changes but can't see any relevant details on this. If you have any info' on why I'm getting this fault it would be much appreciated. thanks, PhilAnonymous
June 15, 2008
The comment has been removedAnonymous
June 19, 2008
Hi, I´m using this tutorial to create and populate a datagrid in silverlight beta 2, but when the grid is populated with the columns defined in the xaml file and with autogenerate columns set to false, I get all the rows but no values. If I don´t define de columns and set autogenerate columns to true everything works fine. Any ideia why this is happening?Anonymous
June 20, 2008
how to change styles of column values at runtime depending upon some condition like one column which contains checkbox if checkbox is checked style of row should be changedAnonymous
June 27, 2008
Excellent post, I was not able to find how to setup the two way binding. One thing... if we add an element to the entity list associated, do we need to rebind the datasource? or the Datagrid is smart enough to detect the change and refresh the grid displayed?Anonymous
July 03, 2008
Scott, I can see how IValueConverter can be useful in certain escenarios, but most of the time using a FormString would be easier, in your example we could specify a formatString of "d" I dont know if there's something like that in SL or WPF. I did a trick to do something similar using ValueConverters, it work fine, but I think there should be a sexier solution. Here's the XAML. <UserControl.Resources> <local:StringFormatConverter x:Name="stringFormatter"/> </UserControl.Resources> <StackPanel Orientation="Vertical"> <StackPanel.DataContext> <SilverlightApplication3:Person/> </StackPanel.DataContext> <TextBlock HorizontalAlignment="Left" VerticalAlignment="Top" Text="{Binding Mode=OneWay, Path=Name}" TextWrapping="Wrap"/> <TextBlock HorizontalAlignment="Left" VerticalAlignment="Top" Text="{Binding Mode=OneWay, Path=LastName}" TextWrapping="Wrap"/> <TextBlock HorizontalAlignment="Left" VerticalAlignment="Top" Text='{Binding Mode=OneWay, Path=DOB, Converter={StaticResource stringFormatter}, ConverterParameter="d"}' TextWrapping="Wrap"/> <TextBlock HorizontalAlignment="Left" VerticalAlignment="Top" Text='{Binding Mode=OneWay, Path=Age, Converter={StaticResource stringFormatter}, ConverterParameter="c"}' TextWrapping="Wrap"/> <TextBlock HorizontalAlignment="Left" VerticalAlignment="Top" Text='{Binding Mode=OneWay, Path=AnualIncome, Converter={StaticResource stringFormatter}, ConverterParameter="0.00"}' TextWrapping="Wrap"/> </StackPanel> Here's de Code public class StringFormatConverter:IValueConverter { #region IValueConverter Members public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) { string formatString = parameter.ToString(); return String.Format("{0:" + formatString + "}", value); } public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) { throw new InvalidOperationException("This Convert supports only OneWay binding"); } #endregion }Anonymous
September 16, 2008
Great post! Coming from WPF apps using ListView, I'm struggling with customizing the silverlight datagrid. One thing that I frequently use in WPF standalone app, and XBAP is the ValueConverter. In this case to give back an image path for showing an image in one of the columns in the datagrid. But when scrolling the datagrid the images are lost forever once they're scrolled out of view, not until the datagrid i refreshed again the images are shown. It seems the virtulization isn't working properly. I'm currently using VS2008sp1,FW 3.5SP1,Blend 2 June preview and downloaded the SilverLight 2.0 Beta 2 for VS. Any ideas?Anonymous
October 14, 2008
As you might have heard , we just released Silverlight 2 , and with it the first version of the SilverlightAnonymous
October 23, 2008
I am having a hard time with the DataGrid and its Template Column. The problem is that I don't know until runtime what property in my datasource to bind to because that is driven by some configuration data that I read up. I have no problem doing this with a DataGridTextColumn since that class offers a Binding property that I can set at runtime but I need to use the Template column since I want to provide a richer UI then just a text string. The Template column doesn't have the Binding property so I would need to specify my binding at design time in Xaml...and that is too early for me. The only way around this seems to have the datatemplate stored as a string, do some type of string substition of that string and then load it as a datatemplate. This doesn't sound like the best idea to me...I would like to keeep my datatemplate/styles in Xaml files so that they can be worked on by my designer in Blend. Is there any other direction that you could point me to? Thanks, PeterAnonymous
October 29, 2008
i'm having a devil of a time with the release version of Silverlight 2.0 defining my DataGrid header information (styling the header row so that it has a particular color/font/etc.) as well as the hover over row treatment and the selection treatment. do you have a definitive guide on how to change these key elements? Should I shell into Blend and edit a control template there and play around or what??Anonymous
December 04, 2008
The comment has been removedAnonymous
December 15, 2008
How can I create grid columns on the fly and bind them to a data source?Anonymous
March 22, 2009
The comment has been removedAnonymous
April 26, 2009
This artical is nice . I want that how to bind data from data base to grid using silver light is it possible.Anonymous
April 28, 2009
The comment has been removedAnonymous
May 18, 2009
hi, I have a problem, everytime i run my application two identical headers were display... Please check my code here... I had noticed that property method's name is also display in the datagrid. What I want is to display the image only dyanamically and remove the other column. Could anyone help me... Thanks in advance... In XAML.. <my:DataGrid x:Name="dataGrid" Margin="80,88,104,116" > <my:DataGrid.Columns> <my:DataGridTemplateColumn Header="Thumbnail"> <my:DataGridTemplateColumn.CellTemplate> <DataTemplate> <Image Source="{Binding Thumbnail}" Width="64"/> </DataTemplate> </my:DataGridTemplateColumn.CellTemplate> </my:DataGridTemplateColumn> </my:DataGrid.Columns> </my:DataGrid> Propety page.. Property Thumbnail() As String Get Return _image End Get Set(ByVal value As String) _image = value End Set End Property XAML.vb... source.Add(New TubeContent() With {.Thumbnail = imageURL})Anonymous
May 19, 2009
Hi Ben, The reason that you are seeing two columns is because the AutoGenerateColumns on your DataGrid is still true (this is the default value). Setting it to false should fix your problem. Hope this helps!Anonymous
May 19, 2009
Hi scmorris, This is works! Thank You Very Much...Anonymous
July 20, 2009
Hi, im new to silver light i have a got a basic doubt. I need to bind an array of items. which contains 5 attributes, and i need only 3 of them to be displayed in the grid. I did the follwoing <data:DataGrid.Columns> <data:DataGridTextColumn Header="Page" Binding="{Binding PageName}" /> <data:DataGridTextColumn Header="Data Item Caption" Binding="{Binding DisplayName}" /> <data:DataGridTextColumn Header="Message" Binding="{Binding Message}" /> <data:DataGridTextColumn Header="Item" Binding="{Binding Item}" Visibility="Collapsed"/> <data:DataGridTextColumn Header="Name" Binding="{Binding Name}" Visibility="Collapsed" /> </data:DataGrid.Columns> But in addition to these the other 5 attributes are also getting binded to the grid. How to make those five columns invisible. Thanks.Anonymous
July 20, 2009
Hi i got the answer for my question. Thank u.Anonymous
July 21, 2009
Hi scmorris, Since DataGridColumn properties aren't DependencyPropertys they can't be data-bound or whatever, right? So is there any way to bind the Width (or other) properties in XAML? Thanks, RobertAnonymous
August 03, 2009
Hi Robert, Unfortunately there is no way to databind properties on DataGridColumns yet. This is since they are DependencyObjects instead of Controls, and DO's cannot be the target of a binding in Silverlight 3. If the future when this functionality exists in the platform you can expect the DataGrid to fully support it. In the mean time, you will have to use programmatic methods to try to emulate the binding logic. Hope this helps.Anonymous
August 18, 2009
Hi Scott... Thanks, very much nice topic, it was very useful :)Anonymous
September 07, 2009
can we transform row and column of the grid so that column appears in the top and row appears in the place of rowAnonymous
November 18, 2009
Scott, This is a great article. I would like to see if there is a way to create dynamic rows for silverlight datagrid?? ThanksAnonymous
April 16, 2010
Hi, Is there any way possible that I can add rows dynamically. for e,g, say pressing the tab in the last row can take me to a new row where I can add values? Thanks guys for your helpAnonymous
February 07, 2011
I'm trying to create a debug window for myself writing out when certain events fire and I'm having problems catching any events when I change the state of the checkbox. Which event should I be listening for to catch this event? Also, I wanted to change the way the tab loops through the grid. Instead of looping through all rows cell by cell, I want the grid to loop through only the cells in the currently selected row and start over when the last cell is reached. I tried the TabNavigation but that doesn't seem to change this behavior. Where should I be looking for this?