Laden...

Cursor Position - Innerhalb des Fenster's verändern

Erstellt von _Cashisclay vor 9 Jahren Letzter Beitrag vor 9 Jahren 4.690 Views
_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren
Cursor Position - Innerhalb des Fenster's verändern

Hallo Liebe Community,

ich möchte meinen Cursor, meine Mouse Position innerhalb des Fensters ändern.

Bis hab ich herausgefunden an welcher Position sich einige Controls befinden. Nur wenn ich dann mit gewissen Standard Sachen versuche die Cursor Position zu ändern bspw.

System.Windows.Forms.Cursor.Position = meineNeuePosition

Ändert er es auf dem gesamten Bildschirm, ich möchte mich gerne nur innerhalb des Fenster bewegen. Wenn ich versuche die Position des Fenster's zu ermitteln, um das ganze dann zu addieren, bekomme ich die Werte 0,0.

Bringt mir nichts. Hat jemand eine Idee, wie ich das ganze umsetzen kann.

Grüße

P
157 Beiträge seit 2014
vor 9 Jahren

Hallo,

die Methoden PointToScreen und ScreenToPoint sind das was du suchst.

vg

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

Hallo,

also PointToScreen kenn ich ScreenToPoint nicht, nur PointFromScreen.

Mit beiden konnte ich bisher nicht das gewünschte Ergebnis erreichen, vllt hab ich was falsch gemacht.

Aktuell versuch ich mit


With Application.Current.MainWindow
MessageBox.Show(.Left & " " .Top)
End With

Die aktuelle Position des Fenster's zu bekommen, jedoch wirft das nicht immer optimale Ergebnisse.

Gruß
P
157 Beiträge seit 2014
vor 9 Jahren

Ach die mein ich doch 😉 Du kannst nur die Koordinaten innerhalb eines Fensters oder die absoluten Koordinaten ermitteln..
Wieso verwendest du eigentlich System.Windows.Forms.Cursor.Position, sonst ist doch deine Frage eher ins Winforms forum einzuordnen ... vg

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

Naja darauf wurde halt verwiesen, in diversen Foren Einträgen.

Ich versuch das mal nochmal ordentlich zu erklären, ich möchte in WPF :

In meinem Fenster den Cursor verschieben, der Sinn dahinter ich möchte mir via Button
ein neues ListBoxItem erstellen und auf dieses Item meinen Cursor legen.

PointFromScreen -
Konvertiert einen in Bildschirmkoordinaten angegebenen Point in einen Point, der das aktuelle Koordinatensystem des Visual darstellt.

ScreenToPoint -
Rechnet die Position des angegebenen Clientpunkts in Bildschirmkoordinaten um

Helfen mir dabei eigentlich nicht wirklich, weil sich selbst dann der Cursor nur innerhalb des Bildschirm verschiebt, nicht innerhalb des Fensters

Grüße

P
157 Beiträge seit 2014
vor 9 Jahren

😉 Ich hab das schon verstanden, ich bin nur davon ausgegangen, dass du weißt wie das in Windows funktioniert...also versuch ich es etwas genauer zu erklären...

  1. Es gibt in WPF keine mit bekannte möglichkeit die Cursorposition zu setzen. Du solltest dir besser ne external deklaration (dllimport) für den WinApi-Aufruf SetCursorPos schreiben ... das ist eine zeile.

  2. Diese Methode arbeitet, wenn es kein gültiges Fensterhandle bekommt, mit absoluten koordinaten.

  3. Du bekommst mit PointToScreen(0,0) bekommst du vom UIElement, an dem du diese methode aufrufst die absoluten koordinaten. Da musst du nicht mal addieren wenn du dein listitem in der hand hast... zb -> MainWindow.PointToScreen(0,0) -> 120, 246 --- ausser es ist maximized, dann bekommst du die minimalkoordinaten deines aktuellen Monitors, wenn du nur einen hast -> 0,0.

  4. diese koordinaten kannst du dann als ausgangspunkt für deine neue mausposition verwenden..

MainWindow-> 200,200
Button im MainWindow -> 10,10

button.PointToScreen(0,0) -> 210,210

vg

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

1.) Ich weiß hab ich schon gemacht : Private Declare Function SetCursorPos Lib "user32" (ByVal X As Integer, ByVal Y As Integer) As Boolean

Hätte ich vllt dazu sagen sollen, sorry schreib selten Foren Beiträge 😐

Ich teste das ganze mal fix, danke.

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren
Dim ListBoxP As Point = ListBoxMain.PointToScreen(New Point(0, 0))

        Dim MainWindowP As Point = Application.Current.MainWindow.PointToScreen(New Point(0, 0))

        Dim MainPoint As Point = New Point(ListBoxP.X + MainWindowP.X, ListBoxP.Y + MainWindowP.Y)

        MessageBox.Show("FirstP X : " & ListBoxP.X & " " & "FirstP Y : " & ListBoxP.Y & " " & "SecondP X : " & MainWindowP.X & " " & "Second P: " & MainWindowP.Y)

        MsgBox(MainPoint.X & " " & MainPoint.Y)

        SetCursorPos(MainPoint.X, MainPoint.Y)

Hat nicht das gewünsche Ergebnis gebracht.

Gruß

Edit : Bei dem Roten Kreis war ca mein Cursor

P
157 Beiträge seit 2014
vor 9 Jahren

Fast großer...fast 😉

ListBoxP.PointToScreen reicht aus...dann hast du die koordinaten des controls ..rechnest noch 1,1 drauf und dann is dein cursor da wo er hin soll...lies dir noch mal meinen 3. punkt genau durch

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

Ja, gut stimmt reicht aus.

Aber wie krieg ich das jetzt zu einem Item der ListBox nach dem gleichen Prinzip?

Edit : Bzw geht das überhaupt?

Gruß

P
157 Beiträge seit 2014
vor 9 Jahren

gar nicht oder nur über einen enormen aufwand...ui-tests proggen ist sehr sehr aufwändig und nicht unbedingt zuverlässig...:) deshalb trennt man die applikationslogik von der oberfläche. mvvm ist hier das zauberwort. da kannst du nämlich per unittest deine funktionen ausführen.

vg

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

Naja das Ziel soll sein beim Hinzufügen eines ListBoxItems den Cursor auf das aktuell hinzugefügte Item zu setzen, da führt kein Weg dran vorbei. So ist die Vorgabe 😐

P
157 Beiträge seit 2014
vor 9 Jahren

Hat sich bestimmt son vollprofi bei euch ausgedacht, ohne das böse zu meinen, unwissenheit kann manchmal eine menge zeit und geld und ärger bedeuten 😉 vielleicht wäre es an dieser stelle sinnvoller darüber nachzudenken, dieses ominöse mvvm mal etwas genauer zu betrachten und dann total eeuphorisch zum verantwortlichen zu rennen und ihm zu sagen dass man diese testerei automatisieren kann -> nunit und buildserver lassen grüßen..das kann man in einem bruchteil der zeit programmieren und läuft ca 10000 mal schneller als n programm zu starten und dann testen zu lassen.

wpf bietet übrigens eine schnittstelle für automated-ui-tests...habs selbst noch nie benutzt, da kann ich dir nur das nachlesen empfehlen.

vg

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

Also von der Idee eher verabschieden 😮

Erstmal danke für die ganze Hilfe 😃

P
157 Beiträge seit 2014
vor 9 Jahren

Kein Ding...viel erfolg noch

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

Moinsen,

ich bin jetzt soweit das ich den Cursor auf das zuletzt hinzugefügt Item setzen kann.


Private Function HöheDerItems() As Integer

Dim Höhe As Integer = 0
Dim iCount As Integer = 0

Do While iCount <= ListBox_Test.Items.Count - 1

Dim Item = CType(ListBox_Test.ItemContainerGenerator.ContainerFromItem(ListBox_Test.Items.Item(iCount)), ListBoxItem)

            If iCount = ListBox_Test.Items.Count - 1 Then
                Höhe += Item.ActualHeight / 2
            Else
                Höhe += Item.ActualHeight
            End If

            iCount = iCount + 1
        Loop

        Return Höhe

    End Function

ListBox_Test.Items.Add("AA")

        ListBox_Test.SelectedIndex = ListBox_Test.Items.Count - 1
        ListBox_Test.Focus()
Dim c As Point = ListBox_Test.PointToScreen(New Point(0, 0))


Dim Breite As Integer = ListBox_Test.ActualWidth / 2



        Dim Höhe As Integer = 10

        MsgBox(Breite.ToString)

        c.X = c.X + Breite

        c.Y = c.Y + HöheDerItems()

        SetCursorPos(c.X, c.Y)

Brauch eigentlich nur noch ein Event für das ListBoxItem, tu mich da gerade noch schwer/dumm.

P
157 Beiträge seit 2014
vor 9 Jahren

Hrhr du gibst nicht auf was 😃

Was machst du denn wenn jemand das DataTemplate für dein ListboxItem anpasst oder die Transformationsmatrizen manipuliert? Dann musst du den Wert deiner geratenen Höhe mit anpassen 😃

Was für ein Event meinst du ? für den Mausklick ? 😃 WinAPI -> SendMessage

Wenn's zum weinen nicht reicht, lach drüber!

_
_Cashisclay Themenstarter:in
277 Beiträge seit 2014
vor 9 Jahren

Aufgeben wäre zu einfach 😕

Also aktuell hab ich es hinbekommen hier mal der Code :

Class MainWindow 

    Private WithEvents CurrentItem As ListBoxItem

    Private _TextBox As TextBox

    Private Function HeightOfItems() As Integer

        Dim _Height As Integer = 0

        Dim iCount As Integer = 0

        Do While iCount <= ListBox_Main.Items.Count - 1

            Dim Item = CType(ListBox_Main.ItemContainerGenerator.ContainerFromItem(ListBox_Main.Items.Item(iCount)), ListBoxItem)

            ' --- Das letzte Item / Neu hinzugefügt --- '
            If iCount = ListBox_Main.Items.Count - 1 Then
                _Height += Item.ActualHeight / 2
            Else
                _Height += Item.ActualHeight
            End If

            iCount = iCount + 1
        Loop

        Return _Height
    End Function

    Private Declare Function SetCursorPos Lib "user32" (ByVal X As Integer, ByVal Y As Integer) As Boolean

    Private Sub Button1_Click(sender As System.Object, e As System.Windows.RoutedEventArgs) Handles Button1.Click

        _TextBox = New TextBox
        _TextBox.Width = 200

        Dim _Object As Object = _TextBox

        ListBox_Main.Items.Add(_Object)

        ListBox_Main.SelectedIndex = ListBox_Main.Items.Count - 1

        ListBox_Main.Focus()

        MsgBox(ListBox_Main.SelectedIndex)

        Dim _Width As Integer = ListBox_Main.ActualWidth / 2

        Dim _ListBox_StartPoint As Point = ListBox_Main.PointToScreen(New Point(0, 0))

        SetCursorPos(_ListBox_StartPoint.X + _Width, _ListBox_StartPoint.Y + HeightOfItems())

        Dim _CurrentItem = CType(ListBox_Main.ItemContainerGenerator.ContainerFromItem(ListBox_Main.Items.Item(ListBox_Main.Items.Count - 1)), ListBoxItem)

        CurrentItem = _CurrentItem

    End Sub

    Private Sub CurrentItem_MouseLeave(sender As Object, e As System.Windows.Input.MouseEventArgs) Handles CurrentItem.MouseLeave
        ' --- TextBox auf Inhalt prüfen --- '
        If _TextBox.Text = "" Then
            ListBox_Main.Items.RemoveAt(ListBox_Main.Items.Count - 1)
        End If
    End Sub
End Class

Einige Fälle sind natürlich noch nicht berücksichtigt, an sich ist die ListBox nur dafür da glaube ich eine IP - Adresse einzutragen bzw irgendein Text einzutragen, da kann nicht soviel manipuliert werden.

Findest du der Wert ist geraten? Ich nehme die exakte Position wo die ListBox beginnt, von dort aus hol ich mir beim Hinzufügen eines Eintrages die aktuelle Breite der ListBox.

Nehme davon die Hälfte, Platziere dort den Cursor.

Und die Höhe hol ich mir ja immer die aktuelle des Items. Alles ohne Raten 😄

Sollte doch klappen?

Grüße

P
157 Beiträge seit 2014
vor 9 Jahren

Natürlich ist das geraten 😉

Also ums mal zu erklären : innerhalb eines ItemsControls kann sich jedes element aufgrund des verwendeten Templates von einander unterscheiden du kannst triggern animieren und komische sachen machen da ändert sich ständig die größe ... und das ganze noch asynchron 😃 Ich sach ja schau dir das mvvm pattern mal an...das ist so primitiv da kann man nicht viel falsch machen ...

wert - binding - control
(Name) {BINDING ... } (TextBox)

außer man versucht quick and dirty lösungen wie deine zu machen 😃 geht ne weile gut...führt aber schlussendlich zu problemen die du heute noch nicht kennst.

Das was du da versuchst kann man mit ca 10 Zeilen Code umsetzen...ohne rechnerei

Wenn's zum weinen nicht reicht, lach drüber!