Release 960805
[wine] / windows / focus.c
1 /*
2  * Focus functions
3  *
4  * Copyright 1993 David Metcalfe
5  *           1994 Alexandre Julliard
6  *           1995 Alex Korobka
7  *
8  */
9
10 #include "win.h"
11 #include "winpos.h"
12 #include "hook.h"
13 #include "color.h"
14 #include "message.h"
15 #include "options.h"
16
17 static HWND hwndFocus = 0;
18
19 /*****************************************************************
20  *               FOCUS_SetXFocus
21  *
22  * Set the X focus.
23  * Explicit colormap management seems to work only with OLVWM.
24  */
25 void FOCUS_SetXFocus( HWND hwnd )
26 {
27     XWindowAttributes win_attr;
28     Window win;
29
30     /* Only mess with the X focus if there's */
31     /* no desktop window and no window manager. */
32     if ((rootWindow != DefaultRootWindow(display)) || Options.managed) return;
33
34     if (!hwnd)  /* If setting the focus to 0, uninstall the colormap */
35     {
36         if (COLOR_GetSystemPaletteFlags() & COLOR_PRIVATE)
37             XUninstallColormap( display, COLOR_GetColormap() );
38         return;
39     }
40
41       /* Set X focus and install colormap */
42
43     if (!(win = WIN_GetXWindow( hwnd ))) return;
44     if (!XGetWindowAttributes( display, win, &win_attr ) ||
45         (win_attr.map_state != IsViewable))
46         return;  /* If window is not viewable, don't change anything */
47
48     XSetInputFocus( display, win, RevertToParent, CurrentTime );
49     if (COLOR_GetSystemPaletteFlags() & COLOR_PRIVATE)
50         XInstallColormap( display, COLOR_GetColormap() );
51
52     EVENT_Synchronize();
53 }
54
55 /*****************************************************************
56  *               FOCUS_SwitchFocus 
57  */
58 void FOCUS_SwitchFocus(HWND hFocusFrom, HWND hFocusTo)
59 {
60     hwndFocus = hFocusTo;
61
62     if (hFocusFrom) SendMessage16( hFocusFrom, WM_KILLFOCUS, (WPARAM)hFocusTo, 0L);
63     if( !hFocusTo || hFocusTo != hwndFocus )
64         return;
65
66     SendMessage16( hFocusTo, WM_SETFOCUS, (WPARAM)hFocusFrom, 0L);
67     FOCUS_SetXFocus( hFocusTo );
68 }
69
70
71 /*****************************************************************
72  *               SetFocus            (USER.22)
73  */
74 HWND SetFocus(HWND hwnd)
75 {
76     HWND hWndPrevFocus, hwndTop = hwnd;
77     WND *wndPtr = WIN_FindWndPtr( hwnd );
78
79     if (wndPtr)
80     {
81           /* Check if we can set the focus to this window */
82
83         while ( (wndPtr->dwStyle & (WS_CHILD | WS_POPUP)) == WS_CHILD  )
84         {
85             if ( wndPtr->dwStyle & ( WS_MINIMIZE | WS_DISABLED) )
86                  return 0;
87             if (!(wndPtr = wndPtr->parent)) return 0;
88             hwndTop = wndPtr->hwndSelf;
89         }
90
91         if( hwnd == hwndFocus ) return hwnd;
92
93         /* call hooks */
94         if( HOOK_CallHooks( WH_CBT, HCBT_SETFOCUS, (WPARAM)hwnd, (LPARAM)hwndFocus) )
95             return 0;
96
97         /* activate hwndTop if needed. */
98         if (hwndTop != GetActiveWindow())
99         {
100             if (!WINPOS_SetActiveWindow(hwndTop, 0, 0)) return 0;
101
102             if (!IsWindow( hwnd )) return 0;  /* Abort if window destroyed */
103         }
104     }
105     else if( HOOK_CallHooks( WH_CBT, HCBT_SETFOCUS, 0, (LPARAM)hwndFocus ) )
106              return 0;
107
108       /* Change focus and send messages */
109     hWndPrevFocus = hwndFocus;
110
111     FOCUS_SwitchFocus( hwndFocus , hwnd );
112
113     return hWndPrevFocus;
114 }
115
116
117 /*****************************************************************
118  *               GetFocus            (USER.23)
119  */
120 HWND GetFocus(void)
121 {
122     return hwndFocus;
123 }
124
125