Domanda

Ho un System.Windows.Form e IntPtr in qualità di HWND.

voglio ciascuno di loro di mettere l'altro in movimento. Sono sorpreso, non ho trovato nulla sul web con "Hwnd get / set posizione C #" e molte varianti, forse sto affaccia risultati evidenti.

Per il bene degli esempi riportati, la forma "a finestra" e la Hwnd "finestra B". Diciamo che anche io voglio la posizione di B per essere la posizione di un + 50 pixel a destra.

È stato utile?

Soluzione

Aggiornamento: Si potrebbe anche voler controllare WinForms' class NativeWindow , che può essere usato per avvolgere un HWWND nativa e ascoltare i messaggi di finestra inviati a quella finestra.

Credo che sarà necessario la funzione API Win32 MoveWindow per impostare la posizione (e dimensioni) della finestra B (la HWND uno). È possibile chiamare questa funzione API da .NET tramite P / Invoke .

Al fine di recuperare la posizione e la dimensione della finestra B corrente, può inoltre essere necessario chiamare GetWindowRect , anche tramite P / Invoke.


Il codice seguente potrebbe non funzionare out of the box, e forse ci sono soluzioni più semplici, ma potrebbe dare un punto di partenza, insieme ai link di cui sopra:

// the following P/Invoke signatures have been copied from pinvoke.net:

[DllImport("user32.dll", SetLastError = true)]
internal static extern bool MoveWindow(IntPtr hWnd, 
                                       int X, int Y,
                                       int nWidth, int nHeight, 
                                       bool bRepaint);

[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool GetWindowRect(HandleRef hWnd, out RECT lpRect);

[StructLayout(LayoutKind.Sequential)]
public struct RECT
{
    public int Left;        // x position of upper-left corner
    public int Top;         // y position of upper-left corner
    public int Right;       // x position of lower-right corner
    public int Bottom;      // y position of lower-right corner
}

...

System.Windows.Form a = ...;
IntPtr b = ...;

RECT bRect;
GetWindowRect(b, out bRect);

MoveWindow(b,
           a.Location.X + 50, b.Location.Y,
           bRect.Right - bRect.Left, bRect.Bottom - bRect.Top,
           true);

Altri suggerimenti

La parte più difficile è quello di ottenere da A a muoversi quando si muove B. Ciò richiede una classe NativeWindow derivata. Utilizzare AssignHandle per fissare la maniglia della finestra che hai. Nel WndProc () ignorare è possibile rilevare il messaggio WM_MOVE, che consente di spostare A. E WM_DESTROY per ripulire.

Questo funziona però solo se la finestra è di proprietà di processo. Lo scenario più tipico è che questa è una finestra appartenente a qualche codice che non si controlla, in esecuzione in un altro programma. Lei ha perfettamente avvitato se questo è il caso, l'approccio NativeWindow non può funzionare. Avresti bisogno di iniettare una DLL non gestita nel processo con SetWindowsHookEx () in modo da poter monitorare WH_CALLWNDPROC. Con qualche tipo di meccanismo IPC per ottenere che la notifica nel vostro processo. Molto difficile da ottenere di destra, non si può scrivere il codice DLL in C #.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top