How to Style Cells in Your .NET Datagrid Application
With the release of our ComponentOne .NET 6 controls, styling cells of a grid is a common help topic many users have questions about. Depending on what styling you would like to apply, there are a number of techniques available built-in to the FlexGrid API.
Additionally, FlexGrid also provides style editors that allow you to customize the appearance of your grid, columns, or captions without writing a single line of code. Design-time editors are available in our .NET Framework release of the control and are currently being added to the features of our .NET 6 release version of FlexGrid.
This article aims to introduce the conceptual knowledge of the FlexGrid CellStyle class, along with the priorities in which they are applied. It also handles a use-case of overriding default style priorities. Let’s take a look at these one-by-one.
Deliver enterprise-level applications faster with the most flexible .NET UI controls. Download ComponentOne Today!
Basics
Creating Reusable Styles
The FlexGrid control uses the CellStyle class to customize cell appearance. When you modify a CellStyle object, all cells that are using that CellStyle are automatically repainted in order to reflect the changes. For this reason, we will need to ensure that we are creating new CellStyle objects for each new style we would like to display; otherwise, only the most recent style applied will be shown. By creating new CellStyle objects, we are also creating reusable styles. This can be done by simply creating a new CellStyle object and adding it to the Styles collection using the Add method, as shown in the line below:
C1.Win.FlexGrid.CellStyle CustomStyle = c1FlexGrid1.Styles.Add("CustomStyle");
Once you have this new custom style created, you can modify the different properties of it to be set to your liking before applying it to a set of rows, columns, or cells, as shown below:
CustomStyle.BackColor = Color.Red;
c1FlexGrid1.Cols[1].Style = CustomStyle;
Creating Styles on the Fly
Another way to assign styles is to utilize the StyleNew property, which is included within FlexGrid elements such as Row, Column, CellRange, etc. The StyleNew property retrieves the object’s style (if it already exists) or creates a new one and assigns it to the object. This property provides a quick way to apply formatting in a manner that is not intended to be reused. For example, if you wanted to make a range of the first two columns in your grid light pink, you could add the following lines of code:
C1.Win.FlexGrid.CellRange rg = c1FlexGrid1.GetCellRange(1, 1, 6, 2);
rg.StyleNew.BackColor = Color.LightPink;
The above CellRange variable “rg” gets assigned the portions of the FlexGrid in our application, and then when the StyleNew.BackColor property is set (since StyleNew is a property belonging to the CellRange class), the assigned cells respond appropriately.
Removing Styles
To clear or remove style formatting applied to a FlexGrid’s cells, you can use the Clear method of FlexGrid and pass “Style” as the parameter to clear custom styles assigned to the cells. Applying the Clear method with the “Style” parameter clears only the style formatting and not the contents or UserData of the grid. This is shown below:
this.c1FlexGrid1.Clear(C1.Win.FlexGrid.ClearFlags.Style);
In the sample application, we created a button that, once clicked, will clear the style formatting applied to the cells in the FlexGrid associated with the form by simply throwing the above line of code inside the button_click event.
Styling the Grid Object
In addition to styling individual cells, columns, or rows, you can also style the entire FlexGrid object itself by setting alternate row colors or adding an image in the background of the grid. To apply alternate row colors, you’ll have to utilize the CellStyle item “Alternate” of the CellStyleCollection class and set the various properties for setting the alternate style, such as shown below:
// Set forecolor for the alternate row
c1FlexGrid1.Styles["Alternate"].ForeColor = Color.White;
// Set backcolor for the alternate row
c1FlexGrid1.Styles["Alternate"].BackColor = Color.CadetBlue;
To set the background image, you can simply reference the BackgroundImage property of the FlexGrid object, and you can utilize the BackgroundImageLayout property to control how the image appears, as shown below:
// Set the background image in grid
c1FlexGrid1.BackgroundImage = Image.FromFile("C:\\IMG-20190524-WA0037.png");
c1FlexGrid1.BackgroundImageLayout = ImageLayout.Stretch;
Additionally, you can customize the Grid’s border by utilizing the BorderStyle property, which accepts values from the BorderStyleEnum provided by the C1.Win.FlexGrid.Util.BaseControls namespace. Below is an example:
// Change the grid border to a three dimensional border
c1FlexGrid1.BorderStyle = C1.Win.C1FlexGrid.Util.BaseControls.BorderStyleEnum.Fixed3D;
Customize Row, Column, and Cell Border
To customize the border style of a particular row or column, you must access the “Border” item of the CellStyle class using the StyleNew property and setting its properties such as border style, direction, and color. The grid control provides BorderStyleEnum as well as BorderDirEnum to set the border style and direction, respectively. The below code shows an example:
// Set the border style for first column
c1FlexGrid1.Cols[1].StyleNew.Border.Style = BorderStyleEnum.Groove;
c1FlexGrid1.Cols[1].StyleNew.Border.Color = Color.Red;
c1FlexGrid1.Cols[1].StyleNew.Border.Direction = BorderDirEnum.Vertical;
//Set the border style for first row
c1FlexGrid1.Rows[1].StyleNew.Border.Style = BorderStyleEnum.Raised
;c1FlexGrid1.Rows[1].StyleNew.Border.Color = Color.Blue;
To customize the border of every cell in the grid, you can access the built-in style “Normal” and set its border properties. Similarly, you can change the style of specific types of cells, such as fixed or frozen, by accessing their corresponding styles from the Styles collection:
// Set the border style for all grid cells
c1FlexGrid1.Styles.Normal.Border.Style = BorderStyleEnum.Double;
Customized Text Styling
In addition to colors, FlexGrid’s CellStyle class also includes properties to manipulate the style of the text within the cells, with the ability to alter the font, margin, orientation, alignment, effects, and more. To change the font within a particular row or column object, you can set the Font property of its CellStyle, as shown in the code below:
//Apply the custom style to a particular row
c1FlexGrid1.Rows[1].StyleNew.Font = new Font("verdana", 10, FontStyle.Underline);
c1FlexGrid1.Rows[0].StyleNew.Font = new Font("verdana", 10, FontStyle.Bold);
You can also change the font of the whole grid by setting the Font property of the FlexGrid object:
// Change the font of whole grid content
c1FlexGrid1.Font = new Font("verdana", 10, FontStyle.Italic);
To learn more about the various other types of Font styling with code examples, check out our documentation here: Customize Text | FlexGrid for WinForms | ComponentOne (grapecity.com)
Customized Glyph Styling
Lastly, FlexGrid allows you to customize the default glyph images used in the grid to indicate various actions, such as column filtering and sorting. This behavior can be changed by using the GridGlyphs class, a collection of images used by the grid to represent different behaviors such as sorting order, filtered state, etc. These images can be accessed through the Glyphs property of the FlexGrid class, which accepts values from the GlyphEnum enumeration.
Setting the Glyphs property to null will restore the default glyphs associated with the grid. If you want to hide a glyph, you can set the Glyph property to a blank image. The code below shows how you can manipulate the glyphs for a grid’s filter icon:
//Create C1BitmapIcon object
C1.Framework.C1BitmapIcon icon1 = new C1.Framework.C1BitmapIcon();
//Create Bitmap object set to the custom image you want for the glyph
Bitmap bitmap = new Bitmap("icon.png");
//Set the source for the C1BitmapIcon object to the Bitmap object
icon1.Source = bitmap;
//Set the FilterEditor glyph to the C1BitmapIcon
c1FlexGrid1.Glyphs[GlyphEnum.FilterEditor] = icon1;
// Customize the glyph for filter icon in column
//Create C1BitmapIcon object
C1.Framework.C1BitmapIcon icon1 = new C1.Framework.C1BitmapIcon();
//Create Bitmap object set to the custom image you want for the glyph
Bitmap bitmap = new Bitmap("icon.png");
//Set the source for the C1BitmapIcon object to the Bitmap object
icon1.Source = bitmap;
//Set the FilterColumn glyph to the C1BitmapIcon
c1FlexGrid1.Glyphs[GlyphEnum.FilteredColumn] = icon1;
Here is an example where I changed the FilterColumn glyph icon to a pink hazardous waste symbol:
Styling Grid’s Elements and their Priorities
As explained throughout the sections above, the appearance of the cells (their alignment, font, colors, borders, etc.) are all handled by their associated CellStyle object. The grid itself also has a Styles property that holds the collection of styles used to format the grid.
The collection of styles includes built-in styles, such as Focus, Highlight, Fixed, etc. Earlier, we explained how you could create your own custom styles and assign them to various Grid elements, such as Rows[], Cols[], Cells, and CellRanges.
Suppressing Default Priority
Some of the built-in styles, such as Focus and Highlight, will suppress any custom style when applied to a cell. If you still want the custom style applied to a cell, you will have to suppress the default style priority even when these other built-in styles are in effect.
To do so, you will have to re-assign the custom style to the desired cell in the “OwnerDrawCell” event. The OwnerDrawCell event and DrawMode property allow you to override every visual aspect of the cell.
The parameters used in the OwnerDrawCell event will enable you to change the data that is displayed along with the style of the cell and allows you to draw whatever you desire into the cell. Following the scenario above, you would need to set the desired custom style to the cell using the e.Style property.
Deliver enterprise-level applications faster with the most flexible .NET UI controls. Download ComponentOne Today!