
This is a view
public partial class MainView : Form, IMainView { private BindingSource _bsPeople = new BindingSource(); public MainView() { InitializeComponent(); SetBindings(); this.CenterToScreen(); this.Text = nameof(WFApp1); } /// <summary> /// Привязки /// </summary> private void SetBindings() { _dataGridViewPeople.AutoGenerateColumns = false; _dataGridViewPeople.DataSource = _bsPeople; } /// <summary> /// Список людей /// </summary> public List<Person> People { get => _bsPeople.List.Cast<Person>().ToList(); set { _bsPeople.Clear(); foreach (var item in value) { _bsPeople.Add(item); } } } /// <summary> /// Привязка к событию клика по названию столбца /// </summary> private IFormsEventHandler<string> _SortPeople; public IFormsEventHandler<string> SortPeople { set { if (_SortPeople != null) return; _SortPeople = value; _dataGridViewPeople.ColumnHeaderMouseClick += (s, e) => { if (_bsPeople.Count == 0) return; if (e.ColumnIndex == 0) return; //клик по "н/п" //получаем название свойства по названю столбца string cName = GetColumnName(e.ColumnIndex); if (String.IsNullOrEmpty(cName)) return; //вызов обработчика _SortPeople.Handler(s, cName); }; } } private string GetColumnName(int columnIndex) { string result = String.Empty; switch (columnIndex) { case 1: result = nameof(ColumnLastName).Replace("Column", ""); break; case 2: result = nameof(ColumnFirstName).Replace("Column", ""); ; break; case 3: result = nameof(ColumnCity).Replace("Column", ""); ; break; default: break; } return result; } }
This is a presenter
public class MainPresenter : IMainPresenter { public IMainView View { get; private set; } //ctor public MainPresenter(IMainView view) { View = view ?? throw new ArgumentNullException(nameof(view)); View.SortPeople = new ParamEventHandler(OnSortPeople); LoadData(); } /// <summary> /// Обработка события клика по столбцу, сортировка /// </summary> /// <param name="columnName">имя столбца-свойства</param> public void OnSortPeople(string columnName) { //запоминаем первого (первая строка в гриде) var firstPerson = View.People.First(); //получаем данные и сортируем, в реальности сортировку можно //сделать и с помощью соотв.запроса к БД var people = Program.Context.GetPeople(); people.Sort(new PersonComparer(columnName)); //находим такого же и удаляем var samePerson = people.Single(p => p.Id == firstPerson.Id); people.RemoveAt(people.IndexOf(samePerson)); //новая коллекция var nPeople = new List<Person>(); //добавляем первого nPeople.Add(firstPerson); //добавляем остальных отсортированных nPeople.AddRange(people); //пронумеруем SetOrderNumbers(nPeople); //отобразим View.People = nPeople; } private void LoadData() { var people = Program.Context.GetPeople(); //пронумеруем SetOrderNumbers(people); //отобразим View.People = people; } private void SetOrderNumbers(List<Person> people) { for (int i = 1; i < people.Count + 1; i++) { people[i - 1].OrderNumber = i; } } }
Custom comparator such
public class PersonComparer : IComparer<Person> { private readonly string _propName; //ctor public PersonComparer(string propName) { if (String.IsNullOrEmpty(propName)) throw new ArgumentNullException(nameof(propName)); _propName = propName; } public int Compare(Person x, Person y) { int result = 0; switch (_propName) { case "FirstName": result = x.FirstName.CompareTo(y.FirstName); break; case "LastName": result = x.LastName.CompareTo(y.LastName); break; case "City": result = x.City.CompareTo(y.City); break; default: break; } return result; } }
The whole example can be downloaded here.