Laden...

WinApi GetWindowRect auf Multimonitorsystem

Erstellt von Ahrimaan vor 13 Jahren Letzter Beitrag vor 13 Jahren 3.752 Views
A
Ahrimaan Themenstarter:in
350 Beiträge seit 2010
vor 13 Jahren
WinApi GetWindowRect auf Multimonitorsystem

allo,

mein programm soll sich über ein anderes Programm "legen"

Dazu habe ich folgende Funktion :


if (process.ProcessName == "CtiClient")
  {
   RECT windowPos = new RECT();
   GetWindowRect(new HandleRef(this,process.Handle), out windowPos);
   this.StartPosition = FormStartPosition.Manual;
   this.SetDesktopLocation(windowPos.Left,windowPos.Top);
  }
[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
        }


Da ich es zur Zeit nur an einer Maschine mit 3 Monitoren testen kann, habe ich den verdacht das es damit nicht so klappt.

Er zeigt mir Koordinaten an aber wenn ich darauf die Position setzte landet das Ding im Nirvana.

Mache ich was falsch ?

Grüße

3.170 Beiträge seit 2006
vor 13 Jahren

Hallo,

  1. das wrappen in HandleRef kannst Du Dir an dieser Stelle vermutlich sparen und stattdessen IntPtr verwenden um das Handle direkt zu übergeben, es funktioniert aber auch mit HandleRef.

  2. Du benutzt das falsche Handle. Versuch mal mit process.MainWindowHandle 🙂

Gruß, MarsStein

Non quia difficilia sunt, non audemus, sed quia non audemus, difficilia sunt! - Seneca

A
Ahrimaan Themenstarter:in
350 Beiträge seit 2010
vor 13 Jahren

Hi MarsStein,

ich habe es auch mal mit dem MainWindowHandle probiert (Auch mal mit Outlook etc.)
Irgendwie will es aber trotzdem nicht.
Das Ding landet immer auf dem hauptscreen oben links
Ich habe auch schon nachgeschaut ob ich das irgendwo setzte aber Pustekuchen....

Ich suche einfach mal weiter vll fällt mir ja was auf.

Grüße

3.170 Beiträge seit 2006
vor 13 Jahren

Hallo,

startest Du den Prozess selbst? Dann solltest Du noch process.WaitForInputIdle() aufrufen, vorher sind alle Werte 0 weil das Fenster noch nicht erstellt ist.

Hier mal ein Beispiel mit HandleRef...

  static class Program
  {
    [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;
      public int Top;
      public int Right;
      public int Bottom;
    }

    [STAThread()]
    static void Main(string[] args)
    {
      Process proc = Process.Start("notepad.exe");
      proc.WaitForInputIdle();
      RECT r;
      GetWindowRect(new HandleRef(new Object(),proc.MainWindowHandle), out r);
      Console.WriteLine("{0} {1} {2} {3}", r.Left, r.Top, r.Bottom, r.Right);
      Console.Read();
    }
  }

und eins mit IntPtr

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

    [StructLayout(LayoutKind.Sequential)]
    public struct RECT
    {
      public int Left;
      public int Top;
      public int Right;
      public int Bottom;
    }

    [STAThread()]
    static void Main(string[] args)
    {
      Process proc = Process.Start("notepad.exe");
      proc.WaitForInputIdle();
      RECT r;
      GetWindowRect(proc.MainWindowHandle, out r);
      Console.WriteLine("{0} {1} {2} {3}", r.Left, r.Top, r.Bottom, r.Right);
      Console.Read();
    }
  }

Beide Varianten funktionieren bei mir problemlos.

Gruß, MarsStein

Non quia difficilia sunt, non audemus, sed quia non audemus, difficilia sunt! - Seneca

A
Ahrimaan Themenstarter:in
350 Beiträge seit 2010
vor 13 Jahren

Hi MarsStein,

der Prozess ist bereits vorhanden, ich starte diesen also nicht selbst.
Das Struct wird auch mit Leben gefüllt bzw. die Funktion liefert True zurück.

Zwar mit Werten wie :

Bottom : 1305
Left : 3352
Right : 4418
Top : -329

Ich fürchte fast es liegt an den Drei Monitoren : Ich muss also die Position umrechnen evtl.

Grüße

EDIT : Multiple Monitor System Metrics

Siehe da , aus Kompatibilitätsgründen wird nur der Primary Monitor angesprochen.