Hello,
I have created a GridViewTextBoxColumn(), on _CellPaint() I am painting three images starting from the left to right. I would like to detect a mouse click on the rectangle that corresponds to the image but I can't get the Cell.Size information on the CellClick() event.
I have tried creating a custom control that holds three buttons but the UI doesn't fit my needs.
In order to determine what was clicked on the cell, I need to know the click x/y and the current cell rectangle.
Thanks!
void grid_CellPaint(object sender, GridViewCellPaintEventArgs e)
{
GridDataCellElement dataCell = e.Cell as GridDataCellElement;
if (dataCell != null && dataCell.ColumnInfo.FieldName == "ID")
{
Size cellSize = e.Cell.Size;
Rectangle rct = new Rectangle(0, 0, cellSize.Height, cellSize.Height);
//using (Pen p = new Pen(Color.Black))
// {
//Flag
rct.Inflate(-2, -2);
e.Graphics.DrawImage(global::DIRC.UITools.Properties.Resources.Flag_red_icon16x16, rct);
//Information Icon
rct = new Rectangle(cellSize.Height, 0, cellSize.Height, cellSize.Height);
rct.Inflate(-2, -2);
e.Graphics.DrawImage(global::DIRC.UITools.Properties.Resources.information_icon_16x16, rct);
//Comment Icon
rct = new Rectangle(cellSize.Height * 2, 0, cellSize.Height, cellSize.Height);
rct.Inflate(-2, -2);
e.Graphics.DrawImage(global::DIRC.UITools.Properties.Resources.comment_icon16x16, rct);
// }
}
}
5 Answers, 1 is accepted
Thank you for writing.
Indeed, creating a custom cell would be a better approach. Detailed information and examples are available here: http://docs.telerik.com/devtools/winforms/gridview/cells/creating-custom-cells.
I hope this helps. Please let me know if you need further assistance.
Regards,
Hristo Merdjanov
Telerik
Hello Hristo,
I looked at the example and what I came up is below. Is there any way to improve it?
Thanks
- Francisco
using System;using System.Collections.Generic;using System.Drawing;using System.Linq;using System.Text;using System.Threading.Tasks;using Telerik.WinControls.Layouts;using Telerik.WinControls.UI;namespace ABC.UITools{ public class CustomGridDataCellElement : GridDataCellElement { private int _buttonCount = 3; public event EventHandler ButtonClick; public CustomGridDataCellElement(GridViewColumn column, GridRowElement row, int buttonCount) : base(column, row) { _buttonCount = buttonCount; for (int i = 0; i < _buttonCount; i++) { RadButtonElement radButtonElement = new RadButtonElement(); radButtonElement.Name = "Button" + i.ToString("00"); radButtonElement.Tag = i; radButtonElement.Click += new EventHandler(Button_Click); radButtonElement.StretchVertically = true; radButtonElement.StretchHorizontally = true; radButtonElement.ShowBorder = false; radButtonElement.ImageAlignment = ContentAlignment.TopLeft; this.Children.Add(radButtonElement); } } protected override void CreateChildElements() { base.CreateChildElements(); } private void Button_Click(object sender, EventArgs e) { this.OnButtonClick(sender, e); } public List<RadButtonElement> Buttons { get{ return this.Children.Where(b => b is RadButtonElement).Cast<RadButtonElement>().ToList(); } } public override bool IsEditable { get { return false; } } protected virtual void OnButtonClick(object sender, EventArgs e) { if (this.ButtonClick != null) { this.ButtonClick(sender, e); } } protected override void DisposeManagedResources() { foreach (var child in this.Children) { if (child is RadButtonElement) { RadButtonElement btn = child as RadButtonElement; btn.Click -= new EventHandler(Button_Click); } } base.DisposeManagedResources(); } protected override SizeF ArrangeOverride(SizeF finalSize) { RectangleF clientRect = this.GetClientRectangle(finalSize); float buttonWidth = clientRect.Size.Width / this.Children.Count; RectangleF buttonFinalRect = new RectangleF(clientRect.Location, new SizeF(buttonWidth, clientRect.Height)); foreach (RadButtonElement button in this.Children) { button.Arrange(buttonFinalRect); buttonFinalRect = new RectangleF(new PointF(buttonFinalRect.X + buttonWidth, buttonFinalRect.Y), buttonFinalRect.Size); } return finalSize; } protected override Type ThemeEffectiveType { get { return typeof(GridDataCellElement); } } public override bool IsCompatible(GridViewColumn data, object context) { return data is TelerikCustomColumn && context is GridDataRowElement; } } public class TelerikCustomColumn : GridViewDataColumn { public TelerikCustomColumn(string fieldName) : base(fieldName) { } public override Type GetCellType(GridViewRowInfo row) { if (row is GridViewDataRowInfo) { return typeof(CustomGridDataCellElement); } return base.GetCellType(row); } }}The idea is to have different options of number of buttons depending on the grid that it is being used on. So for a grid column that needs 3 buttons I would create it like this;
//When creating the grid template. Width is determined based on the number of buttons to //be used * 20. I will be using 16x16 bitmaps on the buttons. grid.MasterTemplate.Columns.Add(new TelerikCustomColumn("Actions") { AllowReorder = false, AllowResize = false, Width = 60, HeaderText = "", AllowSort = false }); Sorry I hit Post before finishing.
//On the CreateCell(object sender, GridViewCreateCellEventArgs e) event//I do this.TelerikCustomColumn dataColumn = e.Column as TelerikCustomColumn; if (e.Row is GridDataRowElement && dataColumn != null && e.Column.FieldName == "Actions") { //Here I pass the number of buttons CustomGridDataCellElement cell = new CustomGridDataCellElement(e.Column, e.Row, 3); e.CellElement = cell; //Load the button images. List<RadButtonElement> btns = cell.Buttons; foreach (var b in btns) { if (b.Tag != null) { b.DisplayStyle = DisplayStyle.Image; b.ImageAlignment = ContentAlignment.MiddleCenter; if ((int)b.Tag == 0) { b.Image = global::ABC.UITools.Properties.Resources.img01; } else if ((int)b.Tag == 1) { b.Image = global::ABC.UITools.Properties.Resources.img02; } else if ((int)b.Tag == 2) { b.Image = global::ABC.UITools.Properties.img03; } } } cell.ButtonClick += new EventHandler(cell_ButtonClick); }On the cell_ButtonClick..
private void cell_ButtonClick(object sender, EventArgs e) { RadButtonElement button = sender as RadButtonElement; CustomGridDataCellElement cell = button.Parent as CustomGridDataCellElement; if (button.Tag != null) { int idx = (int)button.Tag; System.Diagnostics.Debug.Write("\n cell.Button" + idx.ToString()); switch (idx) { case 0: break; case 1: break; case 2: break; } } }
Thanks
Francisco
Thank you for sharing your implementation.
The solution is valid and it follows the suggestions made in our Creating Custom Cells documentation article.
Please let me know if you need further assistance.
Regards,
Hristo Merdjanov
Telerik
