麻烦绘制可滚动的datagridview

时间:2017-04-05 15:09:36

标签: c# winforms datagridview paint

我试图自定义绘制DataGridView,但是在滚动DataGridView之后我无法正确查看它。我的细胞中出现了一些线条。问题是当滚动控件时,paint事件似乎没有重绘单元格,因此在窗体边缘绘制的单元格在滚动到中心时不会重绘。

我可以通过忽略DataGridView边缘的部分单元格没有显示并将它们绘制成完全可见的事实来消除这个问题,但这会使我的应用程序看起来不那么好。

我的问题是:有没有更好的方法来绘制DataGridView,以便我可以调整部分显示单元格的单元格绘制?我已经查看了其他问题,并尝试使用其他油漆事件,但我还没有能够得到任何工作。

这是一个简单的程序,演示了我正在谈论的问题。

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();

        for (int i = 0; i < 256; i++)
            dataGridView1.Rows.Add(new object[] { string.Format("Test_text_{0}", i) });

        dataGridView1.Paint += DataGridView1_Paint;
        dataGridView1.CellPainting += (s, e) => { if (e.RowIndex > 0 && e.ColumnIndex >= 0) e.Handled = true; };
    }

    private void DataGridView1_Paint(object sender, PaintEventArgs e)
    {
        Rectangle rect;

        using (Brush gridBrush = new SolidBrush(dataGridView1.GridColor),
            cellBrush = new SolidBrush(dataGridView1.DefaultCellStyle.BackColor),
            textBrush = new SolidBrush(dataGridView1.DefaultCellStyle.ForeColor))
        {
            using (Pen gridLinePen = new Pen(gridBrush))
            {
                for (int row = 0; row < dataGridView1.Rows.Count; row++)
                {
                    if (!dataGridView1.Rows[row].Displayed)
                        continue;

                    if (dataGridView1.Rows[row].Cells[0].Value != null)
                    {
                        //draw cell
                        rect = dataGridView1.GetCellDisplayRectangle(0, row, true);//Setting cutOverflow to false removes lines
                        e.Graphics.FillRectangle(cellBrush, rect);
                        e.Graphics.DrawLine(gridLinePen, rect.Left, rect.Bottom - 1, rect.Right - 1, rect.Bottom - 1);
                        e.Graphics.DrawLine(gridLinePen, rect.Right - 1, rect.Top, rect.Right - 1, rect.Bottom);

                        //add text
                        e.Graphics.DrawString(dataGridView1.Rows[row].Cells[0].Value.ToString(), 
                            dataGridView1.DefaultCellStyle.Font, textBrush, rect.X + 4, rect.Y + 4);
                    }
                    else
                        //handle empty rows
                        e.Graphics.FillRectangle(gridBrush, dataGridView1.GetCellDisplayRectangle(0, row, true));
                }
            }
        }
    }
}

设计师代码

partial class Form1
{
    /// <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()
    {
        this.dataGridView1 = new System.Windows.Forms.DataGridView();
        this.Column1 = new System.Windows.Forms.DataGridViewTextBoxColumn();
        ((System.ComponentModel.ISupportInitialize)(this.dataGridView1)).BeginInit();
        this.SuspendLayout();
        // 
        // dataGridView1
        // 
        this.dataGridView1.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize;
        this.dataGridView1.Columns.AddRange(new System.Windows.Forms.DataGridViewColumn[] {
        this.Column1});
        this.dataGridView1.Location = new System.Drawing.Point(46, 36);
        this.dataGridView1.Name = "dataGridView1";
        this.dataGridView1.Size = new System.Drawing.Size(184, 428);
        this.dataGridView1.TabIndex = 0;
        // 
        // Column1
        // 
        this.Column1.HeaderText = "Column1";
        this.Column1.Name = "Column1";
        // 
        // Form1
        // 
        this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
        this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
        this.ClientSize = new System.Drawing.Size(281, 522);
        this.Controls.Add(this.dataGridView1);
        this.Name = "Form1";
        this.Text = "Form1";
        ((System.ComponentModel.ISupportInitialize)(this.dataGridView1)).EndInit();
        this.ResumeLayout(false);

    }

    #endregion

    private System.Windows.Forms.DataGridView dataGridView1;
    private System.Windows.Forms.DataGridViewTextBoxColumn Column1;
}

这是一个截图

enter image description here

2 个答案:

答案 0 :(得分:2)

问题是PaintCellPainting事件都只绘制了在滚动DataGridView之前未显示的单元格部分。我能够通过强制整个DataGridView重绘Scroll事件来解决问题。

    dataGridView1.Scroll += (s, e) => dataGridView1.Invalidate();

答案 1 :(得分:0)

您已通过编写

禁用了单元格绘制
dataGridView1.CellPainting += (s, e) =>
    { if (e.RowIndex > 0 && e.ColumnIndex >= 0) e.Handled = true; };

使用CellPainting事件代替Paint事件执行单元格绘制。