将 CellPaint 事件处理程序与 DataGridView 一起使用

Using CellPaint event handler with DataGridView

这里的想法是我重新绘制组合 "cell" 以便它显示颜色和文本块。这是当表单显示并且即将显示下拉列表时:

在我选择了一种颜色之后它变得很奇怪:

现在全错了。我必须将鼠标悬停在控件上才能呈现其他位。只是工作不正常。

我的经纪人:

    private void DataGridView1_CellPainting(object sender, DataGridViewCellPaintingEventArgs e)
    {
        if(e.ColumnIndex == 0 && e.RowIndex > 0)
        {
            e.PaintBackground(e.ClipBounds, true);
            e.PaintContent(e.ClipBounds);

            Graphics g = e.Graphics;
            Color c = Color.Empty;
            string s = "";
            Brush br = SystemBrushes.WindowText;
            Brush brBack;
            Rectangle rDraw;

            rDraw = e.ClipBounds;
            rDraw.Inflate(-1, -1);

            {
                brBack = Brushes.White;
                g.FillRectangle(brBack, e.ClipBounds);
            }

            try
            {
                ComboboxColorItem oColorItem = (ComboboxColorItem)((ComboBox)sender).SelectedItem;
                s = oColorItem.ToString();
                c = oColorItem.Value;
            }
            catch
            {
                s = "red";
                c = Color.Red;
            }

            SolidBrush b = new SolidBrush(c);
            Rectangle r = new Rectangle(e.ClipBounds.Left + 5, e.ClipBounds.Top + 3, 10, 10);
            g.FillRectangle(b, r);
            g.DrawRectangle(Pens.Black, r);
            g.DrawString(s, Form.DefaultFont, Brushes.Black, e.ClipBounds.Left + 25, e.ClipBounds.Top + 1);

            b.Dispose();
            g.Dispose();

            e.Handled = true;
        }
    }
}

有什么我想念的吗?一定是。

更新:

我在 CellPainting 活动中试过这个:

if(e.ColumnIndex == 0 && e.RowIndex > 0)
{
    using (Graphics g = e.Graphics)
    {
        g.FillRectangle(Brushes.Aqua, e.CellBounds);
    }

}
else
{
    e.PaintBackground(e.CellBounds, true);
    e.PaintContent(e.CellBounds);
}
e.Handled = true;

从某种意义上说,这会有所改善,因为它不会那么奇怪。当然,它实际上并没有画任何东西。但是,最左边的单元格(带有编辑符号)不需要很长时间就只显示为白色。所以它的机制仍然不对。 谢谢。

如果我按照建议的方式尝试,我会得到:

进步了!我们可以调整它以仍然包括网格线吗?就像在正常细胞中一样?

之后
  • 将所有 ClipBounds 换成 CellBounds
  • 正在删除 g.Dispose();

..一切看起来都很正常。

这是结果:

在这个 Paint 事件中:

private void dataGridView2_CellPainting(object sender, 
                                        DataGridViewCellPaintingEventArgs e)
{
    if (e.ColumnIndex == 4 && e.RowIndex == 0)  // use your own checks here!!
    {
        e.PaintBackground(e.CellBounds, true);
        e.PaintContent(e.CellBounds);

        Graphics g = e.Graphics;
        Color c = Color.Empty;
        string s = "";
        Brush br = SystemBrushes.WindowText;
        Brush brBack;
        Rectangle rDraw;

        rDraw = e.CellBounds;
        rDraw.Inflate(-1, -1);

        {
            brBack = Brushes.White;
            g.FillRectangle(brBack, rDraw);  // **
        }

        try
        {    // use your own code here again!
            //  ComboboxColorItem oColorItem = 
            //      (ComboboxColorItem)((ComboBox)sender).SelectedItem;
            s = "WW";// oColorItem.ToString();
            c = Color.LawnGreen;// oColorItem.Value;
        } catch
        {
            s = "red";
            c = Color.Red;
        }

        // asuming a square is right; make it a few pixels smaller!
        int butSize = e.CellBounds.Height;  
        Rectangle rbut = new Rectangle(e.CellBounds.Right - butSize , 
                                       e.CellBounds.Top, butSize , butSize );
        ComboBoxRenderer.DrawDropDownButton(e.Graphics, rbut,  
                   System.Windows.Forms.VisualStyles.ComboBoxState.Normal);


        SolidBrush b = new SolidBrush(c);
        Rectangle r = new Rectangle( e.CellBounds.Left + 5, 
                                     e.CellBounds.Top + 3, 10, 10);
        g.FillRectangle(b, r);
        g.DrawRectangle(Pens.Black, r);
        g.DrawString(s, Form.DefaultFont, Brushes.Black, 
                     e.CellBounds.Left + 25, e.CellBounds.Top + 1);

        b.Dispose();
        //g.Dispose();  <-- do not dispose of thing you have not created!

        e.Handled = true;
    }

}

请注意,我只有一张CombBoxCell,所以我更改了支票。而且我没有 ComboboxColorItem,所以我替换了一个随机字符串和颜色。

来自 OP 的更新:我有一些语法错误,需要:

// use your own code here again!
if(DataGridView1.Rows[e.RowIndex].Cells[e.ColumnIndex].Value != null)
{
    ComboboxColorItem oColorItem = (ComboboxColorItem)DataGridView1
                                  .Rows[e.RowIndex].Cells[e.ColumnIndex].Value;
    s = oColorItem.ToString();
    c = oColorItem.Value;
}