tôi cần điều phức tạp hơn một chút - hình ảnh thêm ở phía trước văn bản trong một số tiêu đề cột liên quan đến căn chỉnh cột.
Bạn cần phải thực hiện của riêng bạn System.Windows.Forms.DataGridViewColumnHeaderCell
và thay thế ColumnHeaderCell
:
// Create header and set up image
YourDataGridViewColumnHeaderCell headerCell = new YourDataGridViewColumnHeaderCell();
headerCell.Image = something;
// Create column
DataGridViewColumn yourColumn = new DataGridViewTextBoxColumn();
// ...
yourColumn.ColumnHeaderCell = new headerCell;
Bây giờ là phần hài hước (thực hiện tiêu đề cột của bạn):
class YourDataGridViewColumnHeaderCell : System.Windows.Forms.DataGridViewColumnHeaderCell
{
// Set up image as you want
System.Drawing.Image Image { get; set; }
}
Bây giờ chúng tôi muốn thêm Paint()
phương pháp. Phần khó khăn duy nhất là làm việc với System.Windows.Forms.DataGridViewPaintParts
.
protected override void Paint(Graphics graphics, Rectangle clipBounds, Rectangle cellBounds, int rowIndex, DataGridViewElementStates dataGridViewElementState,
object value, object formattedValue, string errorText, DataGridViewCellStyle cellStyle, DataGridViewAdvancedBorderStyle advancedBorderStyle,
DataGridViewPaintParts paintParts)
{
// Outside header or without an image, use default painting
if ((rowIndex != -1) || (Image == null)) {
base.Paint(graphics, clipBounds, cellBounds, rowIndex, dataGridViewElementState, value, formattedValue, errorText, cellStyle, advancedBorderStyle, paintParts);
return;
}
// Borders, background, focus selection can remain the same
// But Foreground will have different image
base.Paint(graphics, clipBounds, cellBounds, rowIndex, dataGridViewElementState, value, formattedValue, errorText, cellStyle,
advancedBorderStyle, paintParts & ~DataGridViewPaintParts.ContentForeground);
// Repainting of content background (that's where we want to place our image)
if ((paintParts & DataGridViewPaintParts.ContentBackground) != DataGridViewPaintParts.None) {
// +4 is hardcoded margin
Point bounds = new Point(cellBounds.X + 4, cellBounds.Y);
// Handle vertical alignment correctly
switch (cellStyle.Alignment) {
// Top
case DataGridViewContentAlignment.TopLeft:
case DataGridViewContentAlignment.TopCenter:
case DataGridViewContentAlignment.TopRight:
// Already set
break;
// Middle
case DataGridViewContentAlignment.MiddleLeft:
case DataGridViewContentAlignment.MiddleCenter:
case DataGridViewContentAlignment.MiddleRight:
bounds.Y = cellBounds.Y + (cellBounds.Height - Image.Height)/2;
break;
// Bottom
case DataGridViewContentAlignment.BottomLeft:
case DataGridViewContentAlignment.BottomCenter:
case DataGridViewContentAlignment.BottomRight:
bounds.Y = cellBounds.Y + (cellBounds.Height - Image.Height);
break;
}
graphics.DrawImage(Image, bounds);
}
// Foreground should be shifted by left image margin + image.width + right
// image margin and of course target spot should be a bit smaller
if ((paintParts & DataGridViewPaintParts.ContentForeground) != DataGridViewPaintParts.None) {
Rectangle newCellBounds = new Rectangle(cellBounds.X + 4 + Image.Width + 4, cellBounds.Y, cellBounds.Width - Image.Width - 8, cellBounds.Height);
base.Paint(graphics, clipBounds, newCellBounds, rowIndex, dataGridViewElementState, value, formattedValue, errorText, cellStyle,
advancedBorderStyle, DataGridViewPaintParts.ContentForeground);
}
}
Nếu bạn muốn sử dụng AutoSizeColumnsMode
thiết lập để DataGridViewAutoSizeColumnsMode.ColumnHeaders
(do đó bạn sẽ AutoFit ảnh và văn bản), bạn cần phải ghi đè DataGridViewColumnHeaderCell.GetPreferredSize
. Tôi đã làm điều này bằng cách sử dụng triển khai cơ sở và thêm Image.Width + Padding
vào đó.
protected override Size GetPreferredSize(Graphics graphics, DataGridViewCellStyle cellStyle, int rowIndex,Size constraintSize)
{
// Load up original image
Size original = base.GetPreferredSize(graphics, cellStyle, rowIndex, constraintSize);
// Ensure the image is set and that we are working on header
if ((rowIndex != -1) || (Image == null)) {
return original;
}
// -1 is reserved value
if (original.Width < 0) {
return original;
}
return new Size(original.Width + Image.Width + 4, original.Height);
}
LƯU Ý: Tôi đã dành vài giờ đào trong .NET sources cho đến khi tôi figured this out. Hy vọng rằng bạn sẽ không phải làm vậy.
@Lucas - Cảm ơn những lời khuyên. Tôi sẽ cung cấp cho thử này và báo cáo lại ... –
Trong trường hợp bạn không lưu trữ hình ảnh trong một ImageList, sửa đổi lần thứ 2 LOC gần nhất; e.Graphics.DrawImage (hình ảnh, pt); cũng hoạt động. –
Nó hoạt động nhưng làm thế nào tôi có thể đặt hình ảnh bên cạnh văn bản với một số đệm? – Jack