[VB.NET]Drag'n'Drop INNERHALB eines ListViews

Hi Freunde!

Ich verzweifle! Ich möchte Einträge in einem Listview (einzelne und mehrere) verschieben mittels Drag’n’Drop. Ich habe das Netz abgesucht, aber nichts gefunden was mir hilft! NICHTS KLAPPT!!!

Das ganze soll so ähnlich sein wie das Title-Sortieren im Windows Media-Player oder im Winamp. WAS MUSS ICH TUN? Wo finde ich Code-Beispiele?

Was ich nicht suche: Verschieben über mehrere Forms, Controls oder vom/zum Explorer! ich will Einträge nur händisch sortieren können, wie?

Verzweifelte Grüße

Florian

Hi!

Mit „klassischem“ Drag&Drop wirst Du vermutlich nicht so recht weiterkommen, aber ich hab’s eben probiert - wenn Du das selbst machst, ist es nicht schwer.

Im MouseDown-Event bestimmst Du Dir das ListViewItem, auf das geklickt wurde (per listView1.GetItemAt()).
Das merkst Du Dir.
Im MouseMove-Event holst Du Dir auch wieder das Item, über dem die Maus gerade ist. Wenn es das selbe ist wie das gemerkte, dann vielleicht geschickterweise den Cursor auf Cursors.No setzen, damit man weiss, dass es keinen Sinn macht, das Item auf sich selbst fallen zu lassen. Anderenfalls den Cursor auf irgendwas anderes setzen, damit man sieht, dass etwas passiert.
Im MouseUp-Event schließlich wieder das Item bestimmen, auf dem fallengelassen wurde und per listView1.Items.Remove() das gemerkte entfernen und z.B. per listView1.Items.Insert(…) einfügen. Anschließend den Merker des gezogenen Items wieder zurücksetzen.

Wenn Du’s noch komfortabler willst (mit Anzeige, ob vor oder nach einem Item einsortiert wird, dann wird’s etwas aufwändiger…

Gruß,
Martin

P.S.: Beschreibung extra in Prosa, weil ich’s in C# schnell probiert hab und Du nach VB.NET gefragt hast…

Hi Martin!

So eine Idee hatte ich auch schon, allerdings habe ich das ganze viel zu komplizirt angepackt (ich will mehrere Einträge verschieben, ich sollte erstmal EINES realisieren, dann sehen wir weiter…)

P.S.: Beschreibung extra in Prosa, weil ich’s in C# schnell
probiert hab und Du nach VB.NET gefragt hast…

Das ist voll OK, ist mir fast am liebsten!

Also ich habe das ganze realisiert! Ich speichere den Index zwischen und füge das Ding an der neuen Position ein. Das scheint zu klappen! Allerdings löst bei mir das „MouseUp“-Event sofort aus, wenn ich die Mouse nur einen Millimeter bewege, was mache ich da falsch? Ich habe ans ende vom MouseUp eine Message-Box zur kontrolle gesetzt. Wenn ich nun Klicke und die Mouse ein Pixel bewege iss sofort Schluss: Ich kann nicht schieben! Wo ist der fehler?
Das ListView steht auf Detials (Report-Modus), ich habe zwei Spalten und jeweils ein Bild. AllowDrop ist false (mit true gehts auch nicht). Es sind mit dem LV KEINE weiteren Events verknüpft (also nur MouseUp und MouseMove). Das LV leiegt auf einem TAB… Wo könnte mein Fehler sein? Hättest Du evtl eine Idee???

Liebe Grüße und tausend dan schonmal

Florian

Hi Martin!

So eine Idee hatte ich auch schon, allerdings habe ich das
ganze viel zu komplizirt angepackt (ich will mehrere Einträge
verschieben, ich sollte erstmal EINES realisieren, dann sehen
wir weiter…)

P.S.: Beschreibung extra in Prosa, weil ich’s in C# schnell
probiert hab und Du nach VB.NET gefragt hast…

Das ist voll OK, ist mir fast am liebsten!

Also ich habe das ganze realisiert! Ich speichere den Index
zwischen und füge das Ding an der neuen Position ein. Das
scheint zu klappen! Allerdings löst bei mir das
„MouseUp“-Event sofort aus, wenn ich die Mouse nur einen
Millimeter bewege, was mache ich da falsch? Ich habe ans ende

Seltsam - das ist nicht normal. Ohne Deinen Code kann man aber unmöglich sagen, warum. Sortierst Du evtl. schon im MouseMove um?

vom MouseUp eine Message-Box zur kontrolle gesetzt. Wenn ich

Evtl. ist ein System.Diagnostics.Debug.WriteLine() geschickter, damit verliert das Control nicht den Fokus und Du musst nicht klicken.

nun Klicke und die Mouse ein Pixel bewege iss sofort Schluss:
Ich kann nicht schieben! Wo ist der fehler?
Das ListView steht auf Detials (Report-Modus), ich habe zwei
Spalten und jeweils ein Bild. AllowDrop ist false (mit true
gehts auch nicht). Es sind mit dem LV KEINE weiteren Events
verknüpft (also nur MouseUp und MouseMove). Das LV leiegt auf
einem TAB… Wo könnte mein Fehler sein? Hättest Du evtl eine
Idee???

Liebe Grüße und tausend dan schonmal

Florian

Hi Martin!

Seltsam - das ist nicht normal.

Ohne Deinen Code kann man aber
unmöglich sagen, warum. Sortierst Du evtl. schon im MouseMove
um?

NEIN! Ich habe nur MouseUP und MouseDown!

Evtl. ist ein System.Diagnostics.Debug.WriteLine()
geschickter, damit verliert das Control nicht den Fokus und Du
musst nicht klicken.

Jein! Die MsgBox erscheint ja erst, wenn der Drag und Drop - Vorgang zu Ende ist! Aber slebst mit Debug wird klar: MouseUp wird ausgelöst, wenn ich die Mouse bewege, aber der Button noch gedrückt ist!

Hier mal der Code:

Dim merke\_lv as integer = -1
Private Sub lstBilder\_MouseDown(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles lstBilder.MouseDown
 If lstBilder.GetItemAt(e.X, e.Y) Is Nothing Then Exit Sub
 merke\_lv = lstBilder.GetItemAt(e.X, e.Y).Index

 End Sub

 Private Sub lstBilder\_MouseUp(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles lstBilder.MouseUp
 If merke\_lv -1 Then
 Dim merke\_lv\_i = lstBilder.GetItemAt(e.X, e.Y).Index
 lstBilder.Items.Insert(merke\_lv\_i, lstBilder.Items.Item(merke\_lv).Clone)
 If merke\_lv 

Kommt Dir da was "spansich" vor???

Liebe Grüße vom

Florian

Hallo nochmal!
Auf den ersten Blick seh’ ich nichts, was den von Dir beschriebenen Effekt erzeugen könnte.
Lediglich ein Verbesserungsvorschlag im MouseUp-Fall: Statt erst einen Clone einzufügen und dann das Original zu entfernen solltest Du das Ganze vielleicht umdrehen. Erst Original entfernen und dann auch das Original wieder einfügen. Damit bleibt die Objektidentität erhalten.

Aber sonst…

Ich hab’s gestern Abend spaßeshalber mal programmiert, ich glaub’, ich stell’s als Artikel nach CodeProject.
Dann kannst Du Dir ja mal den Code ansehen und evtl. darüber weiterkommen.

Gruß,
Martin