More code moved to the X11 driver (bitmap and palette and misc).
[wine] / windows / multimon.c
1 /*
2  * Multimonitor APIs
3  *
4  * Copyright 1998 Turchanov Sergey
5  */
6
7 #include "monitor.h"
8 #include "winbase.h"
9 #include "winuser.h"
10
11 /**********************************************************************/
12
13 MONITOR_DRIVER *MONITOR_Driver;
14
15 /**********************************************************************/
16
17 #define xPRIMARY_MONITOR ((HMONITOR)0x12340042)
18
19 MONITOR MONITOR_PrimaryMonitor;
20
21 /***********************************************************************
22  *              MONITOR_GetMonitor
23  */
24 MONITOR *MONITOR_GetMonitor(HMONITOR hMonitor)
25 {
26   if(hMonitor == xPRIMARY_MONITOR)
27     {
28       return &MONITOR_PrimaryMonitor;
29     }
30   else
31     {
32       return NULL;
33     }
34 }
35
36 /***********************************************************************
37  *              MONITOR_Initialize
38  */
39 void MONITOR_Initialize(MONITOR *pMonitor)
40 {
41   MONITOR_Driver->pInitialize(pMonitor);
42 }
43
44 /***********************************************************************
45  *              MONITOR_Finalize
46  */
47 void MONITOR_Finalize(MONITOR *pMonitor)
48 {
49   MONITOR_Driver->pFinalize(pMonitor);
50 }
51
52 /***********************************************************************
53  *              MONITOR_IsSingleWindow
54  */
55 BOOL MONITOR_IsSingleWindow(MONITOR *pMonitor)
56 {
57   return MONITOR_Driver->pIsSingleWindow(pMonitor);
58 }
59
60 /***********************************************************************
61  *              MONITOR_GetWidth
62  */
63 int MONITOR_GetWidth(MONITOR *pMonitor)
64 {
65   return MONITOR_Driver->pGetWidth(pMonitor);
66 }
67
68 /***********************************************************************
69  *              MONITOR_GetHeight
70  */
71 int MONITOR_GetHeight(MONITOR *pMonitor)
72 {
73   return MONITOR_Driver->pGetHeight(pMonitor);
74 }
75
76 /***********************************************************************
77  *              MONITOR_GetDepth
78  */
79 int MONITOR_GetDepth(MONITOR *pMonitor)
80 {
81   return MONITOR_Driver->pGetDepth(pMonitor);
82 }
83
84 /***********************************************************************
85  *              MONITOR_GetScreenSaveActive
86  */
87 BOOL MONITOR_GetScreenSaveActive(MONITOR *pMonitor)
88 {
89   return MONITOR_Driver->pGetScreenSaveActive(pMonitor);
90 }
91
92 /***********************************************************************
93  *              MONITOR_SetScreenSaveActive
94  */
95 void MONITOR_SetScreenSaveActive(MONITOR *pMonitor, BOOL bActivate)
96 {
97   MONITOR_Driver->pSetScreenSaveActive(pMonitor, bActivate);
98 }
99
100 /***********************************************************************
101  *              MONITOR_GetScreenSaveTimeout
102  */
103 int MONITOR_GetScreenSaveTimeout(MONITOR *pMonitor)
104 {
105   return MONITOR_Driver->pGetScreenSaveTimeout(pMonitor);
106 }
107
108 /***********************************************************************
109  *              MONITOR_SetScreenSaveTimeout
110  */
111 void MONITOR_SetScreenSaveTimeout(MONITOR *pMonitor, int nTimeout)
112 {
113   MONITOR_Driver->pSetScreenSaveTimeout(pMonitor, nTimeout);
114 }
115
116
117 /**********************************************************************/
118
119 HMONITOR WINAPI MonitorFromPoint(POINT ptScreenCoords, DWORD dwFlags)
120 {
121     if ((dwFlags & (MONITOR_DEFAULTTOPRIMARY | MONITOR_DEFAULTTONEAREST)) ||
122         ((ptScreenCoords.x >= 0) &&
123         (ptScreenCoords.x < GetSystemMetrics(SM_CXSCREEN)) &&
124         (ptScreenCoords.y >= 0) &&
125         (ptScreenCoords.y < GetSystemMetrics(SM_CYSCREEN))))
126     {
127         return xPRIMARY_MONITOR;
128     }
129         return NULL;
130 }
131
132 HMONITOR WINAPI MonitorFromRect(LPRECT lprcScreenCoords, DWORD dwFlags)
133 {
134     if ((dwFlags & (MONITOR_DEFAULTTOPRIMARY | MONITOR_DEFAULTTONEAREST)) ||
135         ((lprcScreenCoords->right > 0) &&
136         (lprcScreenCoords->bottom > 0) &&
137         (lprcScreenCoords->left < GetSystemMetrics(SM_CXSCREEN)) &&
138         (lprcScreenCoords->top < GetSystemMetrics(SM_CYSCREEN))))
139     {
140         return xPRIMARY_MONITOR;
141     }
142     return NULL;
143 }
144
145 HMONITOR WINAPI MonitorFromWindow(HWND hWnd, DWORD dwFlags)
146 {
147     WINDOWPLACEMENT wp;
148
149     if (dwFlags & (MONITOR_DEFAULTTOPRIMARY | MONITOR_DEFAULTTONEAREST))
150         return xPRIMARY_MONITOR;
151
152     if (IsIconic(hWnd) ? 
153             GetWindowPlacement(hWnd, &wp) : 
154             GetWindowRect(hWnd, &wp.rcNormalPosition)) {
155
156         return MonitorFromRect(&wp.rcNormalPosition, dwFlags);
157     }
158
159     return NULL;
160 }
161
162 BOOL WINAPI GetMonitorInfoA(HMONITOR hMonitor, LPMONITORINFO lpMonitorInfo)
163 {
164     RECT rcWork;
165
166     if ((hMonitor == xPRIMARY_MONITOR) &&
167         lpMonitorInfo &&
168         (lpMonitorInfo->cbSize >= sizeof(MONITORINFO)) &&
169         SystemParametersInfoA(SPI_GETWORKAREA, 0, &rcWork, 0))
170     {
171         lpMonitorInfo->rcMonitor.left = 0;
172         lpMonitorInfo->rcMonitor.top  = 0;
173         lpMonitorInfo->rcMonitor.right  = GetSystemMetrics(SM_CXSCREEN);
174         lpMonitorInfo->rcMonitor.bottom = GetSystemMetrics(SM_CYSCREEN);
175         lpMonitorInfo->rcWork = rcWork;
176         lpMonitorInfo->dwFlags = MONITORINFOF_PRIMARY;
177         
178         if (lpMonitorInfo->cbSize >= sizeof(MONITORINFOEXA))
179             lstrcpyA(((MONITORINFOEXA*)lpMonitorInfo)->szDevice, "DISPLAY");
180
181         return TRUE;
182     }
183
184     return FALSE;
185 }
186
187 BOOL WINAPI GetMonitorInfoW(HMONITOR hMonitor, LPMONITORINFO lpMonitorInfo)
188 {
189     RECT rcWork;
190
191     if ((hMonitor == xPRIMARY_MONITOR) &&
192         lpMonitorInfo &&
193         (lpMonitorInfo->cbSize >= sizeof(MONITORINFO)) &&
194         SystemParametersInfoW(SPI_GETWORKAREA, 0, &rcWork, 0))
195     {
196         lpMonitorInfo->rcMonitor.left = 0;
197         lpMonitorInfo->rcMonitor.top  = 0;
198         lpMonitorInfo->rcMonitor.right  = GetSystemMetrics(SM_CXSCREEN);
199         lpMonitorInfo->rcMonitor.bottom = GetSystemMetrics(SM_CYSCREEN);
200         lpMonitorInfo->rcWork = rcWork;
201         lpMonitorInfo->dwFlags = MONITORINFOF_PRIMARY;
202
203         if (lpMonitorInfo->cbSize >= sizeof(MONITORINFOEXW))
204             lstrcpyW(((MONITORINFOEXW*)lpMonitorInfo)->szDevice, (LPCWSTR)"D\0I\0S\0P\0L\0A\0Y\0\0");
205
206         return TRUE;
207     }
208
209     return FALSE;
210 }
211
212 BOOL WINAPI EnumDisplayMonitors(
213         HDC             hdcOptionalForPainting,
214         LPRECT         lprcEnumMonitorsThatIntersect,
215         MONITORENUMPROC lpfnEnumProc,
216         LPARAM          dwData)
217 {
218     RECT rcLimit;
219
220     if (!lpfnEnumProc)
221         return FALSE;
222
223     rcLimit.left   = 0;
224     rcLimit.top    = 0;
225     rcLimit.right  = GetSystemMetrics(SM_CXSCREEN);
226     rcLimit.bottom = GetSystemMetrics(SM_CYSCREEN);
227
228     if (hdcOptionalForPainting)
229     {
230         RECT    rcClip;
231         POINT   ptOrg;
232
233         switch (GetClipBox(hdcOptionalForPainting, &rcClip))
234         {
235         default:
236             if (!GetDCOrgEx(hdcOptionalForPainting, &ptOrg))
237                 return FALSE;
238
239             OffsetRect(&rcLimit, -ptOrg.x, -ptOrg.y);
240             if (IntersectRect(&rcLimit, &rcLimit, &rcClip) &&
241                 (!lprcEnumMonitorsThatIntersect ||
242                      IntersectRect(&rcLimit, &rcLimit, lprcEnumMonitorsThatIntersect))) {
243
244                 break;
245             }
246             /*fall thru */
247         case NULLREGION:
248              return TRUE;
249         case ERROR:
250              return FALSE;
251         }
252     } else {
253         if (    lprcEnumMonitorsThatIntersect &&
254                 !IntersectRect(&rcLimit, &rcLimit, lprcEnumMonitorsThatIntersect)) {
255
256             return TRUE;
257         }
258     }
259
260     return lpfnEnumProc(
261             xPRIMARY_MONITOR,
262             hdcOptionalForPainting,
263             &rcLimit,
264             dwData);
265 }