📄 dc.c
字号:
ret = dc->GDIInfo->ulVersion;
break;
case TECHNOLOGY:
ret = dc->GDIInfo->ulTechnology;
break;
case HORZSIZE:
ret = dc->GDIInfo->ulHorzSize;
break;
case VERTSIZE:
ret = dc->GDIInfo->ulVertSize;
break;
case HORZRES:
ret = dc->GDIInfo->ulHorzRes;
break;
case VERTRES:
ret = dc->GDIInfo->ulVertRes;
break;
case LOGPIXELSX:
ret = dc->GDIInfo->ulLogPixelsX;
break;
case LOGPIXELSY:
ret = dc->GDIInfo->ulLogPixelsY;
break;
case BITSPIXEL:
ret = dc->GDIInfo->cBitsPixel;
break;
case PLANES:
ret = dc->GDIInfo->cPlanes;
break;
case NUMBRUSHES:
UNIMPLEMENTED; /* FIXME */
break;
case NUMPENS:
UNIMPLEMENTED; /* FIXME */
break;
case NUMFONTS:
UNIMPLEMENTED; /* FIXME */
break;
case NUMCOLORS:
ret = dc->GDIInfo->ulNumColors;
break;
case ASPECTX:
ret = dc->GDIInfo->ulAspectX;
break;
case ASPECTY:
ret = dc->GDIInfo->ulAspectY;
break;
case ASPECTXY:
ret = dc->GDIInfo->ulAspectXY;
break;
case PDEVICESIZE:
UNIMPLEMENTED; /* FIXME */
break;
case CLIPCAPS:
UNIMPLEMENTED; /* FIXME */
break;
case SIZEPALETTE:
ret = dc->GDIInfo->ulNumPalReg; /* FIXME not sure */
break;
case NUMRESERVED:
ret = 0;
break;
case COLORRES:
UNIMPLEMENTED; /* FIXME */
break;
case PHYSICALWIDTH:
if(IntGdiEscape(dc, GETPHYSPAGESIZE, 0, NULL, (LPVOID)&pt) > 0)
{
ret = pt.x;
}
else
{
ret = 0;
}
break;
case PHYSICALHEIGHT:
if(IntGdiEscape(dc, GETPHYSPAGESIZE, 0, NULL, (LPVOID)&pt) > 0)
{
ret = pt.y;
}
else
{
ret = 0;
}
break;
case PHYSICALOFFSETX:
if(IntGdiEscape(dc, GETPRINTINGOFFSET, 0, NULL, (LPVOID)&pt) > 0)
{
ret = pt.x;
}
else
{
ret = 0;
}
break;
case PHYSICALOFFSETY:
if(IntGdiEscape(dc, GETPRINTINGOFFSET, 0, NULL, (LPVOID)&pt) > 0)
{
ret = pt.y;
}
else
{
ret = 0;
}
break;
case VREFRESH:
UNIMPLEMENTED; /* FIXME */
break;
case SCALINGFACTORX:
if(IntGdiEscape(dc, GETSCALINGFACTOR, 0, NULL, (LPVOID)&pt) > 0)
{
ret = pt.x;
}
else
{
ret = 0;
}
break;
case SCALINGFACTORY:
if(IntGdiEscape(dc, GETSCALINGFACTOR, 0, NULL, (LPVOID)&pt) > 0)
{
ret = pt.y;
}
else
{
ret = 0;
}
break;
case RASTERCAPS:
ret = dc->GDIInfo->flRaster;
break;
case CURVECAPS:
UNIMPLEMENTED; /* FIXME */
break;
case LINECAPS:
UNIMPLEMENTED; /* FIXME */
break;
case POLYGONALCAPS:
UNIMPLEMENTED; /* FIXME */
break;
case TEXTCAPS:
ret = dc->GDIInfo->flTextCaps;
break;
default:
ret = 0;
break;
}
return ret;
}
INT STDCALL
NtGdiGetDeviceCaps(HDC hDC,
INT Index)
{
PDC dc;
INT ret;
dc = DC_LockDc(hDC);
if (dc == NULL)
{
SetLastWin32Error(ERROR_INVALID_HANDLE);
return 0;
}
ret = IntGdiGetDeviceCaps(dc, Index);
DPRINT("(%04x,%d): returning %d\n", hDC, Index, ret);
DC_UnlockDc( dc );
return ret;
}
DC_GET_VAL( INT, NtGdiGetMapMode, Dc_Attr.iMapMode )
DC_GET_VAL( INT, NtGdiGetPolyFillMode, Dc_Attr.jFillMode )
INT
FASTCALL
IntGdiGetObject(IN HANDLE Handle,
IN INT cbCount,
IN LPVOID lpBuffer)
{
PVOID pGdiObject;
INT Result = 0;
DWORD dwObjectType;
pGdiObject = GDIOBJ_LockObj(GdiHandleTable, Handle, GDI_OBJECT_TYPE_DONTCARE);
if (!pGdiObject)
{
SetLastWin32Error(ERROR_INVALID_HANDLE);
return 0;
}
dwObjectType = GDIOBJ_GetObjectType(Handle);
switch (dwObjectType)
{
case GDI_OBJECT_TYPE_PEN:
case GDI_OBJECT_TYPE_EXTPEN:
Result = PEN_GetObject((PGDIBRUSHOBJ) pGdiObject, cbCount, (PLOGPEN) lpBuffer); // IntGdiCreatePenIndirect
break;
case GDI_OBJECT_TYPE_BRUSH:
Result = BRUSH_GetObject((PGDIBRUSHOBJ ) pGdiObject, cbCount, (LPLOGBRUSH)lpBuffer);
break;
case GDI_OBJECT_TYPE_BITMAP:
Result = BITMAP_GetObject((BITMAPOBJ *) pGdiObject, cbCount, lpBuffer);
break;
case GDI_OBJECT_TYPE_FONT:
Result = FontGetObject((PTEXTOBJ) pGdiObject, cbCount, lpBuffer);
#if 0
// Fix the LOGFONT structure for the stock fonts
if (FIRST_STOCK_HANDLE <= Handle && Handle <= LAST_STOCK_HANDLE)
{
FixStockFontSizeW(Handle, cbCount, lpBuffer);
}
#endif
break;
case GDI_OBJECT_TYPE_PALETTE:
Result = PALETTE_GetObject((PPALGDI) pGdiObject, cbCount, lpBuffer);
break;
default:
DPRINT1("GDI object type 0x%08x not implemented\n", dwObjectType);
break;
}
GDIOBJ_UnlockObjByPtr(GdiHandleTable, pGdiObject);
return Result;
}
INT
NTAPI
NtGdiExtGetObjectW(IN HANDLE hGdiObj,
IN INT cbCount,
OUT LPVOID lpBuffer)
{
INT iRetCount = 0;
INT cbCopyCount;
union
{
BITMAP bitmap;
DIBSECTION dibsection;
LOGPEN logpen;
LOGBRUSH logbrush;
LOGFONTW logfontw;
EXTLOGFONTW extlogfontw;
ENUMLOGFONTEXDVW enumlogfontexdvw;
} Object;
// Normalize to the largest supported object size
cbCount = min((UINT)cbCount, sizeof(Object));
// Now do the actual call
iRetCount = IntGdiGetObject(hGdiObj, cbCount, lpBuffer ? &Object : NULL);
cbCopyCount = min((UINT)cbCount, (UINT)iRetCount);
// Make sure we have a buffer and a copy size
if ((cbCopyCount) && (lpBuffer))
{
// Enter SEH for buffer transfer
_SEH_TRY
{
// Probe the buffer and copy it
ProbeForWrite(lpBuffer, cbCopyCount, sizeof(WORD));
RtlCopyMemory(lpBuffer, &Object, cbCopyCount);
}
_SEH_HANDLE
{
// Clear the return value.
// Do *NOT* set last error here!
iRetCount = 0;
}
_SEH_END;
}
// Return the count
return iRetCount;
}
DC_GET_VAL( INT, NtGdiGetROP2, Dc_Attr.jROP2 )
DC_GET_VAL( INT, NtGdiGetStretchBltMode, Dc_Attr.jStretchBltMode )
DC_GET_VAL( UINT, NtGdiGetTextAlign, Dc_Attr.lTextAlign )
DC_GET_VAL( COLORREF, NtGdiGetTextColor, Dc_Attr.crForegroundClr )
DC_GET_VAL_EX( GetViewportExtEx, Dc_Attr.szlViewportExt.cx, Dc_Attr.szlViewportExt.cy, SIZE, cx, cy )
DC_GET_VAL_EX( GetViewportOrgEx, Dc_Attr.ptlViewportOrg.x, Dc_Attr.ptlViewportOrg.y, POINT, x, y )
DC_GET_VAL_EX( GetWindowExtEx, Dc_Attr.szlWindowExt.cx, Dc_Attr.szlWindowExt.cy, SIZE, cx, cy )
DC_GET_VAL_EX( GetWindowOrgEx, Dc_Attr.ptlWindowOrg.x, Dc_Attr.ptlWindowOrg.y, POINT, x, y )
BOOL
APIENTRY
NtGdiResetDC(
IN HDC hdc,
IN LPDEVMODEW pdm,
OUT PBOOL pbBanding,
IN OPTIONAL VOID *pDriverInfo2,
OUT VOID *ppUMdhpdev)
{
UNIMPLEMENTED;
return 0;
}
BOOL STDCALL
NtGdiRestoreDC(HDC hDC, INT SaveLevel)
{
PDC dc, dcs;
BOOL success;
DPRINT("NtGdiRestoreDC(%lx, %d)\n", hDC, SaveLevel);
dc = DC_LockDc(hDC);
if (!dc)
{
SetLastWin32Error(ERROR_INVALID_HANDLE);
return FALSE;
}
if (SaveLevel < 0)
SaveLevel = dc->saveLevel + SaveLevel + 1;
if(SaveLevel < 0 || dc->saveLevel<SaveLevel)
{
DC_UnlockDc(dc);
return FALSE;
}
success=TRUE;
while (dc->saveLevel >= SaveLevel)
{
HDC hdcs = DC_GetNextDC (dc);
dcs = DC_LockDc (hdcs);
if (dcs == NULL)
{
DC_UnlockDc(dc);
return FALSE;
}
DC_SetNextDC (dc, DC_GetNextDC (dcs));
dcs->hNext = 0;
if (--dc->saveLevel < SaveLevel)
{
DC_UnlockDc( dc );
DC_UnlockDc( dcs );
IntGdiSetDCState(hDC, hdcs);
if (!PATH_AssignGdiPath( &dc->w.path, &dcs->w.path ))
{
/* FIXME: This might not be quite right, since we're
* returning FALSE but still destroying the saved DC state */
success = FALSE;
}
dc = DC_LockDc(hDC);
if(!dc)
{
return FALSE;
}
}
else
{
DC_UnlockDc( dcs );
}
NtGdiDeleteObjectApp (hdcs);
}
DC_UnlockDc( dc );
return success;
}
INT STDCALL
NtGdiSaveDC(HDC hDC)
{
HDC hdcs;
PDC dc, dcs;
INT ret;
DPRINT("NtGdiSaveDC(%lx)\n", hDC);
if (!(hdcs = IntGdiGetDCState(hDC)))
{
return 0;
}
dcs = DC_LockDc (hdcs);
if (dcs == NULL)
{
SetLastWin32Error(ERROR_INVALID_HANDLE);
return 0;
}
dc = DC_LockDc (hDC);
if (dc == NULL)
{
DC_UnlockDc(dcs);
SetLastWin32Error(ERROR_INVALID_HANDLE);
return 0;
}
#if 0
/* Copy path. The reason why path saving / restoring is in SaveDC/
* RestoreDC and not in GetDCState/SetDCState is that the ...DCState
* functions are only in Win16 (which doesn't have paths) and that
* SetDCState doesn't allow us to signal an error (which can happen
* when copying paths).
*/
if (!PATH_AssignGdiPath (&dcs->w.path, &dc->w.path))
{
NtGdiDeleteObjectApp (hdcs);
return 0;
}
#endif
DC_SetNextDC (dcs, DC_GetNextDC (dc));
DC_SetNextDC (dc, hdcs);
ret = ++dc->saveLevel;
DC_UnlockDc( dcs );
DC_UnlockDc( dc );
return ret;
}
HGDIOBJ
STDCALL
NtGdiSelectObject(HDC hDC, HGDIOBJ hGDIObj)
{
HGDIOBJ objOrg = NULL; // default to failure
BITMAPOBJ *pb;
PDC dc;
PGDIBRUSHOBJ pen;
PGDIBRUSHOBJ brush;
XLATEOBJ *XlateObj;
DWORD objectType;
HRGN hVisRgn;
BOOLEAN Failed;
if (!hDC || !hGDIObj)
{
/* From Wine:
* SelectObject() with a NULL DC returns 0 and sets ERROR_INVALID_HANDLE.
* Note: Under XP at least invalid ptrs can also be passed, not just NULL;
* Don't test that here in case it crashes earlier win versions.
*/
if (!hDC) SetLastWin32Error(ERROR_INVALID_HANDLE);
return NULL;
}
dc = DC_LockDc(hDC);
if (NULL == dc)
{
SetLastWin32Error(ERROR_INVALID_HANDLE);
return NULL;
}
objectType = GDIOBJ_GetObjectType(hGDIObj);
switch (objectType)
{
case GDI_OBJECT_TYPE_PEN:
pen = PENOBJ_LockPen((HPEN) hGDIObj);
if (pen == NULL)
{
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -