Як змінити колір рядка в datagridview?


143

Я хотів би змінити колір певного рядка в моєму огляді даних. Рядок слід змінити на червоний, коли значення columncell 7 менше значення в columncell 10. Будь-які пропозиції щодо того, як це досягти?

Відповіді:


192

Вам потрібно провести цикл через рядки в datagridview, а потім порівняти значення стовпців 7 і 10 у кожному рядку.

Спробуйте це:

foreach (DataGridViewRow row in vendorsDataGridView.Rows) 
     if (Convert.ToInt32(row.Cells[7].Value) < Convert.ToInt32(row.Cells[10].Value)) 
     {
         row.DefaultCellStyle.BackColor = Color.Red; 
     }

1
Дякую за допомогу Рікардо. Я спробував запропонований вами код. Я досі не можу змусити його працювати. Ви проти заглянути в цей код і сказати мені, де я помилився? Я початковий студент C #. Я впевнений, що я просто неправильно написав код порівняння. foreach (рядок DataGridView у vendorsDataGridView.Rows) {if (row.Cells [7] .Value is <row.Cells [10] .Value) {dataGridViewTextBoxColumn7.DefaultCellStyle.BackColor = red; } } Я вдячний за твою допомогу. EB
EB.

EB Я додав новий код на основі вказаного вами коду. Ваш синтакс трохи вимкнувся, спробуйте код, який я щойно додав.
Рікардо Санчес

2
Рікардо. Я змінив .text на .value та змінив на DefaultCellstyle.Backcolor = color.red, і код працював !!! Спасибі за ваш час! EB
EB.

60

Я просто досліджував це питання (тому я знаю, що це питання було опубліковане майже 3 роки тому, але, можливо, воно комусь допоможе ...), але здається, що кращим варіантом є розміщення коду всередині RowPrePaintподії, щоб ви не повинні пройти кожен рядок, лише ті, що фарбуються (так що це буде набагато краще при великій кількості даних:

Додайте до події

this.dataGridView1.RowPrePaint 
    += new System.Windows.Forms.DataGridViewRowPrePaintEventHandler(
        this.dataGridView1_RowPrePaint);

Код події

private void dataGridView1_RowPrePaint(object sender, DataGridViewRowPrePaintEventArgs e)
{
    if (Convert.ToInt32(dataGridView1.Rows[e.RowIndex].Cells[7].Text) < Convert.ToInt32(dataGridView1.Rows[e.RowIndex].Cells[10].Text)) 
    {
        dataGridView1.Rows[e.RowIndex].DefaultCellStyle.BackColor = Color.Beige;
    }
}

3
Мені дуже подобається, як ти вирішуєш проблему в корені, а не чекати, поки все не зафарбується. Це дуже "поза межами" підходу. Більшість людей
воліє

Окрім того, що набагато швидше, це також допомагає робити це в потрібний час. У мене виникли проблеми з тим, що мої рядки не забарвлювалися, ймовірно, тому, що я встановив колір не в той час. При такому підході це гарантовано станеться в потрібний час.
sanderd17

1
Це добре працює. Також після сортування її оновлення в правильному порядку.
macmuri

24

Ви шукаєте CellFormattingподію.
Ось приклад.


2
Відмінність цього підходу полягає в тому, що кожну клітинку порівнюватимуть на відміну від лише однієї. Це може бути проблемою з продуктивністю, якщо у вас є кілька сотень комірок.
Рікардо Санчес

21

У мене також виникли проблеми із зміною кольору тексту - я ніколи не бачив зміни кольору.

Поки я не додав код, щоб змінити колір тексту для події DataBindingsCompleteдля DataGridView. Після цього це спрацювало.

Сподіваюся, це допоможе людям, які стикаються з тією ж проблемою.


текстовий колір не змінюється, коли перезапис onLoad (..) або подія. DataBindingsComplete набагато краще місце для настройки кольорів рядків.
Тимофій

13

Щось на кшталт наступного ... припускаючи, що значення в клітинках є Цілими числами.

foreach (DataGridViewRow dgvr in myDGV.Rows)
{
  if (dgvr.Cells[7].Value < dgvr.Cells[10].Value)
  {
    dgvr.DefaultCellStyle.ForeColor = Color.Red;
  }
}

неперевірений, тому вибачте за будь-яку помилку.

Якщо вам відомий конкретний рядок, ви можете пропустити ітерацію:

if (myDGV.Rows[theRowIndex].Cells[7].Value < myDGV.Rows[theRowIndex].Cells[10].Value)
{
  dgvr.DefaultCellStyle.ForeColor = Color.Red;
}

Дякую за твою допомогу. Ваша пропозиція є найближчим до мене, щоб вирішити проблему. Але я постійно отримую помилку: "Значення" не існує в контексті, або "Клітини" не існує в контексті. Намагаючись розібратися в цьому ...
ЕБ.

цей рядок коду (dgvr.Cells [7] .Value <dgvr.Cells [10] .Value) дає мені цю помилку Оператор '<' не може бути застосований до операндів типу 'object' та 'object'
EB.

Потім киньте їх до Integer. :-) щось на кшталт: Convert.ToInt32 (dvgr.Cells [7] .Value) <Convert.ToInt32 (dgvr.Cells [10] .Value)
Demi

8

Деякі люди люблять використовувати Paint, CellPaintingабо CellFormattingподії, але зверніть увагу , що зміна стилю в цих подіях викликають рекурсивні виклики. Якщо ви DataBindingCompleteйого використовуєте, він виконається лише один раз. Аргументом CellFormattingє те, що він викликається лише у видимих ​​комірках, тому вам не доведеться форматувати невидимі комірки, а форматувати їх кілька разів.


5

Ви можете змінити Backcolorрядок за рядком , використовуючи ваш condition.and виклик цієї функції після застосування Datasourceв DatagridView.

Тут функція для цього. Просто скопіюйте це і поставте після цьогоDatabind

private void ChangeRowColor()
{
    for (int i = 0; i < gvItem.Rows.Count; i++)
    {
        if (BindList[i].MainID == 0 && !BindList[i].SchemeID.HasValue)
            gvItem.Rows[i].DefaultCellStyle.BackColor = ColorTranslator.FromHtml("#C9CADD");
        else if (BindList[i].MainID > 0 && !BindList[i].SchemeID.HasValue)
            gvItem.Rows[i].DefaultCellStyle.BackColor = ColorTranslator.FromHtml("#DDC9C9");
        else if (BindList[i].MainID > 0)
            gvItem.Rows[i].DefaultCellStyle.BackColor = ColorTranslator.FromHtml("#D5E8D7");
        else
            gvItem.Rows[i].DefaultCellStyle.BackColor = Color.White;
    }
}

3
private void dtGrdVwRFIDTags_DataSourceChanged(object sender, EventArgs e)
{
    dtGrdVwRFIDTags.Refresh();
    this.dtGrdVwRFIDTags.Columns[1].Visible = false;

    foreach (DataGridViewRow row in this.dtGrdVwRFIDTags.Rows)
    {
        if (row.Cells["TagStatus"].Value != null 
            && row.Cells["TagStatus"].Value.ToString() == "Lost" 
            || row.Cells["TagStatus"].Value != null 
            && row.Cells["TagStatus"].Value.ToString() == "Damaged" 
            || row.Cells["TagStatus"].Value != null 
            && row.Cells["TagStatus"].Value.ToString() == "Discarded")
        {
            row.DefaultCellStyle.BackColor = Color.LightGray;
            row.DefaultCellStyle.Font = new Font("Tahoma", 8, FontStyle.Bold);
        }
        else
        {
            row.DefaultCellStyle.BackColor = Color.Ivory;
        }
    }  

    //for (int i= 0 ; i<dtGrdVwRFIDTags.Rows.Count - 1; i++)
    //{
    //    if (dtGrdVwRFIDTags.Rows[i].Cells[3].Value.ToString() == "Damaged")
    //    {
    //        dtGrdVwRFIDTags.Rows[i].Cells["TagStatus"].Style.BackColor = Color.Red;                   
    //    }
    //}
}

2

Це моє рішення змінити колір на dataGridView із зв'язуваннямDataSource:

private void dataGridViewECO_DataBindingComplete(object sender, DataGridViewBindingCompleteEventArgs e)
{            

    if (e.ListChangedType != ListChangedType.ItemDeleted)
    {

        DataGridViewCellStyle green = this.dataGridViewECO.DefaultCellStyle.Clone();
        green.BackColor = Color.Green;

        DataGridViewCellStyle gray = this.dataGridViewECO.DefaultCellStyle.Clone();
        gray.BackColor = Color.LightGray;



        foreach (DataGridViewRow r in this.dataGridViewECO.Rows)
        {

            if (r.Cells[8].Value != null)
            {

                String stato = r.Cells[8].Value.ToString();


                if (!" Open ".Equals(stato))
                {
                    r.DefaultCellStyle = gray;
                }
                else
                {
                    r.DefaultCellStyle = green;
                }
            }

        }

    }
}

1

Якщо ви прив’яжете до (колекції) конкретних об'єктів, ви можете отримати цей конкретний об'єкт через властивість DataBoundItem рядка. (Щоб уникнути перевірки магічних рядків у комірці та використання "реальних" властивостей об'єкта)

Приклад скелета нижче:

DTO / POCO

public class Employee
{
    public int EmployeeKey {get;set;}

    public string LastName {get;set;}

    public string FirstName {get;set;}

    public bool IsActive {get;set;}
}       

Прив’язка до огляду даних

    private void BindData(ICollection<Employee> emps)
    {
        System.ComponentModel.BindingList<Employee> bindList = new System.ComponentModel.BindingList<Employee>(emps.OrderBy(emp => emp.LastName).ThenBy(emp => emp.FirstName).ToList());
        this.dgvMyDataGridView.DataSource = bindList;
    }       

то обробник подій та отримання конкретного об'єкта (замість DataGridRow та / або комірок)

        private void dgvMyDataGridView_RowPrePaint(object sender, DataGridViewRowPrePaintEventArgs e)
        {
            Employee concreteSelectedRowItem = this.dgvMyDataGridView.Rows[e.RowIndex].DataBoundItem as Employee;
            if (null != concreteSelectedRowItem && !concreteSelectedRowItem.IsActive)
            {
                dgvMyDataGridView.Rows[e.RowIndex].DefaultCellStyle.BackColor = Color.LightGray;
            }
        }

0

Я зазвичай люблю використовувати для цього подію GridView.RowDataBound.

protected void OrdersGridView_RowDataBound(object sender, GridViewRowEventArgs e)
{
    if (e.Row.RowType == DataControlRowType.DataRow)
    {
        e.Row.ForeColor = System.Drawing.Color.Red;
    }
}

1
Його просять DatagridView у програмі Window. А ваша відповідь - про GridView Web.
Пратік 1020

0

Працює над Visual Studio 2010. (Я спробував це і працює!) Він пофарбує весь ваш ряд.

  1. Створіть кнопку для datagridview.
  2. Створіть CellClickподію та поставте наступний рядок коду всередині неї.

if (dataGridView3.Columns[e.ColumnIndex].Index.Equals(0)    
{
    dataGridView3.Rows[e.RowIndex].DefaultCellStyle.BackColor = Color.Beige;
}

0

Ви не згадали, як змінюється значення. Я використовував подібну функціональність, коли користувач вводить значення. тобто вхід і вихід з режиму редагування.

Використання події CellEndEdit datagridview.

private void dgMapTable_CellEndEdit(object sender, DataGridViewCellEventArgs e)
{
    double newInteger;

    if (double.TryParse(dgMapTable[e.ColumnIndex,e.RowIndex].Value.ToString(), out newInteger)
    {
        if (newInteger < 0 || newInteger > 50)
        {
            dgMapTable[e.ColumnIndex, e.RowIndex].Style.BackColor = Color.Red; 

            dgMapTable[e.ColumnIndex, e.RowIndex].ErrorText 
                = "Keep value in Range:" + "0 to " + "50";
        }
    }                               
}

Ви можете додати логіку для очищення сповіщення про помилку аналогічним чином.

якщо у вашому випадку, якщо дані завантажуються програмно, тоді подія CellLeave може використовуватися з тим же кодом.


0

За допомогою цього коду ви змінюєте лише кольори рядків, у яких значенням стовпця є нульовий колір інших рядків, як і раніше, за замовчуванням.

       foreach (DataGridViewRow row in dataGridView1.Rows)
                {
                    if (row.Cells["columnname"].Value != null)
                    {
                        dataGridView1.AlternatingRowsDefaultCellStyle.BackColor = Color.MistyRose;
                    }
                 }

0

Лише зауваження про налаштування DefaultCellStyle.BackColor... ви не можете встановити його жодне прозоре значення, крім Color.Empty. Це значення за замовчуванням. Це хибно означає (для мене, все одно), що прозорі кольори в порядку. Їх немає. Кожен рядок, який я встановив на прозорий колір, просто малює колір виділених рядків.

Я витратив цілком занадто багато часу, бивши головою об стіну над цим питанням.


0

Я приземлився тут, шукаючи рішення для випадку, коли я не використовую прив'язку даних. Ніщо не працювало для мене, але я отримав це врешті з:

dataGridView.Columns.Clear(); 
dataGridView.Rows.Clear();
dataGridView.Refresh();

0

Якщо ви є другим найдемонтованішим розробником на планеті (я є найглухішим), всі вищезазначені рішення, здається, працюють: CellFormatting, DataSourceChanged і RowPrePaint. Я віддаю перевагу RowPrePaint.

Я боровся з цим (занадто довго), тому що мені потрібно було замінити свої SelectionBackColor та SelectionForeColor замість BackColor та ForeColor, коли я змінював вибраний рядок.


0
int counter = gridEstimateSales.Rows.Count;

for (int i = 0; i < counter; i++)
{
    if (i == counter-1)
    {
        //this is where your LAST LINE code goes
        //row.DefaultCellStyle.BackColor = Color.Yellow;
        gridEstimateSales.Rows[i].DefaultCellStyle.BackColor = Color.Red;
    }
    else
    {
        //this is your normal code NOT LAST LINE
        //row.DefaultCellStyle.BackColor = Color.Red;
        gridEstimateSales.Rows[i].DefaultCellStyle.BackColor = Color.White;
    }
}
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.