Form In primo piano

Mettere una finestra sempre in primo piano ha la sua utilita'.

Prendiamo ad esempio un applicazione di monitoring oppure un avvertimento non invasivo per l'utente.

Certo, potremmo dire di mettere un icona sulla traybar e variarla se succede qualcosa pero' molti utenti non fanno caso a quella parte dello schermo e quindi potrebbe non venir recepito l'avvertimento.

Per risolvere possiamo fare una maschera e metterla sempre in primo piano in una parte dello schermo che viene vista dall'utente di turno.

Per farlo e' necessario definire una classica API:

Private Declare Function SetWindowPos Lib "user32" (ByVal hWnd As Long, ByVal hWndInsertAfter As Long, ByVal X As Long, ByVal Y As Long, ByVal cx As Long, ByVal cy As Long, ByVal wFlags As Long) As Long

Vediamo un po' che parametri necessita:

hWnd l'handle della finestra
hWndInsertAfter indica l'handle della finestra su cui posizionare la nostra nell'ordine z oppure possono essere date le seguenti costanti:
HWND_BOTTOM = 1 mette la form sotto tutte le altre
HWND_NOTOPMOST = -2 la imposta come NON "in primo piano"
HWND_TOP = 0 mette la form sopra tutte le altre
HWND_TOPMOST = -1 mette la form "in primo piano" quindi le altre form resteranno sotto
X la left in cui posizionare la form
Y il top in cui posizionare la form
cx la width della form
cy la height della form
wFlags sono parametri di dimensionamento e posizionamento della form
SWP_DRAWFRAME = SWP_FRAMECHANGED disegna un frame intorno alla finestra
SWP_FRAMECHANGED = &H20 manda un messaggio di sistema (WM_NCCALCSIZE) che indica una variazione di dimensione
SWP_HIDEWINDOW = &H80 nasconde la finestra
SWP_NOACTIVATE = &H10 non attiva la finestra
SWP_NOCOPYBITS = &H100 rilascia la memoria client
SWP_NOMOVE = &H2 ignora i parametri X ed Y
SWP_NOOWNERZORDER = &H200 non camia la posione del form padre nell'ordine Z
SWP_NOREDRAW = &H8 non ridisegna la form
SWP_NOREPOSITION = SWP_NOOWNERZORDER non ridisegna la form
SWP_NOSENDCHANGING = &H400 evita che la form ricevi il messaggio WM_WINDOWPOSCHANGING che indica cambiamenti nella form
SWP_NOSIZE = &H1 ignora i parametri cx e cy
SWP_NOZORDER = &H4 ignora il parametro hWndInserAfter
SWP_SHOWWINDOW = &H40 mostra la finestra

Da cio' ne consegue che, una volta definite le costanti che ci interessano:

Const conHwndTopmost = -1
Const conHwndNoTopmost = -2
Const conSwpNoActivate = &H10
Const conSwpShowWindow = &H40
Const conSwpNoMove = &H2
Const conSwpNoSize = &H1

E' sufficiente chiamare la procedura con

SetWindowPos tForm.hWnd, conHwndTopmost, 0, 0, 0, 0, conSwpShowWindow Or conSwpNoMove Or conSwpNoSize

per mettere in primo piano la form e con

SetWindowPos tForm.hWnd, conHwndNoTopmost, 0, 0, 0, 0, conSwpShowWindow Or conSwpNoMove Or conSwpNoSize

per toglierlo dal primo piano.