我在C#2008系统Windows窗体的LargeIcon视图中有一个ListView。
现在,我想将此ListView的一个项目移到同一ListView中的另一个位置上-我们将其称为“拖放”或“商品重新排序”或其他。 VB 6可以做到这一点,并且可以在任何listView中自动执行此操作。

C#似乎没有此功能,或者需要先对其进行编码。对于编码,我没有经验,我在互联网上的研究中也没有找到答案。我发现只有一个“覆盖过程”无效。

我不需要任何其他ListView控件(例如ObjectListView或其他对象),也不需要重写过程或设计新的ListView控件。我想按原样在Microsoft给定的ListView控件中处理它。任何想法。我相信代码会受到高度赞赏
除非它是一个非常简单的单行代码,否则我不能独自完成它。

PS:如果需要移动该物品,则需要该物品的所有属性(文本,标签,图像键,背景色,前景色,名称,工具提示文本等)。我不知道如何做到这一点。
我发现了一个提示:存在删除一个项目(称为.Remove())并插入名为.Insert()的提示。但是有了这些信息,我仍然无法通过鼠标完成项目的“移动”。
我认为listView的所有DragEvent都在这里起作用,但是我不知道如何使用它们以及如何将所选项目(listView1.SelectedItems)复制到正确的位置,并且需要首先获得该位置。

最佳答案

实际上,您谈论的功能不受Winforms而非C#支持。 C#与这种功能无关。它是一种UI技术功能,而不是语言功能。但是,要解决此问题,我们在这里几乎没有代码。它支持用于每个PositionListViewItem属性(在LargeIcon视图中)。另一个重要属性是AutoArrange,应将其设置为false以使Position生效。这是代码:

ListViewItem heldDownItem;
Point heldDownPoint;
//MouseDown event handler for your listView1
private void listView1_MouseDown(object sender, MouseEventArgs e)
{
    //listView1.AutoArrange = false;
    heldDownItem = listView1.GetItemAt(e.X,e.Y);
    if (heldDownItem != null) {
      heldDownPoint = new Point(e.X - heldDownItem.Position.X,
                                e.Y - heldDownItem.Position.Y);
    }
}
//MouseMove event handler for your listView1
private void listView1_MouseMove(object sender, MouseEventArgs e)
{
    if (heldDownItem != null){
        heldDownItem.Position = new Point(e.Location.X - heldDownPoint.X,
                                          e.Location.Y - heldDownPoint.Y);
    }
}
//MouseUp event handler for your listView1
private void listView1_MouseUp(object sender, MouseEventArgs e)
{
    heldDownItem = null;
    //listView1.AutoArrange = true;
}


注意:如您所见,我在此处放置2条注释的代码行listView1.AutoArrange,如果您想reorder而不是更改ListViewItem位置,则可以取消注释这些行。我在这里注意到一些闪烁(当您处理winforms ListView时这是正常的),因此您应该使用此代码(可以放置在表单构造函数中)启用DoubleBuffered

typeof(Control).GetProperty("DoubleBuffered",
                             System.Reflection.BindingFlags.NonPublic |
                             System.Reflection.BindingFlags.Instance)
               .SetValue(listView1, true, null);

09-06 05:03