Лучший способ обновить DataGridView при обновлении базового источника данных - PullRequest
52 голосов
/ 31 октября 2008

Каков наилучший способ обновить DataGridView при обновлении базового источника данных?

Я часто обновляю источник данных и хотел показать результат пользователю, как это происходит.

Я сделал что-то вроде этого (и это работает), но обнулить DataGridView.DataSource не похоже на правильный путь.

List<ItemState> itemStates = new List<ItemState>();
dataGridView1.DataSource = itemStates;

for (int i = 0; i < 10; i++) { 
    itemStates.Add(new ItemState { Id = i.ToString() });
    dataGridView1.DataSource = null;
    dataGridView1.DataSource = itemStates;
    System.Threading.Thread.Sleep(500);
}

Ответы [ 7 ]

47 голосов
/ 13 июля 2009

Я столкнулся с этим сам. Моя рекомендация: если у вас есть право собственности на источник данных, не используйте Список . Используйте BindingList . У BindingList есть события, которые срабатывают при добавлении или изменении элементов, а DataGridView автоматически обновляется при возникновении этих событий.

47 голосов
/ 31 октября 2008

Ну, это не намного лучше, чем это. Официально вы должны использовать

dataGridView1.DataSource = typeof(List); 
dataGridView1.DataSource = itemStates;

Это все еще решение типа «очистить / сбросить источник», но мне еще предстоит найти что-то еще, что надежно обновило бы источник данных DGV.

13 голосов
/ 04 декабря 2016

Самое чистое, эффективное и дружественное для парадигмы решение в этом случае заключается в использовании System.Windows.Forms.BindingSource в качестве прокси между вашим списком элементов (источником данных) и вашим DataGridView:

var itemStates = new List<ItemState>();
var bindingSource1 = new System.Windows.Forms.BindingSource { DataSource = itemStates };
dataGridView1.DataSource = bindingSource1;

Затем, при добавлении элементов, используйте Add() метод BindingSource вместо метода Add() вашего списка:

for (var i = 0; i < 10; i++)
{
    bindingSource1.Add(new ItemState { Id = i.ToString() });
    System.Threading.Thread.Sleep(500);
}

Таким образом, вы добавляете элементы в свой список и уведомляете DataGridView об этих дополнениях с той же строкой кода. Нет необходимости сбрасывать DataGridView DataSource каждый раз, когда вы вносите изменения в список.

Стоит также упомянуть, что вы можете поместить BindingSource на форму непосредственно в конструкторе форм Visual Studio и присоединить ее в качестве источника данных к вашему DataGridView, что сохранит вам строку кода в приведенном выше пример, где я делаю это вручную.

2 голосов
/ 11 мая 2015

Observablecollection : представляет собой динамический сбор данных, который предоставляет уведомления когда элементы добавляются, удаляются или когда весь список обновляется. Вы можете перечислить любую коллекцию, которая реализует интерфейс IEnumerable. Тем не менее, чтобы настроить динамические привязки так, чтобы вставки или удаления в коллекция обновляет пользовательский интерфейс автоматически, коллекция должна реализовывать интерфейс INotifyCollectionChanged. Этот интерфейс предоставляет событие CollectionChanged, событие, которое должно вызываться при изменении базовой коллекции.

Observablecollection<ItemState> itemStates = new Observablecollection<ItemState>();

for (int i = 0; i < 10; i++) { 
    itemStates.Add(new ItemState { Id = i.ToString() });
  }
 dataGridView1.DataSource = itemStates;
0 голосов
/ 14 августа 2015

Вы устанавливаете источник данных внутри цикла и спите 500 после каждого добавления. Почему бы просто не добавить к элементам состояния, а затем установить источник данных ПОСЛЕ того, как вы добавили все. Если вы хотите, чтобы поток спал после этого нормально. Первый блок кода здесь - ваш второй блок, который я модифицировал.

for (int i = 0; i < 10; i++) { 
    itemStates.Add(new ItemState { Id = i.ToString() });
    dataGridView1.DataSource = null;
    dataGridView1.DataSource = itemStates;
    System.Threading.Thread.Sleep(500);
}

Измените свой код следующим образом: это намного быстрее.

for (int i = 0; i < 10; i++) { 
    itemStates.Add(new ItemState { Id = i.ToString() });

}
    dataGridView1.DataSource = typeof(List); 
    dataGridView1.DataSource = itemStates;
    System.Threading.Thread.Sleep(500);
0 голосов
/ 11 мая 2015

Это копия моего ответа с ЭТОГО места.

Только нужно снова заполнить сетку данных, как это:

this.XXXTableAdapter.Fill(this.DataSet.XXX);

Если вы используете автоматическое подключение из dataGridView, этот код автоматически создается в Form_Load ()

0 голосов
/ 31 октября 2008

Попробуйте этот код

List itemStates = new List();

for (int i = 0; i < 10; i++)
{ 
    itemStates.Add(new ItemState { Id = i.ToString() });
    dataGridView1.DataSource = itemStates;
    dataGridView1.DataBind();
    System.Threading.Thread.Sleep(500);
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...