15 UNICODE_STRING Device
, Output
;
17 BOOL Display
= FALSE
, Default
= FALSE
;
22 if ( !ghSpooler
&& !LoadTheSpoolerDrv())
24 DPRINT1("WinSpooler.Drv Did not load!\n");
28 DPRINT("WinSpooler.Drv Loaded! hMod -> 0x%p\n", ghSpooler
);
31 if ((!lpwszDevice
) && (!lpwszDriver
))
33 Default
= TRUE
; // Ask Win32k to set Default device.
34 Display
= TRUE
; // Most likely to be DISPLAY.
38 if ((lpwszDevice
) && (wcslen(lpwszDevice
) != 0)) // First
40 if (!_wcsnicmp(lpwszDevice
, L
"\\\\.\\DISPLAY",11)) Display
= TRUE
;
41 RtlInitUnicodeString(&Device
, lpwszDevice
);
45 if (lpwszDriver
) // Second
47 if ((!_wcsnicmp(lpwszDriver
, L
"DISPLAY",7)) ||
48 (!_wcsnicmp(lpwszDriver
, L
"\\\\.\\DISPLAY",11))) Display
= TRUE
;
49 RtlInitUnicodeString(&Device
, lpwszDriver
);
54 if (lpwszOutput
) RtlInitUnicodeString(&Output
, lpwszOutput
);
58 //Handle Print device or something else.
59 DPRINT1("Not a DISPLAY device! %wZ\n", &Device
);
62 hdc
= NtGdiOpenDCW((Default
? NULL
: &Device
),
63 (PDEVMODEW
) lpInitData
,
64 (lpwszOutput
? &Output
: NULL
),
65 iType
, // DCW 0 and ICW 1.
70 // Handle something other than a normal dc object.
71 if (GDI_HANDLE_GET_TYPE(hdc
) != GDI_OBJECT_TYPE_DC
)
76 GdiGetHandleUserData(hdc
, GDI_OBJECT_TYPE_DC
, (PVOID
*)&Dc_Attr
);
78 pLDC
= LocalAlloc(LMEM_ZEROINIT
, sizeof(LDC
));
80 Dc_Attr
->pvLDC
= pLDC
;
82 pLDC
->iType
= LDC_LDC
; // 1 (init) local DC, 2 EMF LDC
83 DbgPrint("DC_ATTR Allocated -> 0x%x\n",Dc_Attr
);
101 hdcNew
= NtGdiCreateCompatibleDC(hdc
);
105 if (GdiGetHandleUserData(hdc
, GDI_OBJECT_TYPE_DC
, (PVOID
*)&pdcattr
))
107 if (pdcattr
->pvLIcm
) IcmCompatibleDC(hdcNew
, hdc
, pdcattr
);
124 CONST DEVMODEA
* lpdvmInit
)
126 ANSI_STRING DriverA
, DeviceA
, OutputA
;
127 UNICODE_STRING DriverU
, DeviceU
, OutputU
;
128 LPDEVMODEW dvmInitW
= NULL
;
132 * If needed, convert to Unicode
133 * any string parameter.
136 if (lpszDriver
!= NULL
)
138 RtlInitAnsiString(&DriverA
, (LPSTR
)lpszDriver
);
139 RtlAnsiStringToUnicodeString(&DriverU
, &DriverA
, TRUE
);
143 DriverU
.Buffer
= NULL
;
146 if (lpszDevice
!= NULL
)
148 RtlInitAnsiString(&DeviceA
, (LPSTR
)lpszDevice
);
149 RtlAnsiStringToUnicodeString(&DeviceU
, &DeviceA
, TRUE
);
153 DeviceU
.Buffer
= NULL
;
156 if (lpszOutput
!= NULL
)
158 RtlInitAnsiString(&OutputA
, (LPSTR
)lpszOutput
);
159 RtlAnsiStringToUnicodeString(&OutputU
, &OutputA
, TRUE
);
163 OutputU
.Buffer
= NULL
;
166 if (lpdvmInit
!= NULL
)
167 dvmInitW
= GdiConvertToDevmodeW((LPDEVMODEA
)lpdvmInit
);
169 hdc
= IntCreateDICW(DriverU
.Buffer
,
172 lpdvmInit
? dvmInitW
: NULL
,
176 /* Free Unicode parameters. */
177 RtlFreeUnicodeString(&DriverU
);
178 RtlFreeUnicodeString(&DeviceU
);
179 RtlFreeUnicodeString(&OutputU
);
181 /* Return the DC handle. */
195 CONST DEVMODEW
*lpInitData
)
197 return IntCreateDICW(lpwszDriver
,
200 (PDEVMODEW
)lpInitData
,
214 CONST DEVMODEW
*lpdvmInit
)
216 return IntCreateDICW(lpszDriver
,
219 (PDEVMODEW
)lpdvmInit
,
233 CONST DEVMODEA
*lpdvmInit
)
236 LPWSTR lpszDriverW
, lpszDeviceW
, lpszOutputW
;
237 LPDEVMODEW dvmInitW
= NULL
;
240 Status
= HEAP_strdupA2W(&lpszDriverW
, lpszDriver
);
241 if (!NT_SUCCESS(Status
))
242 SetLastError(RtlNtStatusToDosError(Status
));
245 Status
= HEAP_strdupA2W(&lpszDeviceW
, lpszDevice
);
246 if (!NT_SUCCESS(Status
))
247 SetLastError(RtlNtStatusToDosError(Status
));
250 Status
= HEAP_strdupA2W(&lpszOutputW
, lpszOutput
);
251 if (!NT_SUCCESS(Status
))
252 SetLastError(RtlNtStatusToDosError(Status
));
256 dvmInitW
= GdiConvertToDevmodeW((LPDEVMODEA
)lpdvmInit
);
258 hdc
= IntCreateDICW(lpszDriverW
,
261 lpdvmInit
? dvmInitW
: NULL
,
264 HEAP_free(lpszOutputW
);
266 HEAP_free(lpszDeviceW
);
268 HEAP_free(lpszDriverW
);
284 HANDLE hPrinter
= NULL
;
285 ULONG hType
= GDI_HANDLE_GET_TYPE(hdc
);
287 pLDC
= GdiGetLDC(hdc
);
289 if (hType
!= GDILoObjType_LO_DC_TYPE
)
291 return METADC_DeleteDC(hdc
);
294 bResult
= NtGdiDeleteObjectApp(hdc
);
298 DPRINT1("Delete the Local DC structure\n");
303 fpClosePrinter(hPrinter
);
316 HANDLE_METADC0P(INT
, SaveDC
, 0, hdc
);
317 return NtGdiSaveDC(hdc
);
326 RestoreDC(IN HDC hdc
,
329 HANDLE_METADC(BOOL
, RestoreDC
, FALSE
, hdc
, iLevel
);
330 return NtGdiRestoreDC(hdc
, iLevel
);
343 if (GDI_HANDLE_GET_TYPE(hDC
) != GDI_OBJECT_TYPE_DC
&&
344 GDI_HANDLE_GET_TYPE(hDC
) != GDI_OBJECT_TYPE_METADC
)
346 PLDC pLDC
= GdiGetLDC(hDC
);
349 SetLastError(ERROR_INVALID_HANDLE
);
352 /* If a document has started set it to die. */
353 if (pLDC
->Flags
& LDC_INIT_DOCUMENT
) pLDC
->Flags
|= LDC_KILL_DOCUMENT
;
355 return NtGdiCancelDC(hDC
);
358 if (GdiGetHandleUserData((HGDIOBJ
) hDC
, GDI_OBJECT_TYPE_DC
, (PVOID
) &pDc_Attr
))
360 pDc_Attr
->ulDirty_
&= ~DC_PLAYMETAFILE
;
372 return GetDCDWord( hdc
, GdiGetArcDirection
, 0);
382 return GetAndSetDCDWord(hdc
, GdiGetSetArcDirection
, nDirection
, 0, 0, 0);
390 GdiReleaseDC(HDC hdc
)
401 GdiCleanCacheDC(HDC hdc
)
403 if (GDI_HANDLE_GET_TYPE(hdc
) == GDILoObjType_LO_DC_TYPE
)
405 SetLastError(ERROR_INVALID_HANDLE
);
414 GdiConvertAndCheckDC(HDC hdc
)
417 ULONG hType
= GDI_HANDLE_GET_TYPE(hdc
);
418 if (hType
== GDILoObjType_LO_DC_TYPE
|| hType
== GDILoObjType_LO_METADC16_TYPE
)
420 pldc
= GdiGetLDC(hdc
);
423 if (pldc
->Flags
& LDC_SAPCALLBACK
) GdiSAPCallback(pldc
);
424 if (pldc
->Flags
& LDC_KILL_DOCUMENT
) return NULL
;
425 if (pldc
->Flags
& LDC_STARTPAGE
) StartPage(hdc
);
428 SetLastError(ERROR_INVALID_HANDLE
);
441 _In_ UINT uObjectType
)
443 PDC_ATTR pdcattr
= NULL
;
445 /* Check if this is a user mode object */
446 if ((uObjectType
== OBJ_PEN
) ||
447 (uObjectType
== OBJ_EXTPEN
) ||
448 (uObjectType
== OBJ_BRUSH
) ||
449 (uObjectType
== OBJ_COLORSPACE
))
451 /* Get the DC attribute */
452 pdcattr
= GdiGetDcAttr(hdc
);
459 /* Check what object was requested */
464 return pdcattr
->hpen
;
467 return pdcattr
->hbrush
;
470 return pdcattr
->hColorSpace
;
473 uObjectType
= GDI_OBJECT_TYPE_PALETTE
;
477 uObjectType
= GDI_OBJECT_TYPE_FONT
;
481 uObjectType
= GDI_OBJECT_TYPE_BITMAP
;
484 /* All others are invalid */
486 SetLastError(ERROR_INVALID_PARAMETER
);
490 /* Pass the request to win32k */
491 return NtGdiGetDCObject(hdc
, uObjectType
);
502 GOBJENUMPROC lpObjectFunc
,
508 DWORD_PTR EndOfBuffer
;
514 Size
= sizeof(LOGBRUSH
);
518 Size
= sizeof(LOGPEN
);
522 SetLastError(ERROR_INVALID_PARAMETER
);
526 ObjectsCount
= NtGdiEnumObjects(hdc
, nObjectType
, 0, NULL
);
527 if (!ObjectsCount
) return 0;
529 Buffer
= HeapAlloc(GetProcessHeap(), 0, ObjectsCount
* Size
);
532 SetLastError(ERROR_NOT_ENOUGH_MEMORY
);
536 if (!NtGdiEnumObjects(hdc
, nObjectType
, ObjectsCount
* Size
, Buffer
))
538 HeapFree(GetProcessHeap(), 0, Buffer
);
542 EndOfBuffer
= (DWORD_PTR
)Buffer
+ (ObjectsCount
* Size
);
543 while ((DWORD_PTR
)Buffer
< EndOfBuffer
)
545 Result
= lpObjectFunc(Buffer
, lParam
);
547 Buffer
= (PVOID
)((DWORD_PTR
)Buffer
+ Size
);
550 HeapFree(GetProcessHeap(), 0, Buffer
);
566 PDEVCAPS pDevCaps
= GdiDevCaps
; // Primary display device capabilities.
567 DPRINT("Device CAPS1\n");
569 HANDLE_METADC(INT
, GetDeviceCaps
, 0, hdc
, nIndex
);
571 /* Get the DC attribute */
572 pdcattr
= GdiGetDcAttr(hdc
);
575 SetLastError(ERROR_INVALID_PARAMETER
);
579 if (!(pdcattr
->ulDirty_
& DC_PRIMARY_DISPLAY
))
580 return NtGdiGetDeviceCaps(hdc
, nIndex
);
585 return pDevCaps
->ulVersion
;
588 return pDevCaps
->ulTechnology
;
591 return pDevCaps
->ulHorzSize
;
594 return pDevCaps
->ulVertSize
;
597 return pDevCaps
->ulHorzRes
;
600 return pDevCaps
->ulVertRes
;
603 return pDevCaps
->ulLogPixelsX
;
606 return pDevCaps
->ulLogPixelsY
;
609 return pDevCaps
->ulBitsPixel
;
612 return pDevCaps
->ulPlanes
;
618 return pDevCaps
->ulNumPens
;
621 return pDevCaps
->ulNumFonts
;
624 return pDevCaps
->ulNumColors
;
627 return pDevCaps
->ulAspectX
;
630 return pDevCaps
->ulAspectY
;
633 return pDevCaps
->ulAspectXY
;
639 return pDevCaps
->ulSizePalette
;
645 return pDevCaps
->ulColorRes
;
648 return pDevCaps
->ulVertRes
;
651 return pDevCaps
->ulHorzRes
;
654 return pDevCaps
->ulBltAlignment
;
657 return pDevCaps
->ulShadeBlend
;
660 return pDevCaps
->ulColorMgmtCaps
;
663 return pDevCaps
->ulPhysicalWidth
;
666 return pDevCaps
->ulPhysicalHeight
;
668 case PHYSICALOFFSETX
:
669 return pDevCaps
->ulPhysicalOffsetX
;
671 case PHYSICALOFFSETY
:
672 return pDevCaps
->ulPhysicalOffsetY
;
675 return pDevCaps
->ulVRefresh
;
678 return pDevCaps
->ulRasterCaps
;
681 return (CC_CIRCLES
| CC_PIE
| CC_CHORD
| CC_ELLIPSES
| CC_WIDE
|
682 CC_STYLED
| CC_WIDESTYLED
| CC_INTERIORS
| CC_ROUNDRECT
);
685 return (LC_POLYLINE
| LC_MARKER
| LC_POLYMARKER
| LC_WIDE
|
686 LC_STYLED
| LC_WIDESTYLED
| LC_INTERIORS
);
689 return (PC_POLYGON
| PC_RECTANGLE
| PC_WINDPOLYGON
| PC_SCANLINE
|
690 PC_WIDE
| PC_STYLED
| PC_WIDESTYLED
| PC_INTERIORS
);
693 return pDevCaps
->ulTextCaps
;
713 return GetDCDWord(hdc
, GdiGetRelAbs
, 0);
726 return GetAndSetDCDWord(hdc
, GdiGetSetRelAbs
, Mode
, 0, 0, 0);
740 _In_ USHORT usMF16Id
,
745 /* This is a special API, handle it appropriately */
746 HANDLE_METADC2(DWORD
, GetAndSetDCDWord
, hdc
, u
, dwIn
, ulMFId
, usMF16Id
, dwError
);
748 /* Call win32k to do the real work */
749 if (!NtGdiGetAndSetDCDword(hdc
, u
, dwIn
, &dwResult
))
770 if (!NtGdiGetDCDword(hdc
, u
, &dwResult
))
784 GetAspectRatioFilterEx(
786 LPSIZE lpAspectRatio
)
788 return NtGdiGetDCPoint(hdc
, GdiGetAspectRatioFilter
, (PPOINTL
)lpAspectRatio
);
803 return NtGdiGetBoundsRect(hdc
,lprcBounds
,flags
& ~DCB_WINDOWMGR
);
812 SetBoundsRect(HDC hdc
,
816 /* FIXME add check for validate the flags */
817 return NtGdiSetBoundsRect(hdc
, (LPRECT
)prc
, flags
& ~DCB_WINDOWMGR
);
830 return NtGdiGetAppClipBox(hdc
, lprc
);
844 /* Get the DC attribute */
845 pdcattr
= GdiGetDcAttr(hdc
);
848 SetLastError(ERROR_INVALID_PARAMETER
);
852 return pdcattr
->ulBrushClr
;
865 /* Get the DC attribute */
866 pdcattr
= GdiGetDcAttr(hdc
);
869 SetLastError(ERROR_INVALID_PARAMETER
);
873 return pdcattr
->ulPenClr
;
883 _In_ COLORREF crColor
)
888 /* Get the DC attribute */
889 pdcattr
= GdiGetDcAttr(hdc
);
892 SetLastError(ERROR_INVALID_PARAMETER
);
896 /* We handle only enhanced meta DCs here */
897 HANDLE_METADC(COLORREF
, SetDCBrushColor
, CLR_INVALID
, hdc
, crColor
);
899 /* Get old color and store the new */
900 crOldColor
= pdcattr
->ulBrushClr
;
901 pdcattr
->ulBrushClr
= crColor
;
903 if (pdcattr
->crBrushClr
!= crColor
)
905 pdcattr
->ulDirty_
|= DIRTY_FILL
;
906 pdcattr
->crBrushClr
= crColor
;
919 _In_ COLORREF crColor
)
924 /* Get the DC attribute */
925 pdcattr
= GdiGetDcAttr(hdc
);
928 SetLastError(ERROR_INVALID_PARAMETER
);
932 /* We handle only enhanced meta DCs here */
933 HANDLE_METADC(COLORREF
, SetDCPenColor
, CLR_INVALID
, hdc
, crColor
);
935 /* Get old color and store the new */
936 crOldColor
= pdcattr
->ulPenClr
;
937 pdcattr
->ulPenClr
= (ULONG
)crColor
;
939 if (pdcattr
->crPenClr
!= crColor
)
941 pdcattr
->ulDirty_
|= DIRTY_LINE
;
942 pdcattr
->crPenClr
= crColor
;
959 /* Get the DC attribute */
960 pdcattr
= GdiGetDcAttr(hdc
);
963 /* Don't set LastError here! */
967 return pdcattr
->ulBackgroundClr
;
977 _In_ COLORREF crColor
)
982 HANDLE_METADC(COLORREF
, SetBkColor
, CLR_INVALID
, hdc
, crColor
);
984 /* Get the DC attribute */
985 pdcattr
= GdiGetDcAttr(hdc
);
988 SetLastError(ERROR_INVALID_PARAMETER
);
992 /* Get old color and store the new */
993 crOldColor
= pdcattr
->ulBackgroundClr
;
994 pdcattr
->ulBackgroundClr
= crColor
;
996 if (pdcattr
->crBackgroundClr
!= crColor
)
998 pdcattr
->ulDirty_
|= (DIRTY_BACKGROUND
|DIRTY_LINE
|DIRTY_FILL
);
999 pdcattr
->crBackgroundClr
= crColor
;
1015 /* Get the DC attribute */
1016 pdcattr
= GdiGetDcAttr(hdc
);
1017 if (pdcattr
== NULL
)
1019 /* Don't set LastError here! */
1023 return pdcattr
->lBkMode
;
1039 HANDLE_METADC(INT
, SetBkMode
, 0, hdc
, iBkMode
);
1041 /* Get the DC attribute */
1042 pdcattr
= GdiGetDcAttr(hdc
);
1043 if (pdcattr
== NULL
)
1045 SetLastError(ERROR_INVALID_PARAMETER
);
1049 iOldMode
= pdcattr
->lBkMode
;
1050 pdcattr
->jBkMode
= iBkMode
; // Processed
1051 pdcattr
->lBkMode
= iBkMode
; // Raw
1067 /* Get the DC attribute */
1068 pdcattr
= GdiGetDcAttr(hdc
);
1069 if (pdcattr
== NULL
)
1071 /* Do not set LastError here! */
1075 return pdcattr
->jROP2
;
1090 HANDLE_METADC(INT
, SetROP2
, 0, hdc
, rop2
);
1092 /* Get the DC attribute */
1093 pdcattr
= GdiGetDcAttr(hdc
);
1094 if (pdcattr
== NULL
)
1096 SetLastError(ERROR_INVALID_PARAMETER
);
1100 if (NtCurrentTeb()->GdiTebBatch
.HDC
== hdc
)
1102 if (pdcattr
->ulDirty_
& DC_MODE_DIRTY
)
1105 pdcattr
->ulDirty_
&= ~DC_MODE_DIRTY
;
1109 rop2Old
= pdcattr
->jROP2
;
1110 pdcattr
->jROP2
= (BYTE
)rop2
;
1122 GetPolyFillMode(HDC hdc
)
1126 /* Get DC attribute */
1127 pdcattr
= GdiGetDcAttr(hdc
);
1128 if (pdcattr
== NULL
)
1130 /* Don't set LastError here! */
1134 /* Return current fill mode */
1135 return pdcattr
->lFillMode
;
1145 _In_
int iPolyFillMode
)
1147 INT iOldPolyFillMode
;
1150 HANDLE_METADC(INT
, SetPolyFillMode
, 0, hdc
, iPolyFillMode
);
1152 /* Get the DC attribute */
1153 pdcattr
= GdiGetDcAttr(hdc
);
1154 if (pdcattr
== NULL
)
1156 SetLastError(ERROR_INVALID_PARAMETER
);
1160 if (NtCurrentTeb()->GdiTebBatch
.HDC
== hdc
)
1162 if (pdcattr
->ulDirty_
& DC_MODE_DIRTY
)
1164 NtGdiFlush(); // Sync up pdcattr from Kernel space.
1165 pdcattr
->ulDirty_
&= ~DC_MODE_DIRTY
;
1169 iOldPolyFillMode
= pdcattr
->lFillMode
;
1170 pdcattr
->lFillMode
= iPolyFillMode
;
1172 return iOldPolyFillMode
;
1181 GetGraphicsMode(HDC hdc
)
1185 /* Get the DC attribute */
1186 pdcattr
= GdiGetDcAttr(hdc
);
1187 if (pdcattr
== NULL
)
1189 /* Don't set LastError here! */
1193 /* Return current graphics mode */
1194 return pdcattr
->iGraphicsMode
;
1209 /* Check parameters */
1210 if ((iMode
< GM_COMPATIBLE
) || (iMode
> GM_ADVANCED
))
1212 SetLastError(ERROR_INVALID_PARAMETER
);
1216 /* Get the DC attribute */
1217 pdcattr
= GdiGetDcAttr(hdc
);
1218 if (pdcattr
== NULL
)
1220 SetLastError(ERROR_INVALID_PARAMETER
);
1224 /* Check for trivial case */
1225 if (iMode
== pdcattr
->iGraphicsMode
)
1228 if (NtCurrentTeb()->GdiTebBatch
.HDC
== hdc
)
1230 if (pdcattr
->ulDirty_
& DC_MODE_DIRTY
)
1232 NtGdiFlush(); // Sync up pdcattr from Kernel space.
1233 pdcattr
->ulDirty_
&= ~DC_MODE_DIRTY
;
1237 /* One would think that setting the graphics mode to GM_COMPATIBLE
1238 * would also reset the world transformation matrix to the unity
1239 * matrix. However, in Windows, this is not the case. This doesn't
1240 * make a lot of sense to me, but that's the way it is.
1242 iOldMode
= pdcattr
->iGraphicsMode
;
1243 pdcattr
->iGraphicsMode
= iMode
;
1255 _In_ CONST DEVMODEW
*lpInitData
)
1257 NtGdiResetDC ( hdc
, (PDEVMODEW
)lpInitData
, NULL
, NULL
, NULL
);
1269 _In_ CONST DEVMODEA
*lpInitData
)
1271 LPDEVMODEW InitDataW
;
1273 InitDataW
= GdiConvertToDevmodeW((LPDEVMODEA
)lpInitData
);
1275 NtGdiResetDC ( hdc
, InitDataW
, NULL
, NULL
, NULL
);
1276 HEAP_free(InitDataW
);
1281 /* FIXME: include correct header */
1282 HPALETTE WINAPI
NtUserSelectPalette(HDC hDC
,
1284 BOOL ForceBackground
);
1291 BOOL bForceBackground
)
1293 HANDLE_METADC(HPALETTE
, SelectPalette
, NULL
, hdc
, hpal
, bForceBackground
);
1295 return NtUserSelectPalette(hdc
, hpal
, bForceBackground
);
1304 GetStretchBltMode(HDC hdc
)
1308 /* Get the DC attribute */
1309 pdcattr
= GdiGetDcAttr(hdc
);
1310 if (pdcattr
== NULL
)
1312 /* Don't set LastError here! */
1316 return pdcattr
->lStretchBltMode
;
1326 _In_
int iStretchMode
)
1331 HANDLE_METADC(INT
, SetStretchBltMode
, 0, hdc
, iStretchMode
);
1333 /* Get the DC attribute */
1334 pdcattr
= GdiGetDcAttr(hdc
);
1335 if (pdcattr
== NULL
)
1337 SetLastError(ERROR_INVALID_PARAMETER
);
1341 iOldMode
= pdcattr
->lStretchBltMode
;
1342 pdcattr
->lStretchBltMode
= iStretchMode
;
1344 // Wine returns an error here. We set the default.
1345 if ((iStretchMode
<= 0) || (iStretchMode
> MAXSTRETCHBLTMODE
)) iStretchMode
= WHITEONBLACK
;
1347 pdcattr
->jStretchBltMode
= iStretchMode
;
1361 /* Get the DC attribute */
1362 pdcattr
= GdiGetDcAttr(hdc
);
1363 if (pdcattr
== NULL
)
1365 /* Don't set LastError here! */
1369 /* Return the current font */
1370 return pdcattr
->hlfntNew
;
1381 return NtGdiSelectBitmap(hdc
, hbmp
);
1393 HANDLE_METADC(HBRUSH
, SelectBrush
, NULL
, hdc
, hbr
);
1395 /* Get the DC attribute */
1396 pdcattr
= GdiGetDcAttr(hdc
);
1397 if (pdcattr
== NULL
)
1399 SetLastError(ERROR_INVALID_PARAMETER
);
1403 /* Get the current brush. If it matches the new brush, we're done */
1404 hbrOld
= pdcattr
->hbrush
;
1408 /* Set the new brush and update dirty flags */
1409 pdcattr
->hbrush
= hbr
;
1410 pdcattr
->ulDirty_
|= DC_BRUSH_DIRTY
;
1423 HANDLE_METADC(HPEN
, SelectPen
, NULL
, hdc
, hpen
);
1425 /* Get the DC attribute */
1426 pdcattr
= GdiGetDcAttr(hdc
);
1427 if (pdcattr
== NULL
)
1429 SetLastError(ERROR_INVALID_HANDLE
);
1433 /* Get the current pen. If it matches the new pen, we're done */
1434 hpenOld
= pdcattr
->hpen
;
1435 if (hpenOld
== hpen
)
1438 /* Set the new pen and update dirty flags */
1439 pdcattr
->ulDirty_
|= DC_PEN_DIRTY
;
1440 pdcattr
->hpen
= hpen
;
1453 HANDLE_METADC(HFONT
, SelectFont
, NULL
, hdc
, hfont
);
1455 /* Get the DC attribute */
1456 pdcattr
= GdiGetDcAttr(hdc
);
1457 if (pdcattr
== NULL
)
1459 SetLastError(ERROR_INVALID_PARAMETER
);
1463 /* Get the current font. If it matches the new font, we're done */
1464 hfontOld
= pdcattr
->hlfntNew
;
1465 if (hfontOld
== hfont
)
1468 /* Set the new font and update dirty flags */
1469 pdcattr
->hlfntNew
= hfont
;
1470 pdcattr
->ulDirty_
&= ~SLOW_WIDTHS
;
1471 pdcattr
->ulDirty_
|= DIRTY_CHARSET
;
1473 /* If the DC does not have a DIB section selected, try a batch command */
1474 if (!(pdcattr
->ulDirty_
& DC_DIBSECTION
))
1478 pgO
= GdiAllocBatchCommand(hdc
, GdiBCSelObj
);
1481 pgO
->hgdiobj
= hfont
;
1486 /* We could not use the batch command, call win32k */
1487 return NtGdiSelectFont(hdc
, hfont
);
1501 /* Fix up 16 bit handles */
1502 hobj
= GdiFixUpHandle(hobj
);
1503 if (!GdiValidateHandle(hobj
))
1508 /* Call the appropriate select function */
1509 switch (GDI_HANDLE_GET_TYPE(hobj
))
1511 case GDILoObjType_LO_REGION_TYPE
:
1512 return (HGDIOBJ
)UlongToHandle(ExtSelectClipRgn(hdc
, hobj
, RGN_COPY
));
1514 case GDILoObjType_LO_BITMAP_TYPE
:
1515 case GDILoObjType_LO_DIBSECTION_TYPE
:
1516 return GdiSelectBitmap(hdc
, hobj
);
1518 case GDILoObjType_LO_BRUSH_TYPE
:
1519 return GdiSelectBrush(hdc
, hobj
);
1521 case GDILoObjType_LO_PEN_TYPE
:
1522 case GDILoObjType_LO_EXTPEN_TYPE
:
1523 return GdiSelectPen(hdc
, hobj
);
1525 case GDILoObjType_LO_FONT_TYPE
:
1526 return GdiSelectFont(hdc
, hobj
);
1528 case GDILoObjType_LO_ICMLCS_TYPE
:
1529 return SetColorSpace(hdc
, hobj
);
1531 case GDILoObjType_LO_PALETTE_TYPE
:
1532 SetLastError(ERROR_INVALID_FUNCTION
);
1541 /***********************************************************************
1542 * D3DKMTCreateDCFromMemory (GDI32.@)
1544 DWORD WINAPI
D3DKMTCreateDCFromMemory( D3DKMT_CREATEDCFROMMEMORY
*desc
)
1546 return NtGdiDdDDICreateDCFromMemory( desc
);
1549 DWORD WINAPI
D3DKMTDestroyDCFromMemory( const D3DKMT_DESTROYDCFROMMEMORY
*desc
)
1551 return NtGdiDdDDIDestroyDCFromMemory( desc
);