This is a migrated thread and some comments may be shown as answers.

CellFormatting and speed

11 Answers 361 Views
GridView
This is a migrated thread and some comments may be shown as answers.
Svein Thomas
Top achievements
Rank 1
Svein Thomas asked on 14 Dec 2010, 11:58 AM
Hi,

I have a grid that i have added a custom column containing a progress bar. This is done by adding the progressbar or updating the progressbar each time the CellFormatting event is fired. But it seems like this is done way to often?
In my opinion would i like to paint this the first time i load the row. Then I want to be able to update the progressbar in a row when the progressbar values  have changed. 
Now it updates this each time i click in a cell or change row. And it does not just happen to the row the i clicked in.. it fires for all visible rows in the grid. 

How can i avoid this, how can i speed up the grid. NB the progressvalue function (my function) is slow as well, but fast enough if i was to set the progress value for a specific row.

Regards
Svein Thomas

11 Answers, 1 is accepted

Sort by
0
Richard Slade
Top achievements
Rank 2
answered on 14 Dec 2010, 12:27 PM
Hello,

from what I understand of your situation the CellFormatting event is the way to go. Because the radGridView uses UI Virtualization, tyou cannot just paint items on load. Please take a look at this link on logical vs visual grid strcuture that should help

Hope that helps
Richard
0
Svein Thomas
Top achievements
Rank 1
answered on 14 Dec 2010, 12:44 PM
Well i understand that the cellformatting event is fired when a cell needs update, but does it need to fire for all the visible rows/cells when i click a single cell? And is there a smart way to figure out that a cell does not need update and then just skip this?

Regards
Svein Thomas
0
Richard Slade
Top achievements
Rank 2
answered on 14 Dec 2010, 12:46 PM
Hello,

Are you able to provide a basic sample, and I'll be happy to take a look at it for you and se if there are ways to speed it up.
Thanks
Richard
0
Svein Thomas
Top achievements
Rank 1
answered on 14 Dec 2010, 01:24 PM
Ok. I cannot give you the exact data that i use, but I use a Linq datasource and some Stored procs to get the values. Thats why my progressbar function is a bit slow. I have tried to create an example that illustrates my grid speed. 

using System.ComponentModel;
using System.Threading;
using System.Windows.Forms;
using Telerik.WinControls.UI;
 
namespace MySlowGrid
{
    public class Form1 : Form
    {
        /// <summary>
        /// Required designer variable.
        /// </summary>
        private System.ComponentModel.IContainer components = null;
 
        /// <summary>
        /// Clean up any resources being used.
        /// </summary>
        /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
        }
 
        #region Windows Form Designer generated code
 
        /// <summary>
        /// Required method for Designer support - do not modify
        /// the contents of this method with the code editor.
        /// </summary>
        private void InitializeComponent()
        {
            Telerik.WinControls.UI.GridViewTextBoxColumn gridViewTextBoxColumn1 = new Telerik.WinControls.UI.GridViewTextBoxColumn();
            Telerik.WinControls.UI.GridViewTextBoxColumn gridViewTextBoxColumn2 = new Telerik.WinControls.UI.GridViewTextBoxColumn();
            Telerik.WinControls.UI.GridViewTextBoxColumn gridViewTextBoxColumn3 = new Telerik.WinControls.UI.GridViewTextBoxColumn();
            Telerik.WinControls.UI.GridViewTextBoxColumn gridViewTextBoxColumn4 = new Telerik.WinControls.UI.GridViewTextBoxColumn();
            Telerik.WinControls.UI.GridViewTextBoxColumn gridViewTextBoxColumn5 = new Telerik.WinControls.UI.GridViewTextBoxColumn();
            this.radGridView1 = new Telerik.WinControls.UI.RadGridView();
            ((System.ComponentModel.ISupportInitialize)(this.radGridView1)).BeginInit();
            ((System.ComponentModel.ISupportInitialize)(this.radGridView1.MasterTemplate)).BeginInit();
            this.SuspendLayout();
            //
            // radGridView1
            //
            this.radGridView1.BackColor = System.Drawing.SystemColors.Control;
            this.radGridView1.Cursor = System.Windows.Forms.Cursors.Default;
            this.radGridView1.Dock = System.Windows.Forms.DockStyle.Fill;
            this.radGridView1.Font = new System.Drawing.Font("Segoe UI", 8.25F);
            this.radGridView1.ForeColor = System.Drawing.SystemColors.ControlText;
            this.radGridView1.ImeMode = System.Windows.Forms.ImeMode.NoControl;
            this.radGridView1.Location = new System.Drawing.Point(0, 0);
            //
            // radGridView1
            //
            gridViewTextBoxColumn1.FieldName = "A";
            gridViewTextBoxColumn1.FormatInfo = new System.Globalization.CultureInfo("");
            gridViewTextBoxColumn1.HeaderText = "column1";
            gridViewTextBoxColumn1.Name = "column1";
            gridViewTextBoxColumn1.Width = 76;
            gridViewTextBoxColumn2.FieldName = "B";
            gridViewTextBoxColumn2.FormatInfo = new System.Globalization.CultureInfo("");
            gridViewTextBoxColumn2.HeaderText = "column2";
            gridViewTextBoxColumn2.Name = "column2";
            gridViewTextBoxColumn2.Width = 81;
            gridViewTextBoxColumn3.FieldName = "C";
            gridViewTextBoxColumn3.FormatInfo = new System.Globalization.CultureInfo("");
            gridViewTextBoxColumn3.HeaderText = "column3";
            gridViewTextBoxColumn3.Name = "column3";
            gridViewTextBoxColumn3.Width = 82;
            gridViewTextBoxColumn4.FieldName = "D";
            gridViewTextBoxColumn4.FormatInfo = new System.Globalization.CultureInfo("");
            gridViewTextBoxColumn4.HeaderText = "column4";
            gridViewTextBoxColumn4.Name = "column4";
            gridViewTextBoxColumn4.Width = 90;
            gridViewTextBoxColumn5.FormatInfo = new System.Globalization.CultureInfo("");
            gridViewTextBoxColumn5.HeaderText = "column5";
            gridViewTextBoxColumn5.Name = "ProgressBar";
            gridViewTextBoxColumn5.Width = 88;
            this.radGridView1.MasterTemplate.Columns.AddRange(new Telerik.WinControls.UI.GridViewDataColumn[] {
            gridViewTextBoxColumn1,
            gridViewTextBoxColumn2,
            gridViewTextBoxColumn3,
            gridViewTextBoxColumn4,
            gridViewTextBoxColumn5});
            this.radGridView1.Name = "radGridView1";
            this.radGridView1.Padding = new System.Windows.Forms.Padding(0, 0, 0, 1);
            this.radGridView1.ReadOnly = true;
            this.radGridView1.RightToLeft = System.Windows.Forms.RightToLeft.No;
            //
            //
            //
            this.radGridView1.RootElement.Padding = new System.Windows.Forms.Padding(0, 0, 0, 1);
            this.radGridView1.ShowGroupPanel = false;
            this.radGridView1.Size = new System.Drawing.Size(599, 416);
            this.radGridView1.TabIndex = 0;
            this.radGridView1.Text = "radGridView1";
            //
            // Form1
            //
            this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
            this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
            this.ClientSize = new System.Drawing.Size(599, 416);
            this.Controls.Add(this.radGridView1);
            this.Name = "Form1";
            this.Text = "Form1";
            ((System.ComponentModel.ISupportInitialize)(this.radGridView1.MasterTemplate)).EndInit();
            ((System.ComponentModel.ISupportInitialize)(this.radGridView1)).EndInit();
            this.ResumeLayout(false);
 
        }
 
        #endregion
 
        private Telerik.WinControls.UI.RadGridView radGridView1;
 
        public Form1()
        {
            InitializeComponent();
            BindingList<MyData> list = new BindingList<MyData>(); ;
            for (int i = 0; i <= 20; i++)
            {
                list.Add(new MyData(100, 40));
            }
            radGridView1.DataSource = list;
            radGridView1.CellFormatting += new Telerik.WinControls.UI.CellFormattingEventHandler(radGridView1_CellFormatting);
        }
 
 
        void radGridView1_CellFormatting(object sender, Telerik.WinControls.UI.CellFormattingEventArgs e)
        {
            if (e.CellElement.ColumnInfo is GridViewDataColumn &&
                   ((GridViewDataColumn)e.CellElement.ColumnInfo).Name == "ProgressBar")
            {
 
                MyData a = ((MyData)e.CellElement.RowInfo.DataBoundItem);
                int progressValue = a.mySlowFunction();
                int progressMaxValue = a.B;
                if (e.CellElement.Children.Count > 0)
                {
                     
                    var prg = e.CellElement.Children[0] as RadProgressBarElement;
                    prg.Maximum = progressMaxValue;
                    prg.Value1 = progressValue;
                    prg.Text = string.Format("{0}/{1}", progressValue, progressMaxValue);
                    return;
                }
 
 
 
                RadProgressBarElement element = new RadProgressBarElement();
                element.Minimum = 0; //set min value of RadProgressBarElement 
                element.Maximum = progressMaxValue; //also max
                element.Value1 = progressValue > progressMaxValue ? progressMaxValue : progressValue;
                element.Text = string.Format("{0}/{1}", progressValue, progressMaxValue);
                //element.ProgressText =
                element.StretchHorizontally = true;
                element.StretchVertically = true;
                e.CellElement.Children.Add(element);
            }
        }
 
    }
 
 
    public class MyData
    {
        public string A { get; set; }
        public int B { get; set; }
        public string C { get; set; }
        public int D { get; set; }
 
        public MyData(int b, int d)
        {
            A = "ProgressBar MaxValue";
            B = b;
            C = "ProgressBar Value";
            D = d;
        }
 
        public int mySlowFunction()
        {
            Thread.Sleep(100);
            return D;
        }
 
    }
 
}
0
Richard Slade
Top achievements
Rank 2
answered on 14 Dec 2010, 01:52 PM
Hi,

The only thing I've added is at the end of the following line
if (e.CellElement.ColumnInfo is GridViewDataColumn && e.CellElement is GridDataCellElement &&
which does make some difference.

However, the slow part of it is the sleep to simulate the query. I'd also advise in your real app not using LINQ to SQL as this is considerably slower than using an ExecuteScaler for exmaple.

Let me know if that helps, or if I can be of any more help
Richard
0
Svein Thomas
Top achievements
Rank 1
answered on 14 Dec 2010, 02:15 PM
I understand that the linq and my slow function is slow.. but it is only slow when all the rows are painted/updated...
It is not very slow if its only one row that is updated. So how can i just update the changed row? 
In the view there are 20 rows. only two of them is updated when i change row.

This means that the change of row would only take 200 ms not 2000 ms. I can live with 200.

Regards
Svein Thomas
0
Svein Thomas
Top achievements
Rank 1
answered on 14 Dec 2010, 02:34 PM
One other thing that i noticed is that, if I make the window so small that the progressbar column does not show and then resizes the window.. i get the progress bars in the other columns.. see attached screenshot. 
0
Richard Slade
Top achievements
Rank 2
answered on 14 Dec 2010, 02:37 PM
Hi again,

I'm afraid this is not how CellFormatting works. This has already been explained in this forum thread which may help.
Hope this helps
Richard
0
Svett
Telerik team
answered on 17 Dec 2010, 12:42 AM
Hi Svein Thomas,

After inspecting your code snippet I noticed that you are creating the progress bar element in the CellFormatting event. The preferable practice to add elements concerns the process of creating a custom cell element which hosts the progress bar element. You can read more about how you can create it in these resources:


This will prevent the issue that you have mentioned.
Kind regards,
Svett
the Telerik team
Check out the Q1 2011 Roadmap for Telerik Controls for Windows Forms.
0
Svein Thomas
Top achievements
Rank 1
answered on 17 Dec 2010, 01:03 PM
Hi, this was useful ;)
But one more question. How can i set two to one cell by binding?
For the progressbar i like to set both the value1 and maximum

Regards
Svein Thomas
0
Svett
Telerik team
answered on 22 Dec 2010, 02:38 PM
Hello Svein Thomas,

I have attached a sample project that demonstrates how you can achieve the desired behavior.

All the best,
Svett
the Telerik team
Check out the Q1 2011 Roadmap for Telerik Controls for Windows Forms.
Tags
GridView
Asked by
Svein Thomas
Top achievements
Rank 1
Answers by
Richard Slade
Top achievements
Rank 2
Svein Thomas
Top achievements
Rank 1
Svett
Telerik team
Share this question
or