![]() |
Virtual Treeview und Drag'n'Drop
Moin,
So, nachdem ich jetzt schon einige Stunden an diesem Problem hänge, dachte ich mir, ich frage hier mal nach: Ich habe in einem Projekt von mir zwei Virtual Treeviews (Eines links, das andere rechts). Die fertige Funktion der beiden sollte dann so aussehen: Die Items im rechten vst sollen per Drag'n'Drop verschoben werden(funktioniert bereits) und man soll Items aus dem Linken dem Rechten hinzufügen können(das Linke soll nichts können, außer diese Nodes wegzuschicken, um das Rechte weiter zu füllen). Wie bereits gesagt, habe ich bereits 50% fertig. Denn alle Move-Operationen funktionieren perfekt. Nur wenn es dann an's Kopieren geht, habe ich einfach keine Ahnung wie ich an die Daten komme, um sie im neuen Node des rechten Vsts einzufügen. (Achja, ich arbeite mit der OLE-Drag-Version. Sollte die VCL-Drag-Version für meine Zwecke besser geeignet sein, so lasst es mich bitte wissen!). Hier mal was ich schon habe:
Delphi-Quellcode:
Als Clipboard-Format ist Virtual Tree Data gewählt, der DragType ist, wie bereits gesagt dtOLE und der DragMode ist dmAutomatic.
procedure TFrmSmartBarDlg.InsertData(Sender: TVirtualStringTree; DataObject:
IDataObject; Formats: TFormatArray; Effect: Integer; Mode: TVTNodeAttachMode); var FormatAccepted: Boolean; I: Integer; begin FormatAccepted := False; for I := 0 to High(Formats) do begin if Formats[I] = CF_VIRTUALTREE then begin if not FormatAccepted then begin Sender.ProcessDrop(DataObject, Sender.DropTargetNode, Effect, Mode); FormatAccepted := True; end; end; end; end; procedure TFrmSmartBarDlg.vstRightDragDrop(Sender: TBaseVirtualTree; Source: TObject; DataObject: IDataObject; Formats: TFormatArray; Shift: TShiftState; Pt: TPoint; var Effect: Integer; Mode: TDropMode); procedure DetermineEffect; begin // Set Effect accordingly. if Source = Sender then begin Effect := DROPEFFECT_MOVE; end else begin Effect := DROPEFFECT_COPY; end; end; var Attachmode: TVTNodeAttachMode; Nodes: TNodeArray; begin Nodes := nil; // Translate the drop position into an node attach mode. case Mode of dmAbove: AttachMode := amInsertBefore; dmOnNode: AttachMode := amInsertAfter; dmBelow: AttachMode := amInsertAfter; else AttachMode := amNowhere; end; if DataObject <> nil then begin // OLE drag'n drop. Perform full processing. // Determine action in advance even if we don't use the dropped data. // Note: The Effect parameter is a variable which must be set to the action we // will actually take, to notify the sender of the drag operation about remaining actions. // This value determines what the caller will do after the method returns, // e.g. if DROPEFFECT_MOVE is returned then the source data will be deleted. DetermineEffect; InsertData(Sender as TVirtualStringTree, DataObject, Formats, Effect, AttachMode); end; end; Ich hoffe ihr könnt mir aus meiner Verzweiflung wieder hinaushelfen ;) Edit: Achja, das Kopieren des Nodes an sich funktioniert ja, das heißt, ich habe dann ein komplett leeres Node, an der Stelle wo ich das gezogenen einfügen wollte. Das Problem, welches sich mir stellt ist einfach wie ich an die Daten komme(die in Form eines Records vorliegen) und jene dann weiterleite, bzw. dem neuen Node anhänge. Edit2: Auch die Suche hier um Forum und bei Mike direkt gibt nur sehr wenig her. Und falls ich mal was zu dem Thema finde, ist es entweder genau das, was ich nicht brauche, oder einfach unbeantwortet. Ebenfalls ist die Demo für meine Zwecke unbrauchbar, denn diese kopiert nur die Captions an sich, da ich aber mehrere Daten speichere, brauche ich direkt den Zugriff auf den betreffenden Record. Danke schonmal & Grüße, Max |
Re: Virtual Treeview und Drag'n'Drop
hi max,
ich habe etwas ähnliches, verwende aber zum kopieren / verschieben im gleichen prog nicht OLE. Folgendes prinzip: im quellensteuerelement wird mit OnMouseDown festgehalten, wo die maustaste gedrückt wird. gleichzeitig gehen die daten, die zu verschieben sind in einen record (als zwischenspeicher). dann überprüfe ich in OnMouseMove, ob die maus bei gedrückter taste gezogen wird. entfernt sich die maus um einen bestimmten betrag von der stelle, wo geklickt wurde, wird im record ein kennzeichen gesetzt, daß einen dragoperation im gange ist. wird nun die maustaste im zweiten steuerelement losgelassen, so kann man dort erfahren, daß sie aus dem ersten steuerelement gezogen wurde. der punkt, an dem sie losgelassen wurde ist das ziel und dorthin werden die daten aus dem record übernommen. das ganze funktioniert ohne alle drag&drop-methoden. nur noch eine kleine ergänzung ist sinnvoll: ich setze einen HOOK für die maus, um von jeder stelle zu erfahren, ob die maus gehengelassen wurde. letzteres hat zur folge, daß im record das kennzeichen zurückgesetzt wird, durch das man erfährt, daß eine dragoperation im gange ist. manfred |
Re: Virtual Treeview und Drag'n'Drop
Zitat:
Grüße & Hilfe, Max |
Re: Virtual Treeview und Drag'n'Drop
alles ansichtssache, ich finde es zB etwas aufwendig, wenn ich windows für drag&drop
bemühen soll, solange alles in einem prog bleibt... sonst aber garnicht so schlimm, wird dir gefallen... ist nicht von mir, habe ich auch in DP gefunden. im formular deklarieren:
Delphi-Quellcode:
in FormCreate:
protected (z.B.)
HookID : HHook; IsMouseDown: boolean; ... (Formular heißt HF)
Delphi-Quellcode:
dann eine funktion erstellen
procedure THF.FormCreate(Sender: TObject);
... HookId:=SetWindowsHookEx(WH_MOUSE,MouseProc,0,GetCurrentThreadId()); ...
Delphi-Quellcode:
und in FormClose wieder freigeben
// HOOK zur Feststellung von WM_LBUTTONDOWN und WM_LBUTTONUP auch
// außerhalb des Programmes (Es wird die Variable IsMouseDown gesetzt) function MouseProc(nCode: Integer; wParam, lParam: Longint): Longint; stdcall; begin case nCode < 0 of True: Result := CallNextHookEx(HF.HookID, nCode, wParam, lParam) else begin case wParam of WM_LBUTTONDOWN : HF.IsMouseDown:=TRUE; WM_LBUTTONUP : HF.IsMouseDown:=FALSE; end; { of case } Result := CallNextHookEx(HF.HookID, nCode, wParam, lParam); end end; end;
Delphi-Quellcode:
gruß
procedure THF.FormClose(Sender: TObject; var Action: TCloseAction);
... if HookID <> 0 then UnHookWindowsHookEx(HookID); ... |
Re: Virtual Treeview und Drag'n'Drop
ps: das MouseUp wird auch dann erkannt, wenn sich die maus außerhalb des programmes befindet
Manfred |
Re: Virtual Treeview und Drag'n'Drop
klingt irgendwie alles kompliziert was ihr macht.
du hast doch im drop ereignis die variable source. das ist der tree/obj aus dem die daten kommen. also einfach testen ob das die gültige quelle ist. in der gültigen quelle brauchst du dann doch nur die "selected" nodes auswerten und einfügen/kopieren. |
Re: Virtual Treeview und Drag'n'Drop
Zitat:
Vor lauter Wald sieht man keine Bäume mehr, oder wie war das noch? :mrgreen: Danke & Grüße, Max |
Alle Zeitangaben in WEZ +1. Es ist jetzt 09:53 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz