首页 文章

ListBox选择所有项目

提问于
浏览
23

单击CheckBox时,我需要选择ListBox中的所有项目 . 是否可以使用一行代码选择ListBox中的所有项目?或者我是否必须遍历所有项目并将其中的每一项设置为true?

谢谢 :)

12 回答

  • 1

    我想你必须在这里循环 . 一次选择所有项目是一个非常具体(可能很少见)的用例,开箱即用提供该功能毫无意义 . 此外,无论如何,循环将只有两行代码 .

  • 8

    事实是 ListBox.Items 是一个普通的对象集合并返回普通的无类型对象,这些对象不能被多选(默认情况下) .

    如果您想多选所有项目,那么这将有效:

    for (int i = 0; i < myListBox.Items.Count;i++)
       {
           myListBox.SetSelected(i, true);
       }
    
  • 61

    据我所知,使用任何.NET方法选择大量项目远比进行直接PInvoke调用慢,将LB_SETSEL消息(0x185)传递给控件,并带有一个标志,指示是否要选择(1)或取消选择(0)以及魔术值(-1),表示更改应适用于所有项目 .

    [DllImport("user32.dll", EntryPoint = "SendMessage")]
      internal static extern IntPtr SendMessage(IntPtr hWnd, UInt32 msg, IntPtr wParam, IntPtr lParam);
    
      // Select All
      SendMessage(listBox.Handle, 0x185, (IntPtr)1, (IntPtr)(-1));
    
      // Unselect All
      SendMessage(listBox.Handle, 0x185, (IntPtr)0, (IntPtr)(-1));
    
  • 0

    我已经看到了许多(类似的)答案,这些答案在逻辑上都是一样的,我很困惑为什么他们都不适合我 . 关键是将列表框的 SelectionMode 设置为 SelectionMode.MultiSimple . 它不适用于 SelectionMode.MultiExtended . 考虑到在列表框中选择多个项目,您将选择模式设置为多个模式,并且大多数人都采用传统的 MultiExtended 样式,这个答案应该有很多帮助 . 而且不是 foreach ,而是 for .

    你应该这样做:

    lb.SelectionMode = SelectionMode.MultiSimple;
    for (int i = 0; i < lb.Items.Count; i++)
        lb.SetSelected(i, true);
    lb.SelectionMode = //back to what you want
    

    要么

    lb.SelectionMode = SelectionMode.MultiSimple;
    for (int i = 0; i < lb.Items.Count; i++)
        lb.SelectedIndices.Add(i);
    lb.SelectionMode = //back to what you want
    
  • -4

    我使用Mika的解决方案,但如果你有数以千计的物品,这可能会非常慢 . 为了大幅提高速度,您可以暂时关闭可见性 . 在您可能怀疑的操作过程中,列表框实际上不会消失,但在我的情况下,选择的速度至少快10倍 .

    myListBox.Visible = false;
    for (int i = 0; i < myListBox.Items.Count;i++)
    {
        myListBox.SetSelected(i, true);
    }
    myListBox.Visible = true;
    
  • 1

    在此构造函数中,您需要启用所需文本框的多选模式( MultiExtended ) .

    public Form1()
    {
        InitializeComponent();
        listBox1.SelectionMode = SelectionMode.MultiExtended;
        listBox2.SelectionMode = SelectionMode.MultiExtended;
    }
    

    在此之后,使用循环选择所有内容:

    private void selectAll_Click(object sender, EventArgs e)
    {
        for (int val = 0; val < listBox1.Items.Count; val++)
        {
            listBox1.SetSelected(val, true);
        }
    }
    

    我测试了它 . 有用 . 您也可以使用 [CTRL/SHIFT] button + left click 单独选择项目 .

  • 1

    Select All 绝对可以直接使用:

    $("#ListBoxID option").prop("selected", true);
    
  • 0

    我知道这个问题是用.NET 2.0标记的,但如果您在3.5中可以使用LINQ,则可以执行以下操作:

    ASP.NET WebForms

    var selected = listBox.Items.Cast<System.Web.UI.WebControls.ListItem>().All(i => i.Selected = true);
    

    WinForms

    var selected = listBox.SelectedItems.Cast<int>().ToArray();
    
  • 0

    如果您有许多(100)个项目,这绝对不是很好,但比循环快得多:选择列表框并模拟[home]和[shift] [end]的键输入

    lb.BeginUpdate();
    lb.Select();
    SendKeys.Send("{Home}");
    SendKeys.Send("+{End}");
    lb.EndUpdate();
    

    编辑:我猜测只适用于SelectionMode.MultiExtended

    DoubleEDit:也要注意,这对于之后使用lb.selecteditems执行的代码来说可能太慢了,但是对于用户将单击的[Select All]按钮可能很有用 .

  • 1

    在我的情况下,我有10k项目,基本循环方法花了将近一分钟完成 . 使用@DiogoNeves回答并扩展它我希望能够选择全部(Ctrl A)和复制(Ctrl C) . 我处理了这两种方式 . 我使用BeginUpdate()和EndUpdate()来推迟绘图,但我还添加了一个直接复制全部(Ctrl Shift C),它甚至在复制前都没有选择项目 .

    private static void HandleListBoxKeyEvents(object sender, KeyEventArgs e)
    {
        var lb = sender as ListBox;
        // if copy
        if (e.Control && e.KeyCode == Keys.C)
        {
            // if shift is also down, copy everything!
            var itemstocopy = e.Shift ? lb.Items.Cast<object>() : lb.SelectedItems.Cast<object>();
            // build clipboard buffer
            var copy_buffer = new StringBuilder();
            foreach (object item in itemstocopy)
                copy_buffer.AppendLine(item?.ToString());
            if (copy_buffer.Length > 0)
                Clipboard.SetText(copy_buffer.ToString());
        }
        // if select all
        else if (e.Control && e.KeyCode == Keys.A)
        {
            lb.BeginUpdate();
            for (var i = 0; i < lb.Items.Count; i++)
                lb.SetSelected(i, true);
            lb.EndUpdate();
        }
    }
    
  • 8

    我将nawfal的想法添加到我已经拥有的内容中,这也是使用'BeginUpdate' . 另外,视图位置也保持不变,正如用户所期望的那样 . 对我来说,这似乎解决了所有问题:

    public void SelectAll()
    {
        bool prevBusy = MouseHelper.IsBusy;
        MouseHelper.IsBusy = true;
        int topIndex = TopIndex;
    
        // BUG: In 'SelectionMode.MultiExtended' the box gets crazy
        SelectionMode previousMode = this.SelectionMode;
        this.SelectionMode = SelectionMode.MultiSimple;
    
        this.BeginUpdate();
    
        for (int i = 0; i < Items.Count; i++)
        {
            SelectedIndices.Add(i);
        }
    
        this.EndUpdate();
        this.SelectionMode = previousMode;
    
        TopIndex = topIndex;
        MouseHelper.IsBusy = prevBusy;
    }
    
  • 4
    private void Button_Click(object sender, RoutedEventArgs e)
        {
    
                listbox.SelectAll();
    
        }
    

相关问题