onmouseover bei einem static



  • Könntest Du mir dazu ein Beispiel geben? Ich weiß nicht so recht, was ich da nun genau machen muß :-(.

    THX, CQ.



  • Das geht so:

    SetWindowLongPtr(hWnd, GWLP_WNDPROC, reinterpret_cast<LONG_PTR>(NewWndProc));
    

    NewWndProc ist eine Funktion die die nachrichten erhält.



  • Vielen Dank für Deine Hilfe. Ich habe es mal so probiert, doch dummerweise erhalte ich folgende Fehlermeldung:

    *.cpp(97) : error C2065: 'SetWindowLongPtr' : nichtdeklarierter Bezeichner
    *.cpp(97) : error C2065: 'GWLP_WNDPROC' : nichtdeklarierter Bezeichner
    *.cpp(97) : error C2061: Syntaxfehler : Bezeichner 'LONG_PTR'
    *

    Yo, ich habe all die Headerfile ge-included. Also

    #include <windows.h>
    #include <winuser.h>
    #include <windef.h>
    #include <basetsd.h>
    

    Und die Library User32.lib habe ich auch drin. Trotzdem funktioniert es nicht. Ist doch komisch, oder?!

    Danke schon mal im Voraus!

    CQ.



  • Das Problem hatte ich auch, ich hatte einfach zu alte Header. Du musst wohl das neue SDK installieren.
    Wenn nicht, tut es auch SetWindowLong, GWL_WNDPROC und LONG



  • Hallöchen,

    vielen Dank erstmal für Eure Mühe! Ich habe folgenden Code mal eingebaut:

    BOOL CALLBACK StaticWndProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) {
    TRACKMOUSEEVENT tme;
    
        switch (msg) {
            case WM_MOUSEMOVE:   tme.cbSize = sizeof(tme);
                     tme.dwFlags = TME_HOVER;
                     tme.dwHoverTime = 1;
    
                     tme.dwFlags = TME_CANCEL | TME_HOVER | TME_LEAVE;
                     tme.hwndTrack = hwnd;
                     tme.dwHoverTime = HOVER_DEFAULT;
                     _TrackMouseEvent(&tme);
    
            break;
    
            case WM_MOUSEHOVER: tme.cbSize = sizeof(tme);
                        tme.dwFlags = TME_LEAVE;
                        tme.hwndTrack = hwnd;
                        tme.dwHoverTime = HOVER_DEFAULT;
    
                        SetFontOfStatic(hwnd, IDC_STATIC_VERGESSEN);
    
                        _TrackMouseEvent(&tme);
    
                        RedrawWindow(hwnd, NULL,    NULL, RDW_INVALIDATE | RDW_UPDATENOW | RDW_ERASE);
                        SendMessage(hwnd, WM_PAINT, 0, 0);
    
            break;
    
            case WM_MOUSELEAVE: tme.cbSize = sizeof(tme);
                        tme.dwFlags = TME_HOVER;
                        tme.hwndTrack = hwnd;
                        tme.dwHoverTime = HOVER_DEFAULT;
    
                        _TrackMouseEvent(&tme);
    
                        SendMessage(hwnd, WM_PAINT, 0, 0);
    
            break;
        }
    
        return DefWindowProc (hwnd, msg, wp, lp) ;
    
    }
    

    und gesetzt habe ich das ganze wie folgt:

    SetWindowLong(GetDlgItem(hw, IDC_STATIC_VERGESSEN), GWL_WNDPROC, (long) StaticWndProc);
    

    Jedenfalls der Effekt der Geschichte ist der, daß das Static nun gar nicht mehr angezeigt wird.

    Hat jemand von Euch eine Idee dazu?

    THX, CQ.



  • WNDPROC g_wndprocOld;
    
    BOOL CALLBACK StaticWndProc(HWND hwnd, UINT msg, WPARAM wp, LPARAM lp) {
    TRACKMOUSEEVENT tme;
    static BOOL bHot = FALSE;
    
        switch (msg) {
            case WM_MOUSEMOVE:
                 if(!bHot)
                 {
                     bHot = TRUE;
    
                     tme.cbSize      = sizeof(tme);
                     tme.dwFlags     = TME_LEAVE;
                     tme.hwndTrack   = hwnd;
                     tme.dwHoverTime = HOVER_DEFAULT;
                     _TrackMouseEvent(&tme);
                     SetFontOfStatic(hwnd, IDC_STATIC_VERGESSEN);
                     InvalidateRect(hWnd, NULL, TRUE);
                 }
                 break;
            case WM_MOUSELEAVE:
                 bHot = FALSE;
                 InvalidateRect(hWnd, NULL, TRUE);
                 break;
        }
      return(CallWindowProc(g_wndprocOld, hwnd, msg, wp, lp));
    }
    

    Setzen dann so:

    g_wndprocOld = (WNDPROC)SetWindowLong(GetDlgItem(hw, IDC_STATIC_VERGESSEN), GWL_WNDPROC, (LONG)StaticWndProc);
    

    Ich habe aber nichts getestet!



  • Hi!

    Vielen Dank!!! Leider klappt es so nicht. D.h. er springt in diese CASE Anweisungen gar nicht rein. Komisch. In meinem Code hat er es ja wenigstens noch gemacht...

    THX,

    CQ.



  • WM_MOUSEMOVE wird auch an das Parent des Statics gesendet, wenn die Maus über dem Static bewegt wird. Dann könnte man doch testen, ob sich der Cursor im WindowRect des Statics befindet per PtInRect(). Man könnte sich das SubClassing also sparen.



  • Genaugenommen habe ich über Spy++ gerade festgestellt, dass ein Static überhaupt kein WM_MOUSEMOVE empfängt. Aber vielleicht ist es ja anders, wenn es gesubclassed ist? 😕



  • WM_MOUSEMOVE wird auch an das Parent des Statics gesendet,

    Das halte ich für ein Gerücht.

    er springt in diese CASE Anweisungen gar nicht rein

    Wenn Du bei WM_MOUSEMOVE nicht ankommst, bewegst Du entweder nicht die Maus über das static oder Du hast bei SetWindowLong das flasche Fenster angegeben.



  • Genaugenommen habe ich über Spy++ gerade festgestellt, dass ein Static überhaupt kein WM_MOUSEMOVE empfängt.

    Unsinn.



  • Wenn ich mich richtig erinnere haben wir dazu ein Beispiel auf unserer HP (Link untenstehend).
    Allerdings bezieht sich das auf das Einbauen eines Hyperlinks in ein Fenster.
    Ist im Prinzip aber gleich. Dort ändert der Mauszeiger sich beim Überfahren..



  • Original erstellt von -King-:
    [quote]Genaugenommen habe ich über Spy++ gerade festgestellt, dass ein Static überhaupt kein WM_MOUSEMOVE empfängt.

    **
    Unsinn.**[/QUOTE]
    Na, dann mach das doch mal selber, verdammt noch mal! Jetzt bin ich wirklich ein bisschen böse. Ich habe ein Fenster mit einem WS_CHILD | WS_VISIBLE-Static darauf. OHNE SubClassing. UND DAS EMPFÄNGT LAUT SPY++ KEIN WM_MOUSEMOVE!!! 😡



  • Original erstellt von -King-:
    [quote]WM_MOUSEMOVE wird auch an das Parent des Statics gesendet,

    **Das halte ich für ein Gerücht.
    **[/QUOTE]
    Ich kann nur wiederholen: probier's selber aus! Spy++ sagt mir bestimmt nicht nur aus Spaß, dass WM_MOUSEMOVE an das Parent geschickt wird.



  • Mein Spy zeigt alles an, so wie es sich gehört. So schwierig ist das Programm doch auch gar nicht zu bedienen ...



  • Aber irgendwie kommen nur die Nachrichten an, wenn man das Static mit dem Style SS_NOTIFY erstellt. Verstehe garnicht wie die das geschafft haben zu verhindern, dass die ganzen Notifications gesendet werden. Gibt's da ne Option beim Registrieren der Klasse oder wie hat Microsoft das gemacht?



  • Aber irgendwie kommen nur die Nachrichten an, wenn man das Static mit dem Style SS_NOTIFY erstellt.

    Das ist nun wieder ganz was anderes. SS_NOTIFY bewirkt, daß das static bestimmte Nachrichten an das Parent sendet. WM_MOUSEMOVE wird von Windows versendet und kommt auch beim static an (wie bei jedem Fenster eben).

    Verstehe garnicht wie die das geschafft haben zu verhindern, dass die ganzen Notifications gesendet werden. Gibt's da ne Option beim Registrieren der Klasse oder wie hat Microsoft das gemacht?

    Von welchen Notifications sprichts Du?



  • @-King-
    DU scheinst Schwierigkeiten mit dem Programm zu haben.

    So, ich hab das jetzt mal explizit ausprobiert. Meine WindowProc (des Parent) sieht jetzt so aus:

    static bool   bHot;
    static POINT  pt;
    static RECT   rect;
    
    switch(msg)
    {
       case WM_MOUSEMOVE:
          pt = Point(LOWORD(Msg.LParam), HIWORD(Msg.LParam));
          // Das Static befindet sich an (0,0). Daher gehts auch mit ClientRect
          ::GetClientRect(hStat, &rect);
          if(PtInRect(&rect, pt))
          {
             bHot = TRUE;
             SetWindowText(hStat, "HALLO_OVER");
          }
          else
             if(bHot)
             {
                bHot = FALSE;
                SetWindowText(hStat, "HALLO");
             }
          break;
    }
    // An die Default-Proc weitergeben
    

    Und das funktioniert wunderbar!!! Wenn ich im Static bin, steht da HALLO_OVER, sonst nur HALLO. Auch Könige dürfen sich mal irren, -King-. 😉

    [ Dieser Beitrag wurde am 29.08.2002 um 15:31 Uhr von WebFritzi editiert. ]



  • Ok, Du hast recht. Bei mir ist das zwar anders, aber was soll's. Mein Windows scheint kaputt zu sein ...

    <edit> .. und das auf drei verschiedenen Rechnern. </edit>

    [ Dieser Beitrag wurde am 29.08.2002 um 15:39 Uhr von -King- editiert. ]



  • Bei mir ist es auch so:

    Gesubclasstes Static-Control ohne SS_NOTIFY -> erhält keine WM_MOUSEMOVE Nachrichten

    Gesubclasstes Static-Control mit SS_NOTIFY -> erhält WM_MOUSEMOVE Nachrichten

    Werde es später aber nochmals testen.


Anmelden zum Antworten