2016-11-03 4 views
3

Ich habe folgendes Problem:Schreib absolute Mausposition in TextBox

Ich habe ein Fenster mit zwei Textfelder. Wenn ich in ein Textfeld klicke und irgendwo anders klicke (auch außerhalb des Fensters), sollte die Mausklickposition in das Textfeld geschrieben werden.

Ich fand die MouseKeyHook Bibliothek, in der eine Demo zeigt, wie die Mausposition in einer Windows-Form aktualisiert wird. Aber ich habe es noch nicht geschafft, den Code auf mein Problem anzuwenden. Ich weiß nicht einmal, wo ich den in der Demo gefundenen Code schreiben soll.

Was ich mit so weit kam ist folgende:

using System.Windows; 
using System.Windows.Controls; 
using System.Windows.Input; 

namespace LineClicker 
{ 
    /// <summary> 
    /// Interaction logic for MainWindow.xaml 
    /// </summary> 
    public partial class MainWindow : Window 
    { 
     public MainWindow() 
     { 
      InitializeComponent(); 
     } 

     private void StarttextBox_GotFocus(object sender, RoutedEventArgs e) 
     { 
      Mouse.Capture(StarttextBox); 
      StarttextBox.Text = string.Format(" x {0} , y {1}", PointToScreen(Mouse.GetPosition(this)).X, PointToScreen(Mouse.GetPosition(this)).Y); 
     } 
    } 
} 

Dies ist der Code für eine textBox. Wenn ich darauf klicke, werden x- und y-Koordinaten angezeigt. Sie sind nicht absolut, ich denke, das liegt an dem Parameter this in der GetPosition Methode. Was muss ich anstelle von this wählen?

Eine andere Sache ist, dass die Position nicht immer aktualisiert wird. Wenn ich die Maus in die untere rechte Ecke meines Desktops bewege und dann die Textbox aktiviere, indem ich sie einraste, wird die Position nicht aktualisiert.

Was sind die Schritte hier zu tun?

+0

Wenn Sie die absolute Position der Maus relativ zum Bildschirm abrufen und aktualisieren möchten, auch wenn Sie sich außerhalb des WPF-Fensters befinden, müssen Sie ein MouseHook verwenden (Verwendet Win32 API-Aufrufe, um die Position zu erhalten) und einen Timer, der die Position ermittelt und in Ihrem TextBlock anzeigt. –

Antwort

3

Ich konnte dieses Ergebnis erreichen Cursor.Position mit:

A Punkt Dies repräsentiert die Position des Cursors in Bildschirmkoordinaten.

Beispiel

using System.Windows; 

namespace WpfApplication1 
{ 
    public partial class MainWindow : Window 
    { 
     public MainWindow() 
     { 
      InitializeComponent(); 
     } 

     private void textBox_GotFocus(object sender, RoutedEventArgs e) 
     { 
      var postion = System.Windows.Forms.Cursor.Position; 
      textBox.Text = string.Format($"{postion.X}, {postion.Y}"); 
     } 
    } 
} 

Sie aus dem the Microsoft reference source sehen kann, dass Cursor.Position wie folgt definiert ist:

public static Point Position { 
    get { 
     NativeMethods.POINT p = new NativeMethods.POINT(); 
     UnsafeNativeMethods.GetCursorPos(p); 
     return new Point(p.x, p.y); 
    } 
    set { 
     IntSecurity.AdjustCursorPosition.Demand(); 
     UnsafeNativeMethods.SetCursorPos(value.X, value.Y); 
    } 
} 

So wie gerade in yan yankelevich's answer, verwendet es noch SetCursorPos, aber So ist es einfacher zu telefonieren.

Abgesehen davon hängt es wahrscheinlich nur davon ab, ob Sie froh sind, den Verweis auf System.Windows.Forms aufzunehmen.

+0

Wenn ich dies versuche, ist 'System.Windows.Forms' rot unterstrichen und es gibt einen Fehler CS0234 C# Der Typ oder Namespace Name 'Forms' existiert nicht im Namespace 'System.Windows' (fehlt eine Assembly? Referenz?) –

+0

@DavidP Sie müssen 'System.Windows.Forms' als Referenz hinzufügen, indem Sie' Project' -> 'Add Reference' wählen und dann aus der Liste (Es wird unter Assemblies -> Framework) – Bassie

+0

Es hat funktioniert, danke! Diese Lösung sieht einfacher aus als die von yan yankalevich. Gibt es irgendwelche Vorteile/Nachteile zwischen Ihrer Antwort und seiner? –

2

Zuerst müssen Sie die absolute Mausposition ermitteln (nicht relativ zu Ihrem Fenster oder Ihren Steuerelementen). Um dies zu tun benötigen Sie eine dieser Optionen (von hier: https://stackoverflow.com/a/4232281/4664754):

  • durch einen Verweis auf System.Windows.Forms in Ihrem Projekt hinzufügen (geht in Referenzen in Ihrer Lösung Explorer -> Rechtsklick -> Fügen Sie eine Referenz hinzu -> Assemblys -> Framework -> Markieren Sie das Kästchen neben System.Windows.Forms). Dann diese statische funtcion in irgendeiner Klasse hinzufügen (lass es MouseHelper.cs nennen):

    public static Point GetMousePositionWindowsForms() 
    { 
        System.Drawing.Point point = Control.MousePosition; 
        return new Point(point.X, point.Y); 
    } 
    
  • Durch diesen Code in Ihrem MainWindow.xaml.cs einfügen:

    [DllImport("user32.dll")] 
        [return: MarshalAs(UnmanagedType.Bool)] 
        internal static extern bool GetCursorPos(ref Win32Point pt); 
    
        [StructLayout(LayoutKind.Sequential)] 
        internal struct Win32Point 
        { 
         public Int32 X; 
         public Int32 Y; 
        }; 
        public static Point GetMousePosition() 
        { 
         Win32Point w32Mouse = new Win32Point(); 
         GetCursorPos(ref w32Mouse); 
         return new Point(w32Mouse.X, w32Mouse.Y); 
        } 
    

Was auch immer das Wie Sie wählen, müssen Sie eine dieser Funktionen in Ihrem OnFocusChanged auf diese Weise aufrufen:

Auf diese Weise sollten die Koordinaten korrekt sein. Für Ihr Problem, dass Koordinaten nicht zur richtigen Zeit angezeigt werden, denke ich, dass Ihre Fokuslösung nicht das ist, wonach Sie suchen.

sollten Sie versuchen, etwas zu implementieren: https://stackoverflow.com/a/2064009/4664754 und Ihre Textfelder Werte der TheMouseMoved Ereignis aufgerufen wird jedes Mal ändern