kernel32/nls: Added LOCALE_SNAN entries.
[wine.git] / dlls / winemac.drv / gdi.c
blob896016bfb2112135bbeb1da07f78ce946760a662
1 /*
2 * Mac graphics driver initialisation functions
4 * Copyright 1996 Alexandre Julliard
5 * Copyright 2011, 2012, 2013 Ken Thomases for CodeWeavers, Inc.
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #include "config.h"
24 #include "macdrv.h"
25 #include "winreg.h"
27 WINE_DEFAULT_DEBUG_CHANNEL(macdrv);
30 typedef struct
32 struct gdi_physdev dev;
33 } MACDRV_PDEVICE;
35 static inline MACDRV_PDEVICE *get_macdrv_dev(PHYSDEV dev)
37 return (MACDRV_PDEVICE*)dev;
41 /* a few dynamic device caps */
42 static CGRect desktop_rect; /* virtual desktop rectangle */
43 static int horz_size; /* horz. size of screen in millimeters */
44 static int vert_size; /* vert. size of screen in millimeters */
45 static int horz_res; /* width in pixels of screen */
46 static int vert_res; /* height in pixels of screen */
47 static int desktop_horz_res; /* width in pixels of virtual desktop */
48 static int desktop_vert_res; /* height in pixels of virtual desktop */
49 static int bits_per_pixel; /* pixel depth of screen */
50 static int device_data_valid; /* do the above variables have up-to-date values? */
52 int retina_on = FALSE;
54 static CRITICAL_SECTION device_data_section;
55 static CRITICAL_SECTION_DEBUG critsect_debug =
57 0, 0, &device_data_section,
58 { &critsect_debug.ProcessLocksList, &critsect_debug.ProcessLocksList },
59 0, 0, { (DWORD_PTR)(__FILE__ ": device_data_section") }
61 static CRITICAL_SECTION device_data_section = { &critsect_debug, -1, 0, 0, 0, 0 };
64 static const struct gdi_dc_funcs macdrv_funcs;
66 /***********************************************************************
67 * compute_desktop_rect
69 static void compute_desktop_rect(void)
71 CGDirectDisplayID displayIDs[32];
72 uint32_t count, i;
74 desktop_rect = CGRectNull;
75 if (CGGetActiveDisplayList(sizeof(displayIDs)/sizeof(displayIDs[0]),
76 displayIDs, &count) != kCGErrorSuccess ||
77 !count)
79 displayIDs[0] = CGMainDisplayID();
80 count = 1;
83 for (i = 0; i < count; i++)
84 desktop_rect = CGRectUnion(desktop_rect, CGDisplayBounds(displayIDs[i]));
85 desktop_rect = cgrect_win_from_mac(desktop_rect);
89 /***********************************************************************
90 * macdrv_get_desktop_rect
92 * Returns the rectangle encompassing all the screens.
94 CGRect macdrv_get_desktop_rect(void)
96 CGRect ret;
98 EnterCriticalSection(&device_data_section);
100 if (!device_data_valid)
102 check_retina_status();
103 compute_desktop_rect();
105 ret = desktop_rect;
107 LeaveCriticalSection(&device_data_section);
109 TRACE("%s\n", wine_dbgstr_cgrect(ret));
111 return ret;
115 /**********************************************************************
116 * device_init
118 * Perform initializations needed upon creation of the first device.
120 static void device_init(void)
122 CGDirectDisplayID mainDisplay = CGMainDisplayID();
123 CGSize size_mm = CGDisplayScreenSize(mainDisplay);
124 CGDisplayModeRef mode = CGDisplayCopyDisplayMode(mainDisplay);
126 check_retina_status();
128 /* Initialize device caps */
129 horz_size = size_mm.width;
130 vert_size = size_mm.height;
132 bits_per_pixel = 32;
133 if (mode)
135 CFStringRef pixelEncoding = CGDisplayModeCopyPixelEncoding(mode);
137 horz_res = CGDisplayModeGetWidth(mode);
138 vert_res = CGDisplayModeGetHeight(mode);
140 if (pixelEncoding)
142 if (CFEqual(pixelEncoding, CFSTR(IO32BitDirectPixels)))
143 bits_per_pixel = 32;
144 else if (CFEqual(pixelEncoding, CFSTR(IO16BitDirectPixels)))
145 bits_per_pixel = 16;
146 else if (CFEqual(pixelEncoding, CFSTR(IO8BitIndexedPixels)))
147 bits_per_pixel = 8;
148 CFRelease(pixelEncoding);
151 CGDisplayModeRelease(mode);
153 else
155 horz_res = CGDisplayPixelsWide(mainDisplay);
156 vert_res = CGDisplayPixelsHigh(mainDisplay);
159 if (retina_on)
161 horz_res *= 2;
162 vert_res *= 2;
165 compute_desktop_rect();
166 desktop_horz_res = desktop_rect.size.width;
167 desktop_vert_res = desktop_rect.size.height;
169 device_data_valid = TRUE;
173 void macdrv_reset_device_metrics(void)
175 EnterCriticalSection(&device_data_section);
176 device_data_valid = FALSE;
177 LeaveCriticalSection(&device_data_section);
181 static MACDRV_PDEVICE *create_mac_physdev(void)
183 MACDRV_PDEVICE *physDev;
185 EnterCriticalSection(&device_data_section);
186 if (!device_data_valid) device_init();
187 LeaveCriticalSection(&device_data_section);
189 if (!(physDev = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*physDev)))) return NULL;
191 return physDev;
195 /**********************************************************************
196 * CreateDC (MACDRV.@)
198 static BOOL macdrv_CreateDC(PHYSDEV *pdev, LPCWSTR driver, LPCWSTR device,
199 LPCWSTR output, const DEVMODEW* initData)
201 MACDRV_PDEVICE *physDev = create_mac_physdev();
203 TRACE("pdev %p hdc %p driver %s device %s output %s initData %p\n", pdev,
204 (*pdev)->hdc, debugstr_w(driver),debugstr_w(device), debugstr_w(output),
205 initData);
207 if (!physDev) return FALSE;
209 push_dc_driver(pdev, &physDev->dev, &macdrv_funcs);
210 return TRUE;
214 /**********************************************************************
215 * CreateCompatibleDC (MACDRV.@)
217 static BOOL macdrv_CreateCompatibleDC(PHYSDEV orig, PHYSDEV *pdev)
219 MACDRV_PDEVICE *physDev = create_mac_physdev();
221 TRACE("orig %p orig->hdc %p pdev %p pdev->hdc %p\n", orig, (orig ? orig->hdc : NULL), pdev,
222 ((pdev && *pdev) ? (*pdev)->hdc : NULL));
224 if (!physDev) return FALSE;
226 push_dc_driver(pdev, &physDev->dev, &macdrv_funcs);
227 return TRUE;
231 /**********************************************************************
232 * DeleteDC (MACDRV.@)
234 static BOOL macdrv_DeleteDC(PHYSDEV dev)
236 MACDRV_PDEVICE *physDev = get_macdrv_dev(dev);
238 TRACE("hdc %p\n", dev->hdc);
240 HeapFree(GetProcessHeap(), 0, physDev);
241 return TRUE;
245 /***********************************************************************
246 * GetDeviceCaps (MACDRV.@)
248 static INT macdrv_GetDeviceCaps(PHYSDEV dev, INT cap)
250 INT ret;
252 EnterCriticalSection(&device_data_section);
254 if (!device_data_valid) device_init();
256 switch(cap)
258 case HORZSIZE:
259 ret = horz_size;
260 break;
261 case VERTSIZE:
262 ret = vert_size;
263 break;
264 case HORZRES:
265 ret = horz_res;
266 break;
267 case VERTRES:
268 ret = vert_res;
269 break;
270 case DESKTOPHORZRES:
271 ret = desktop_horz_res;
272 break;
273 case DESKTOPVERTRES:
274 ret = desktop_vert_res;
275 break;
276 case BITSPIXEL:
277 ret = bits_per_pixel;
278 break;
279 default:
280 LeaveCriticalSection(&device_data_section);
281 dev = GET_NEXT_PHYSDEV( dev, pGetDeviceCaps );
282 return dev->funcs->pGetDeviceCaps( dev, cap );
285 TRACE("cap %d -> %d\n", cap, ret);
287 LeaveCriticalSection(&device_data_section);
288 return ret;
292 static const struct gdi_dc_funcs macdrv_funcs =
294 NULL, /* pAbortDoc */
295 NULL, /* pAbortPath */
296 NULL, /* pAlphaBlend */
297 NULL, /* pAngleArc */
298 NULL, /* pArc */
299 NULL, /* pArcTo */
300 NULL, /* pBeginPath */
301 NULL, /* pBlendImage */
302 NULL, /* pChord */
303 NULL, /* pCloseFigure */
304 macdrv_CreateCompatibleDC, /* pCreateCompatibleDC */
305 macdrv_CreateDC, /* pCreateDC */
306 macdrv_DeleteDC, /* pDeleteDC */
307 NULL, /* pDeleteObject */
308 NULL, /* pDeviceCapabilities */
309 NULL, /* pEllipse */
310 NULL, /* pEndDoc */
311 NULL, /* pEndPage */
312 NULL, /* pEndPath */
313 NULL, /* pEnumFonts */
314 NULL, /* pEnumICMProfiles */
315 NULL, /* pExcludeClipRect */
316 NULL, /* pExtDeviceMode */
317 NULL, /* pExtEscape */
318 NULL, /* pExtFloodFill */
319 NULL, /* pExtSelectClipRgn */
320 NULL, /* pExtTextOut */
321 NULL, /* pFillPath */
322 NULL, /* pFillRgn */
323 NULL, /* pFlattenPath */
324 NULL, /* pFontIsLinked */
325 NULL, /* pFrameRgn */
326 NULL, /* pGdiComment */
327 NULL, /* pGetBoundsRect */
328 NULL, /* pGetCharABCWidths */
329 NULL, /* pGetCharABCWidthsI */
330 NULL, /* pGetCharWidth */
331 macdrv_GetDeviceCaps, /* pGetDeviceCaps */
332 macdrv_GetDeviceGammaRamp, /* pGetDeviceGammaRamp */
333 NULL, /* pGetFontData */
334 NULL, /* pGetFontRealizationInfo */
335 NULL, /* pGetFontUnicodeRanges */
336 NULL, /* pGetGlyphIndices */
337 NULL, /* pGetGlyphOutline */
338 NULL, /* pGetICMProfile */
339 NULL, /* pGetImage */
340 NULL, /* pGetKerningPairs */
341 NULL, /* pGetNearestColor */
342 NULL, /* pGetOutlineTextMetrics */
343 NULL, /* pGetPixel */
344 NULL, /* pGetSystemPaletteEntries */
345 NULL, /* pGetTextCharsetInfo */
346 NULL, /* pGetTextExtentExPoint */
347 NULL, /* pGetTextExtentExPointI */
348 NULL, /* pGetTextFace */
349 NULL, /* pGetTextMetrics */
350 NULL, /* pGradientFill */
351 NULL, /* pIntersectClipRect */
352 NULL, /* pInvertRgn */
353 NULL, /* pLineTo */
354 NULL, /* pModifyWorldTransform */
355 NULL, /* pMoveTo */
356 NULL, /* pOffsetClipRgn */
357 NULL, /* pOffsetViewportOrg */
358 NULL, /* pOffsetWindowOrg */
359 NULL, /* pPaintRgn */
360 NULL, /* pPatBlt */
361 NULL, /* pPie */
362 NULL, /* pPolyBezier */
363 NULL, /* pPolyBezierTo */
364 NULL, /* pPolyDraw */
365 NULL, /* pPolyPolygon */
366 NULL, /* pPolyPolyline */
367 NULL, /* pPolygon */
368 NULL, /* pPolyline */
369 NULL, /* pPolylineTo */
370 NULL, /* pPutImage */
371 NULL, /* pRealizeDefaultPalette */
372 NULL, /* pRealizePalette */
373 NULL, /* pRectangle */
374 NULL, /* pResetDC */
375 NULL, /* pRestoreDC */
376 NULL, /* pRoundRect */
377 NULL, /* pSaveDC */
378 NULL, /* pScaleViewportExt */
379 NULL, /* pScaleWindowExt */
380 NULL, /* pSelectBitmap */
381 NULL, /* pSelectBrush */
382 NULL, /* pSelectClipPath */
383 NULL, /* pSelectFont */
384 NULL, /* pSelectPalette */
385 NULL, /* pSelectPen */
386 NULL, /* pSetArcDirection */
387 NULL, /* pSetBkColor */
388 NULL, /* pSetBkMode */
389 NULL, /* pSetBoundsRect */
390 NULL, /* pSetDCBrushColor */
391 NULL, /* pSetDCPenColor */
392 NULL, /* pSetDIBitsToDevice */
393 NULL, /* pSetDeviceClipping */
394 macdrv_SetDeviceGammaRamp, /* pSetDeviceGammaRamp */
395 NULL, /* pSetLayout */
396 NULL, /* pSetMapMode */
397 NULL, /* pSetMapperFlags */
398 NULL, /* pSetPixel */
399 NULL, /* pSetPolyFillMode */
400 NULL, /* pSetROP2 */
401 NULL, /* pSetRelAbs */
402 NULL, /* pSetStretchBltMode */
403 NULL, /* pSetTextAlign */
404 NULL, /* pSetTextCharacterExtra */
405 NULL, /* pSetTextColor */
406 NULL, /* pSetTextJustification */
407 NULL, /* pSetViewportExt */
408 NULL, /* pSetViewportOrg */
409 NULL, /* pSetWindowExt */
410 NULL, /* pSetWindowOrg */
411 NULL, /* pSetWorldTransform */
412 NULL, /* pStartDoc */
413 NULL, /* pStartPage */
414 NULL, /* pStretchBlt */
415 NULL, /* pStretchDIBits */
416 NULL, /* pStrokeAndFillPath */
417 NULL, /* pStrokePath */
418 NULL, /* pUnrealizePalette */
419 NULL, /* pWidenPath */
420 macdrv_wine_get_wgl_driver, /* wine_get_wgl_driver */
421 GDI_PRIORITY_GRAPHICS_DRV /* priority */
425 /******************************************************************************
426 * macdrv_get_gdi_driver
428 const struct gdi_dc_funcs * CDECL macdrv_get_gdi_driver(unsigned int version)
430 if (version != WINE_GDI_DRIVER_VERSION)
432 ERR("version mismatch, gdi32 wants %u but winemac has %u\n", version, WINE_GDI_DRIVER_VERSION);
433 return NULL;
435 return &macdrv_funcs;