Anwendung = Top Form ?

  • VB.NET
  • .NET (FX) 4.5–4.8

Es gibt 8 Antworten in diesem Thema. Der letzte Beitrag () ist von woeh.

    Anwendung = Top Form ?

    hallo :)

    wie erfahre ich welches fenster das Foregroundwindow ist, sobald ich das NotifyIcon klicke ?

    sinn ist, dass wenn meine anwendung nicht das Foregroundwindow ist, soll es nach vorne kommen.
    ist es das Foregroundwindow, soll es Visible=False sein.

    sobald ich aber das NotifyIcon klicke, ist das Foregroundfenster weg.

    jmd ne idee ? ?(

    woeh schrieb:

    ist es das Foregroundwindow, soll es Visible=False sein
    Es kann nur dann im Vordergrund sein und somit den Eingabefokus haben, wenn es sichtbar ist. Meines Erachtens ist das sogar eine Windows-Definition.

    Dass Du mit einem Klick auf ein anderes Fenster (nämlich das NotifyIcon und somit die Taskleiste) den Eingabefocus wechselst (= Wechsel des »foreground window«), ist Dir schon klar, oder?
    Aber das mal beiseite gelegt: Was genau willst Du eigentlich erreichen? Dass Dein Fenster, welches mit dem TrayIcon verbunden ist, in den Vordergrund kommt und den Eingabefokus erhält?

    Wenn Du also Dein NotifyIcon/TrayIcon klickst, dann sag doch: Me.Show: Me.Activate. Das sollte schon reichen, da das NotifyIcon doch bestimmt innerhalb der anzuzeigenden Form definiert ist und somit Me auf diese Form verweist.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „VaporiZed“ ()

    Also ans aktive Fenster kommst du mit GetActiveWindow(user32.dll), so kannst du schauen ob dein Fenster das aktive ist.

    VB.NET-Quellcode

    1. <DllImport("user32.dll")>
    2. Private Shared Function GetActiveWindow() As IntPtr
    3. End Function
    4. Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
    5. If GetActiveWindow() = Handle Then
    6. MessageBox.Show("I'm the active Window!")
    7. End If
    8. End Sub


    Edit, kannst auch GetForeGroundWindow(user32.dll) nehmen, hier wird galube ich nach dem Z-Index geurteilt, gibt ja auch Fenster welche TopMost sind.

    VB.NET-Quellcode

    1. <DllImport("user32.dll")>
    2. Private Shared Function GetForeGroundWindow() As IntPtr
    3. End Function


    And i think to myself... what a wonderfuL World!
    also....bist jetzt habe ich es so gemacht:

    VB.NET-Quellcode

    1. NotifyIcon_MouseDoubleClick
    2. visible = Not (Me.Visible)


    es ist aber so, dass wenn meine anwendung nicht das Foregroundwindow ist, aber sichtbar, und man den doppelklick macht, dass es dann verschwindet und man nochmal klicken muß, damit er erscheint.

    es soll aber nur dann verschwinden, wenn es das Foregroundwindow ist, ansonsten soll es nach vorne kommen. bei einem weiteren klick soll es dann wieder verschwinden.

    VB.NET-Quellcode

    1. Private Sub NotifyIcon_MouseDoubleClick(sender As Object, e As MouseEventArgs) Handles NotifyIcon.MouseDoubleClick
    2. Dim visible As Boolean
    3. Dim myApp As Boolean = False
    4. MsgBox(GetActiveWindow) ' = 0 ???
    @Eddy: GetForeGroundWindow => GetForegroundWindow, da P/Invoke => case sensitive
    @woeh: Und genau das ist eben das (momentane) Dilemma: Da das Icon in der Taskleiste liegt, hat die Taskleiste sowohl bei GetForegroundWindow als auch bei GetActiveWindow die Oberhand, eben weil es den Eingabefokus durch den Mausklick auf das Icon bekommt => Dein Programm verliert immer den Fokus und die Vordergrundposition innerhalb der angezeigten Fenster.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Nein, der Timer bringt Dir gar nichts, da einmal sich zwischen zwei TimerTicks alles mögliche an Fenstern vor Dein Programm schieben könnten und zum anderen (ich hab da mal was probiert) sich beim Klick auf das Icon zwischen dem fokussierten Fenster (= Taskleiste bzw. Traybereich) und meiner App bei mir 20 weitere Fenster befinden, ohne dass sich was davorgeschoben hätte. Da ist jedes Taskleistensymbol inkl. dem Startmenü usw. dabei, ohne, dass ich was dazu machen musste. Das liegt wohl daran, dass eben durch den Wechsel auf das NotifyIcon einfach eine Kaskade an Fensterwechseln stattfindet, damit sichergestellt wird, dass Windows schön (ok, ist Ansichtssache) bleibt und die Taskleiste und Co. richtig angezeigt werden.
    Vielleicht gibt es noch einen anderen, kreativen Weg, Dein Ziel zu erreichen, aber ich sehe momentan keinen.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    ich glaube so:

    man müßte taskleiste, startmenubutton & systray erumieren und aus dem prozess auschließen bzw. das vorletzte foregroundwindow nehmen und das alles im Notify_Mousemove basteln ....könnte es so klappen ?

    wäre mir aber zuviel arbeit....nur damit man einen klick weniger macht.

    ich habe mir das mal angeschaut...parentklasse von der ganzen taskleiste & systray und so ist "Shell_TrayWnd"...man müßte also immer nur das oberste parent abfragen...ist es "Shell_TrayWnd", dann das vorletzte foregroundwindow nehmen...mal schauen ob ich was bastel :)

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „woeh“ ()

    Anwendung = Top Form ? GELÖST !

    das problem: ist meine form die oberste anwendung wenn ich "NotifyIcon" klicke ?

    die lösung in einer klasse (mit nem timer abfragen)

    VB.NET-Quellcode

    1. Imports System.Runtime.InteropServices
    2. Public Class clsForegroundwindow
    3. <DllImport("user32.dll", ExactSpelling:=True, CharSet:=CharSet.Auto)>
    4. Public Shared Function GetParent(ByVal hWnd As IntPtr) As IntPtr
    5. End Function
    6. <DllImport("user32.dll", SetLastError:=True)>
    7. Private Shared Function GetForegroundWindow() As IntPtr
    8. End Function
    9. <DllImport("user32.dll", CharSet:=CharSet.Auto)>
    10. Private Shared Function GetClassName(ByVal hWnd As System.IntPtr,
    11. ByVal lpClassName As System.Text.StringBuilder,
    12. ByVal nMaxCount As Integer) As Integer
    13. End Function
    14. Private Declare Auto Function FindWindow Lib "user32.dll" (ByVal lpClassName As String, ByVal lpWindowName As String) As IntPtr
    15. Private mHwnd As IntPtr
    16. Public ReadOnly Property GetWindow
    17. Get
    18. Return mHwnd
    19. End Get
    20. End Property
    21. Private taskHwnd As IntPtr
    22. Public Sub New()
    23. taskHwnd = FindWindow("Shell_TrayWnd", "")
    24. End Sub
    25. Public Sub Checkforegroundwindoww()
    26. Dim sClassName As New System.Text.StringBuilder("", 256)
    27. Dim hwnd As IntPtr
    28. hwnd = GetForegroundWindow()
    29. Do While GetParent(hwnd) <> 0
    30. hwnd = GetParent(hwnd)
    31. Loop
    32. GetClassName(hwnd, sClassName, 256)
    33. If sClassName.ToString = "DV2ControlHost" Then Exit Sub
    34. If sClassName.ToString = "Progman" Then Exit Sub
    35. If hwnd <> taskHwnd Then
    36. mHwnd = hwnd
    37. End If
    38. End Sub
    39. End Class


    geht doch 8o

    also: man nehme einen timer in seinem projekt, der in der klasse den Sub "Checkforegroundwindow" aufruft.

    der sub prüft welches fenster das foregroundfenster ist.
    dabei werden taskleiste, systray, startbotton, startmenü und desktop ausgeschlossen.

    mit dem Property "GetWindow" erhält man dann das aktuelle foregroundfenster.

    wenn man nun z.b. auf das "NotifyIcon" klickt, fragt man vorher mit "GetWindow" das foregroundfenster ab. und tada...man erhält das fenster, das vorher das oberste war.

    weiß nicht....bin nicht so gut im erklären...hoffe es hilft. bei meinem projekt gehts zumindest.

    viel spaß ;)

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „woeh“ ()