首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> .NET 網頁程式設計 >> 關於.NET

WinForms ListBox 項目上下移動擴展方法實作

     編輯:關於.NET

前言

WinForms 原生 ListBox 不支援項目上下移動。本文提供基於 C# 3.0+ 擴展方法的完整實作,支援多選項目移動、邊界檢查與無選項時的回呼處理,程式碼簡潔優雅,可直接複製使用。

核心功能

  • MoveSelectedItems:批次移動所有選中項目(向上/向下)。
  • MoveSelectedItem:移動單一選中項目(預設為當前選中索引)。
  • 自動處理邊界條件(首項無法上移、尾項無法下移)。
  • 支援 Action 回呼處理「無選項」情況。

完整程式碼

public static class ListBoxExtension
{
    // 批次移動,支援無選項回呼
    public static bool MoveSelectedItems(this ListBox listBox, bool isUp, Action noSelectAction)
    {
        if (listBox.SelectedItems.Count > 0)
            return listBox.MoveSelectedItems(isUp);
        else
        {
            noSelectAction();
            return false;
        }
    }

    // 批次移動核心邏輯
    public static bool MoveSelectedItems(this ListBox listBox, bool isUp)
    {
        bool result = true;
        var indices = listBox.SelectedIndices;

        if (isUp)
        {
            if (listBox.SelectedItems.Count > 0 && indices[0] != 0)
            {
                foreach (int i in indices)
                    result &= MoveSelectedItem(listBox, i, true);
            }
        }
        else
        {
            if (listBox.SelectedItems.Count > 0 && indices[indices.Count - 1] != listBox.Items.Count - 1)
            {
                for (int i = indices.Count - 1; i >= 0; i--)
                    result &= MoveSelectedItem(listBox, indices[i], false);
            }
        }
        return result;
    }

    // 單項移動,支援無選項回呼
    public static bool MoveSelectedItem(this ListBox listBox, bool isUp, Action noSelectAction)
    {
        if (listBox.SelectedItems.Count > 0)
            return MoveSelectedItem(listBox, listBox.SelectedIndex, isUp);
        else
        {
            noSelectAction();
            return false;
        }
    }

    // 單項移動(預設當前選中)
    public static bool MoveSelectedItem(this ListBox listBox, bool isUp)
    {
        return MoveSelectedItem(listBox, listBox.SelectedIndex, isUp);
    }

    // 底層單項移動實作
    private static bool MoveSelectedItem(this ListBox listBox, int selectedIndex, bool isUp)
    {
        if (selectedIndex != (isUp ? 0 : listBox.Items.Count - 1))
        {
            object current = listBox.Items[selectedIndex];
            int insertAt = selectedIndex + (isUp ? -1 : 1);

            listBox.Items.RemoveAt(selectedIndex);
            listBox.Items.Insert(insertAt, current);
            listBox.SelectedIndex = insertAt;
            return true;
        }
        return false;
    }
}

使用範例

private void btnUp_Click(object sender, EventArgs e)
{
    this.listBox1.MoveSelectedItems(true, () => 
    {
        MessageBox.Show("請選擇項目");
    });
}

private void btnDown_Click(object sender, EventArgs e)
{
    this.listBox1.MoveSelectedItems(false, () => 
    {
        MessageBox.Show("請選擇項目");
    });
}

設計重點

  1. 反向迭代下移:下移時從最大索引向 0 迭代,避免移動後索引變化影響後續項目。
  2. 正向迭代上移:上移時從最小索引開始,同理避免索引錯亂。
  3. 邊界保護:移動前檢查是否已達首尾,避免例外。
  4. 選中狀態保持:移動後自動將 SelectedIndex 更新至新位置,使用者體驗連貫。

適用版本與擴充

需 C# 3.0+(.NET Framework 3.5+)支援擴展方法與 Lambda 運算式。若專案為 .NET 2.0,可將擴展方法改為靜態工具類別,Lambda 改為匿名委派即可相容。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved