星期日, 2月 18, 2018

[C#] DataGridView - 使用 IComparer 自訂排序

這篇 MSDN 文章 - 如何:自訂 Windows Form DataGridView 控制項的排序 的第三個範例:使用 IComparer 介面的自訂排序,就單純把 Code Copy Paste 下來,看看 run 的效果

MSDN 上針對 Sort(IComparer) 說明
Sort(IComparer) 方法多載會使用實作 IComparer 介面之類別的執行個體做為參數。 當您想要提供自訂排序 (例如,當資料行中的值沒有自然排序次序時或當自然排序次序不適用時),這個多載會非常有用。 在這種情況下,您不能使用自動排序,但可能還是想要使用者依按一下資料行行首來排序。 若不使用資料行行首做為選取範圍
Project

[C#] DataGridView - 使用 IComparer 自訂排序-5

Layout

[C#] DataGridView - 使用 IComparer 自訂排序-1



RowComparer
using System.Collections;
using System.Windows.Forms;

namespace OrderIComparer
{
    public class RowComparer : IComparer
    {
        private static int sortOrderModifier = 1;

        public RowComparer(SortOrder sortOrder)
        {
            if (sortOrder == SortOrder.Descending)
            {
                sortOrderModifier = -1;
            }
            else if (sortOrder == SortOrder.Ascending)
            {
                sortOrderModifier = 1;
            }
        }

        public int Compare(object x, object y)
        {
            DataGridViewRow DataGridViewRow1 = (DataGridViewRow)x;
            DataGridViewRow DataGridViewRow2 = (DataGridViewRow)y;

            // Try to sort based on the Last Name column.
            int CompareResult = string.Compare(
                DataGridViewRow1.Cells[1].Value.ToString(),
                DataGridViewRow2.Cells[1].Value.ToString());

            // If the Last Names are equal, sort based on the First Name.
            if (CompareResult == 0)
            {
                CompareResult = string.Compare(
                    DataGridViewRow1.Cells[0].Value.ToString(),
                    DataGridViewRow2.Cells[0].Value.ToString());
            }
            return CompareResult * sortOrderModifier;
        }
    }
}
>
Code
namespace OrderIComparer
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();

            flowLayoutPanel1.FlowDirection = FlowDirection.TopDown;
            flowLayoutPanel1.AutoSize = true;

            rdoAscending.Checked = true;

            dataGridView1.AutoGenerateColumns = false;
            dataGridView1.AllowUserToAddRows = false;
            dataGridView1.MultiSelect = false;
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            PopulateDataGridView();
        }

        private void PopulateDataGridView()
        {
            dataGridView1.Size = new Size(300, 300);

            // Set the properties of the DataGridView columns.
            dataGridView1.Columns.Add(new DataGridViewTextBoxColumn()
            {
                HeaderText = "First Name",
                Name = "ColFirst",
                SortMode = DataGridViewColumnSortMode.Programmatic
            });

            dataGridView1.Columns.Add(new DataGridViewTextBoxColumn()
            {
                HeaderText = "Last Name",
                Name = "ColLast",
                SortMode = DataGridViewColumnSortMode.Programmatic
            });

            // Add rows of data to the DataGridView.
            dataGridView1.Rows.Add(new string[] { "Peter", "Parker" });
            dataGridView1.Rows.Add(new string[] { "James", "Jameson" });
            dataGridView1.Rows.Add(new string[] { "May", "Parker" });
            dataGridView1.Rows.Add(new string[] { "Mary", "Watson" });
            dataGridView1.Rows.Add(new string[] { "Eddie", "Brock" });
        }

        private void btnSort_Click(object sender, EventArgs e)
        {
            if (rdoAscending.Checked == true)
            {
                dataGridView1.Sort(new RowComparer(SortOrder.Ascending));
            }
            else if (rdoDescending.Checked == true)
            {
                dataGridView1.Sort(new RowComparer(SortOrder.Descending));
            }
        }
    }
}
執行結果

[C#] DataGridView - 使用 IComparer 自訂排序-4

MSDN 說明
只有在 DataGridView 控制項未繫結至外部資料來源,且 VirtualMode 屬性為 false 時,Sort(IComparer) 方法多載才能作用。 若要自訂繫結至外部資料來源之資料行的排序,必須使用由資料來源所提供的排序作業。 在虛擬模式中,您必須為未繫結的資料行自行提供排序作業。
設定 DataGridView.DataSource 會出現下圖錯誤訊息

[C#] DataGridView - 使用 IComparer 自訂排序-2

設定 VirtualMode 會出現下圖錯誤訊息

[C#] DataGridView - 使用 IComparer 自訂排序-3

沒有留言:

張貼留言