Добавить несколько отмеченных списков в столбцы таблицы данных - PullRequest
0 голосов
/ 18 января 2011

Поскольку мы можем добавить один флажок к столбцу в столбце представления таблицы данных, но возможно ли добавить флажок со списком проверок в представление таблицы данных, цель состоит в том, чтобы иметь ячейку, имеющую несколько флажков.

Как мы можем их добавить?

Как мы можем получить доступ к их свойствам, таким как текст и галочка?

Получил ответ, но не могу понять http://social.msdn.microsoft.com/Forums/en/winformsdatacontrols/thread/6c68a44c-c4ab-4caf-94e9-249ec63a90d0

Ответы [ 2 ]

2 голосов
/ 03 марта 2015

Прочтите мои комментарии внизу этого ответа, прежде чем использовать этот код.


По вопросу как мы можем получить доступ к тексту и флажкам из этого столбца CheckListBox DataGridView :
public class CheckedListBoxColumn : DataGridViewColumn
{
    public CheckedListBoxColumn()
        : base(new CheckedListBoxCell())
    {
    }

    public override DataGridViewCell CellTemplate
    {
        get
        {
            return base.CellTemplate;
        }
        set
        {
            if (value != null &&
                !value.GetType().IsAssignableFrom(typeof(CheckedListBoxCell)))
            {
                throw new InvalidCastException("Must be a CheckedListBoxCell");
            }
            base.CellTemplate = value;
        }
    }
}

public class CheckedListBoxCell : DataGridViewCell
{
    public CheckedListBoxCell()
        : base()
    {

    }

    public override void InitializeEditingControl(int rowIndex, object
        initialFormattedValue, DataGridViewCellStyle dataGridViewCellStyle)
    {
        // Set the value of the editing control to the current cell value.  
        base.InitializeEditingControl(rowIndex, initialFormattedValue,
            dataGridViewCellStyle);
        CheckedListBoxEditingControl ctl =
            DataGridView.EditingControl as CheckedListBoxEditingControl;
        InitializeCheckedListBox(ctl, (ICollection)this.FormattedValue);
    }
    private void InitializeCheckedListBox(CheckedListBox ctrl, ICollection value)
    {
        ctrl.Items.Clear();
        foreach (object obj in value)
        {
            ctrl.Items.Add(obj.ToString());
        }
        ctrl.Tag = this.Value;
    }
    public override Type EditType
    {
        get
        {
            return typeof(CheckedListBoxEditingControl);
        }
    }
    protected override object GetFormattedValue(object value, int rowIndex, ref DataGridViewCellStyle cellStyle, System.ComponentModel.TypeConverter valueTypeConverter, System.ComponentModel.TypeConverter formattedValueTypeConverter, DataGridViewDataErrorContexts context)
    {
        if (value == null)
        {
            return new List<object>();
        }
        return base.GetFormattedValue(value, rowIndex, ref cellStyle, valueTypeConverter, formattedValueTypeConverter, context);
    }
    public override Type FormattedValueType
    {
        get
        {
            return typeof(ICollection);
        }
    }
    public override Type ValueType
    {
        get
        {
            return typeof(ICollection);
        }
    }
    private CheckedListBox internalControl;

    protected override void Paint(System.Drawing.Graphics graphics, System.Drawing.Rectangle clipBounds, System.Drawing.Rectangle cellBounds, int rowIndex, DataGridViewElementStates cellState, object value, object formattedValue, string errorText, DataGridViewCellStyle cellStyle, DataGridViewAdvancedBorderStyle advancedBorderStyle, DataGridViewPaintParts paintParts)
    {
        base.Paint(graphics, clipBounds, cellBounds, rowIndex, cellState, value, formattedValue, errorText, cellStyle, advancedBorderStyle, paintParts);
        graphics.FillRectangle(new SolidBrush(cellStyle.BackColor), cellBounds);

        if (internalControl == null)
        {
            internalControl = new CheckedListBox();
        }
        internalControl.Items.Clear();
        ICollection collection = value as ICollection;
        if (collection != null)
        {
            foreach (object obj in collection)
            {
                internalControl.Items.Add(obj);
            }
            Bitmap bmp = new Bitmap(cellBounds.Width, cellBounds.Height);
            internalControl.DrawToBitmap(bmp, new Rectangle(0, 0, bmp.Width, bmp.Height));
            graphics.DrawImage(bmp, cellBounds, new Rectangle(0, 0, bmp.Width, bmp.Height), GraphicsUnit.Pixel);
        }
    }
    protected override void OnClick(DataGridViewCellEventArgs e)
    {
        this.DataGridView.BeginEdit(false);
        base.OnClick(e);
    }
}

class CheckedListBoxEditingControl : CheckedListBox, IDataGridViewEditingControl
{
    DataGridView dataGridView;
    private bool valueChanged = false;
    int rowIndex;

    public CheckedListBoxEditingControl()
    {

    }

    // Implements the IDataGridViewEditingControl.EditingControlFormattedValue   
    // property.  
    public object EditingControlFormattedValue
    {
        get
        {
            return this.Tag;
        }
        set
        {
            //  this.Tag = value;  
        }
    }

    // Implements the   
    // IDataGridViewEditingControl.GetEditingControlFormattedValue method.  
    public object GetEditingControlFormattedValue(
        DataGridViewDataErrorContexts context)
    {
        return EditingControlFormattedValue;
    }

    // Implements the   
    // IDataGridViewEditingControl.ApplyCellStyleToEditingControl method.  
    public void ApplyCellStyleToEditingControl(
        DataGridViewCellStyle dataGridViewCellStyle)
    {
        this.Font = dataGridViewCellStyle.Font;
        this.ForeColor = dataGridViewCellStyle.ForeColor;
        this.BackColor = dataGridViewCellStyle.BackColor;
    }

    // Implements the IDataGridViewEditingControl.EditingControlRowIndex   
    // property.  
    public int EditingControlRowIndex
    {
        get
        {
            return rowIndex;
        }
        set
        {
            rowIndex = value;
        }
    }

    // Implements the IDataGridViewEditingControl.EditingControlWantsInputKey   
    // method.  
    public bool EditingControlWantsInputKey(
        Keys key, bool dataGridViewWantsInputKey)
    {
        // Let the DateTimePicker handle the keys listed.  
        switch (key & Keys.KeyCode)
        {
            case Keys.Left:
            case Keys.Up:
            case Keys.Down:
            case Keys.Right:
            case Keys.Home:
            case Keys.End:
            case Keys.PageDown:
            case Keys.PageUp:
                return true;
            default:
                return !dataGridViewWantsInputKey;
        }
    }

    // Implements the IDataGridViewEditingControl.PrepareEditingControlForEdit   
    // method.  
    public void PrepareEditingControlForEdit(bool selectAll)
    {
        // No preparation needs to be done.  
    }

    // Implements the IDataGridViewEditingControl  
    // .RepositionEditingControlOnValueChange property.  
    public bool RepositionEditingControlOnValueChange
    {
        get
        {
            return false;
        }
    }

    // Implements the IDataGridViewEditingControl  
    // .EditingControlDataGridView property.  
public DataGridView EditingControlDataGridView
{
    get
    {
        return dataGridView;
    }
    set
    {
        dataGridView = value;
    }
}

// Implements the IDataGridViewEditingControl  
// .EditingControlValueChanged property.  
public bool EditingControlValueChanged
{
    get
    {
        return valueChanged;
    }
    set
    {
        valueChanged = value;
    }
}

// Implements the IDataGridViewEditingControl  
// .EditingPanelCursor property.  
public Cursor EditingPanelCursor
{
    get
    {
        return base.Cursor;
    }
}
}    

Интересное сообщение в блоге посвящено проблемам этого класса: http://dotnetgenetics.blogspot.com.au/2014/01/custom-checkedlistbox-datagridview.html

Добавьте свойство в класс CheckedListBoxCell для извлечения отмеченных элементов:

 public ICollection CheckedItems
 {
    get
    {
        if (internalControl == null)
            return null;
        else
        {
            if (internalControl != null)
            {
                if (internalControl.CheckedItems.Count > 0)
                {
                    return internalControl.CheckedItems;
                }
                else
                {
                    if ((CheckedListBox)this.DataGridView.Rows[RowIndex].Cells[ColumnIndex].DataGridView.EditingControl != null)
                    {
                        CheckedListBox checks = (CheckedListBox)this.DataGridView.Rows[RowIndex].Cells[ColumnIndex].DataGridView.EditingControl;
                        if (checks.CheckedItems.Count > 0)
                            return checks.CheckedItems;
                        else
                            return null;
                    }
                    else
                        return null;
                }
            }
            else
            {
                return null;
            }
        }
    }
}  

Это способ получения проверенных пунктов.

 private void btnShow_Click(object sender, EventArgs e)  
 {  
   StringBuilder builder = new StringBuilder();  
   foreach (DataGridViewRow item in dgCheckListColumn1.Rows)  
   {  
     DataGridViewCell cell = item.Cells[1];  
     if (((cell as CheckedListBoxCell).CheckedItems != null))  
     {  
       if (((cell as CheckedListBoxCell).CheckedItems.Count > 0))  
       {  
         foreach (var checkItem in ((cell as CheckedListBoxCell).CheckedItems))  
         {  
           builder.AppendLine(String.Format("Row {0} : item: {1}", item.Index + 1, checkItem.ToString()));  
         }  
         builder.AppendLine(Environment.NewLine);  
       }   
     }  
   }  
   MessageBox.Show("Checked Items: \n" + builder.ToString());  
 }  


Мой взгляд на все это - его дерьмо - выглядит дерьмом и ведет себя как дерьмо .. даже чувствует себя дерьмом:

enter image description here


ИМХО, гораздо лучше подключиться к событию щелчка ячейки DataGridView и открыть CheckedListbox:
private void dataGridView1_CellClick(object sender, DataGridViewCellEventArgs e)
{
    if (e.ColumnIndex == 1)
    {
        int RowHeight1 = DataGridView1.Rows[e.RowIndex].Height;
        Rectangle CellRectangle1 = DataGridView1.GetCellDisplayRectangle(e.ColumnIndex, e.RowIndex, false);

        CellRectangle1.X += DataGridView1.Left;
        CellRectangle1.Y += DataGridView1.Top + RowHeight1;

        Point DisplayPoint1 = PointToScreen(new Point(CellRectangle1.X, CellRectangle1.Y));
        checkedListBox1.Left = CellRectangle1.X;
        checkedListBox1.Top = CellRectangle1.Y;
    }
}

enter image description here

0 голосов
/ 18 января 2011

Вы можете сделать это, создав собственный столбец DataGridView. Есть много статей в Интернете, которые демонстрируют это; вот один пример . Предоставьте флажки как свойства для доступа к их свойствам.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...