Spostamento e ridimensionamento dei controlli in fase di esecuzione

Ecco come abilitare il trascinamento e il ridimensionamento dei controlli (su un modulo Delphi) con il mouse, mentre l'applicazione è in esecuzione.

Editor di moduli in fase di esecuzione

Dopo aver posizionato un controllo (componente visivo) sul modulo, è possibile regolare la posizione, le dimensioni e altre proprietà in fase di progettazione. Esistono tuttavia situazioni in cui è necessario consentire a un utente dell'applicazione di riposizionare i controlli dei moduli e modificarne le dimensioni, in fase di esecuzione.

Per abilitare il movimento dell'utente in fase di esecuzione e il ridimensionamento dei controlli in un modulo con un mouse, tre eventi relativi al mouse necessita di una gestione speciale: OnMouseDown, OnMouseMove e OnMouseUp.

In teoria, supponiamo che tu voglia consentire a un utente di spostare (e ridimensionare) un controllo pulsante, con un mouse, in fase di esecuzione. Innanzitutto, gestisci l'evento OnMouseDown per consentire all'utente di "afferrare" il pulsante. Successivamente, l'evento OnMouseMove dovrebbe riposizionare (spostare, trascinare) il pulsante. Infine, OnMouseUp dovrebbe completare l'operazione di spostamento.

instagram viewer

Trascinamento e ridimensionamento dei controlli modulo in pratica

Innanzitutto, rilascia diversi controlli in un modulo. Avere un CheckBox per abilitare o disabilitare lo spostamento e il ridimensionamento dei controlli in fase di esecuzione.

Successivamente, definire tre procedure (in interfaccia sezione della dichiarazione del modulo) che gestirà gli eventi del mouse come descritto sopra:

genere
TForm1 = classe(TForm)... procedura ControlMouseDown (Mittente: TObject; Pulsante: TMouseButton; Maiusc: TShiftState; X, Y: intero); procedura ControlMouseMove (Mittente: TObject; Maiusc: TShiftState; X, Y: intero); procedura ControlMouseUp (Mittente: TObject; Pulsante: TMouseButton; Maiusc: TShiftState; X, Y: intero); privato
inReposition: booleano; oldPos: TPoint; 

Nota: sono necessarie due variabili a livello di modulo per contrassegnare se si sta verificando il movimento del controllo (inReposition) e per memorizzare il controllo della posizione precedente (oldPos).

Nell'evento OnLoad del modulo, assegnare le procedure di gestione degli eventi del mouse agli eventi corrispondenti (per i controlli che si desidera siano trascinabili / ridimensionabili):

procedura TForm1.FormCreate (Mittente: TObject); inizio
Button1.OnMouseDown: = ControlMouseDown; Button1.OnMouseMove: = ControlMouseMove; Button1.OnMouseUp: = ControlMouseUp; Edit1.OnMouseDown: = ControlMouseDown; Edit1.OnMouseMove: = ControlMouseMove; Edit1.OnMouseUp: = ControlMouseUp; Panel1.OnMouseDown: = ControlMouseDown; Panel1.OnMouseMove: = ControlMouseMove; Panel1.OnMouseUp: = ControlMouseUp; Button2.OnMouseDown: = ControlMouseDown; Button2.OnMouseMove: = ControlMouseMove; Button2.OnMouseUp: = ControlMouseUp; fine; (* FormCreate *)

Nota: il codice sopra riportato consente il riposizionamento di runtime di Button1, Edit1, Panel1 e Button2.

Infine, ecco il codice magico:

proceduraTForm1.ControlMouseDown ( Mittente: TObject; Pulsante: TMouseButton; Maiusc: TShiftState; X, Y: intero);inizioSe (ChkPositionRunTime. controllato) E
(Mittente è TWinControl) poiinizio
inReposition: = true; SetCapture (TWinControl (Sender) .Handle); GetCursorPos (oldPos); fine; fine; (* ControlMouseDown *)

ControlMouseDown in breve: una volta che un utente preme un pulsante del mouse su un controllo, se il riposizionamento di runtime è abilitato (casella di controllo chkPositionRunTime è selezionato) e il controllo che ha ricevuto il mouse anche in basso deriva da TWinControl, segno che il riposizionamento del controllo è in corso (inReposition: = True) e assicurati che tutta l'elaborazione del mouse sia acquisita per il controllo - per evitare che gli eventi "click" predefiniti vengano trasformati.

proceduraTForm1.ControlMouseMove ( Mittente: TObject; Maiusc: TShiftState; X, Y: intero);const
minWidth = 20; minHeight = 20; var
newPos: TPoint; frmPoint: TPoint; inizioSe inReposition poiiniziocon TWinControl (mittente) fareinizio
GetCursorPos (newPos); Se ssShift nel Cambio poiinizio//resize
Schermo. Cursore: = crSizeNWSE; frmPoint: = ScreenToClient (Mouse. CursorPos); Se frmPoint. X> minWidth poi
Larghezza: = frmPoint. X; Se frmPoint. Y> minHeight poi
Altezza: = frmPoint. Y; finealtro//moveinizio
Schermo. Cursore: = crSize; Sinistra: = Sinistra - oldPos. X + newPos. X; In alto: = In alto - oldPos. Y + newPos. Y; oldPos: = newPos; fine; fine; fine; fine; (* ControlMouseMove *)

ControlMouseMove in breve: cambiare il cursore dello schermo per riflettere l'operazione: se si preme il tasto Maiusc consente di ridimensionare il controllo o semplicemente spostare il controllo in una nuova posizione (dove sta andando il mouse). Nota: minWidth e minHeight le costanti forniscono una sorta di vincolo dimensionale (larghezza e altezza minima del controllo).

Quando il pulsante del mouse viene rilasciato, il trascinamento o il ridimensionamento è finito:

proceduraTForm1.ControlMouseUp ( Mittente: TObject; Pulsante: TMouseButton; Maiusc: TShiftState; X, Y: intero);inizioSe inReposition poiinizio
Schermo. Cursore: = crDefault; ReleaseCapture; inReposition: = False; fine; fine; (* ControlMouseUp *)

ControlMouseUp in breve: quando un utente ha finito di spostare (o ridimensionare il controllo) rilasciare la cattura del mouse (per abilitare l'elaborazione dei clic predefinita) e contrassegnare che il riposizionamento è terminato.

E quello lo fa! Scarica l'applicazione di esempio e prova tu stesso.

Nota: un altro modo per spostare i controlli in fase di esecuzione è utilizzare Delphi's trascinare e rilasciare proprietà e metodi correlati (DragMode, OnDragDrop, DragOver, BeginDrag, ecc.). Il trascinamento della selezione può essere utilizzato per consentire agli utenti di trascinare elementi da un controllo, ad esempio una casella di riepilogo o una vista ad albero, in un altro.

Come ricordare la posizione e le dimensioni del controllo?

Se si consente a un utente di spostare e ridimensionare i controlli del modulo, è necessario assicurarsi che il posizionamento del controllo sia in qualche modo salvato quando il modulo viene chiuso e che la posizione di ciascun controllo viene ripristinata quando il modulo viene creato / caricato. Ecco come archiviare le proprietà Sinistra, Superiore, Larghezza e Altezza, per ogni controllo in un modulo, in un INI file.

Che ne dite di 8 maniglie di dimensioni?

Quando si consente a un utente di spostare e ridimensionare i controlli nel modulo Delphi, in fase di esecuzione utilizzando il mouse, su imitare completamente l'ambiente in fase di progettazione, è necessario aggiungere otto maniglie di dimensioni all'essere di controllo ridimensionato.