📄 color.c
字号:
}
if (!(dc = DC_LockDc(hDC)))
{
SetLastWin32Error(ERROR_INVALID_HANDLE);
_SEH_LEAVE;
}
palGDI = PALETTE_LockPalette(dc->w.hPalette);
if (palGDI != NULL)
{
if (pe != NULL)
{
UINT CopyEntries;
if (StartIndex + Entries < palGDI->NumColors)
CopyEntries = StartIndex + Entries;
else
CopyEntries = palGDI->NumColors - StartIndex;
memcpy(pe,
palGDI->IndexedColors + StartIndex,
CopyEntries * sizeof(pe[0]));
Ret = CopyEntries;
}
else
{
Ret = dc->GDIInfo->ulNumPalReg;
}
}
}
_SEH_HANDLE
{
SetLastNtError(_SEH_GetExceptionCode());
}
_SEH_END;
if (palGDI != NULL)
PALETTE_UnlockPalette(palGDI);
if (dc != NULL)
DC_UnlockDc(dc);
return Ret;
}
UINT STDCALL NtGdiGetSystemPaletteUse(HDC hDC)
{
return SystemPaletteUse;
}
/*!
The RealizePalette function modifies the palette for the device associated with the specified device context. If the device context is a memory DC, the color table for the bitmap selected into the DC is modified. If the device context is a display DC, the physical palette for that device is modified.
A logical palette is a buffer between color-intensive applications and the system, allowing these applications to use as many colors as needed without interfering with colors displayed by other windows.
1= IF DRAWING TO A DEVICE
-- If it is a paletted bitmap, and is not an identity palette, then an XLATEOBJ is created between the logical palette and
the system palette.
-- If it is an RGB palette, then an XLATEOBJ is created between the RGB values and the system palette.
2= IF DRAWING TO A MEMORY DC\BITMAP
-- If it is a paletted bitmap, and is not an identity palette, then an XLATEOBJ is created between the logical palette and
the dc palette.
-- If it is an RGB palette, then an XLATEOBJ is created between the RGB values and the dc palette.
*/
UINT STDCALL NtGdiRealizePalette(HDC hDC)
{
/*
* This function doesn't do any real work now and there's plenty
* of bugd in it (calling SetPalette for high/true-color modes,
* using DEFAULT_PALETTE instead of the device palette, ...).
*/
PALOBJ *palPtr, *sysPtr;
PPALGDI palGDI, sysGDI;
int realized = 0;
PDC dc;
HPALETTE systemPalette;
BOOLEAN success;
USHORT sysMode, palMode;
dc = DC_LockDc(hDC);
if (!dc)
return 0;
systemPalette = NtGdiGetStockObject((INT)DEFAULT_PALETTE);
palGDI = PALETTE_LockPalette(dc->w.hPalette);
palPtr = (PALOBJ*) palGDI;
if (palGDI == NULL)
{
/* FIXME - Handle palGDI == NULL!!!!
we should not unlock dc and return 0 ??
shall we create the pallete ??
*/
DC_UnlockDc(dc);
return 0;
}
sysGDI = PALETTE_LockPalette(systemPalette);
sysPtr = (PALOBJ*) sysGDI;
if (sysGDI == NULL)
{
/* FIXME - Handle sysGDI == NULL!!!!!
we should not unlock dc and return 0 ??
shall we create the pallete ??
*/
PALETTE_UnlockPalette(palGDI);
DC_UnlockDc(dc);
return 0;
}
// Step 1: Create mapping of system palette\DC palette
#ifndef NO_MAPPING
realized = PALETTE_SetMapping(palPtr, 0, palGDI->NumColors,
(dc->w.hPalette != hPrimaryPalette) ||
(dc->w.hPalette == NtGdiGetStockObject(DEFAULT_PALETTE)));
#else
realized = 0;
#endif
// Step 2:
// The RealizePalette function modifies the palette for the device associated with the specified device context. If the
// device context is a memory DC, the color table for the bitmap selected into the DC is modified. If the device
// context is a display DC, the physical palette for that device is modified.
if(dc->w.flags == DC_MEMORY)
{
// Memory managed DC
ASSERT(sysGDI->NumColors <= 256);
success = ((GDIDEVICE *)dc->GDIDevice)->DriverFunctions.SetPalette(
dc->PDev, sysPtr, 0, 0, sysGDI->NumColors);
} else {
if( ((GDIDEVICE *)dc->GDIDevice)->DriverFunctions.SetPalette)
{
ASSERT(palGDI->NumColors <= 256);
success = ((GDIDEVICE *)dc->GDIDevice)->DriverFunctions.SetPalette(
dc->PDev, palPtr, 0, 0, palGDI->NumColors);
}
}
// need to pass this to IntEngCreateXlate with palettes unlocked
sysMode = sysGDI->Mode;
palMode = palGDI->Mode;
PALETTE_UnlockPalette(sysGDI);
PALETTE_UnlockPalette(palGDI);
// Step 3: Create the XLATEOBJ for device managed DCs
if(dc->w.flags != DC_MEMORY)
{
// Device managed DC
palGDI->logicalToSystem = IntEngCreateXlate(sysMode, palMode, systemPalette, dc->w.hPalette);
}
DC_UnlockDc(dc);
return realized;
}
BOOL STDCALL NtGdiResizePalette(HPALETTE hpal,
UINT Entries)
{
/* PALOBJ *palPtr = (PALOBJ*)AccessUserObject(hPal);
UINT cPrevEnt, prevVer;
INT prevsize, size = sizeof(LOGPALETTE) + (cEntries - 1) * sizeof(PALETTEENTRY);
XLATEOBJ *XlateObj = NULL;
if(!palPtr) return FALSE;
cPrevEnt = palPtr->logpalette->palNumEntries;
prevVer = palPtr->logpalette->palVersion;
prevsize = sizeof(LOGPALETTE) + (cPrevEnt - 1) * sizeof(PALETTEENTRY) + sizeof(int*) + sizeof(GDIOBJHDR);
size += sizeof(int*) + sizeof(GDIOBJHDR);
XlateObj = palPtr->logicalToSystem;
if (!(palPtr = GDI_ReallocObject(size, hPal, palPtr))) return FALSE;
if(XlateObj)
{
XLATEOBJ *NewXlateObj = (int*) HeapReAlloc(GetProcessHeap(), 0, XlateObj, cEntries * sizeof(int));
if(NewXlateObj == NULL)
{
ERR("Can not resize logicalToSystem -- out of memory!");
GDI_ReleaseObj( hPal );
return FALSE;
}
palPtr->logicalToSystem = NewXlateObj;
}
if(cEntries > cPrevEnt)
{
if(XlateObj) memset(palPtr->logicalToSystem + cPrevEnt, 0, (cEntries - cPrevEnt)*sizeof(int));
memset( (BYTE*)palPtr + prevsize, 0, size - prevsize );
PALETTE_ValidateFlags((PALETTEENTRY*)((BYTE*)palPtr + prevsize), cEntries - cPrevEnt );
}
palPtr->logpalette->palNumEntries = cEntries;
palPtr->logpalette->palVersion = prevVer;
// GDI_ReleaseObj( hPal );
return TRUE; */
UNIMPLEMENTED;
return FALSE;
}
BOOL STDCALL NtGdiSetColorAdjustment(HDC hDC,
CONST LPCOLORADJUSTMENT ca)
{
UNIMPLEMENTED;
return FALSE;
}
UINT STDCALL NtGdiSetPaletteEntries(HPALETTE hpal,
UINT Start,
UINT Entries,
CONST LPPALETTEENTRY pe)
{
PPALGDI palGDI;
WORD numEntries;
palGDI = PALETTE_LockPalette(hpal);
if (!palGDI) return 0;
numEntries = palGDI->NumColors;
if (Start >= numEntries)
{
PALETTE_UnlockPalette(palGDI);
return 0;
}
if (numEntries < Start + Entries)
{
Entries = numEntries - Start;
}
memcpy(palGDI->IndexedColors + Start, pe, Entries * sizeof(PALETTEENTRY));
PALETTE_ValidateFlags(palGDI->IndexedColors, palGDI->NumColors);
ExFreePool(palGDI->logicalToSystem);
palGDI->logicalToSystem = NULL;
PALETTE_UnlockPalette(palGDI);
return Entries;
}
UINT STDCALL
NtGdiSetSystemPaletteUse(HDC hDC, UINT Usage)
{
UINT old = SystemPaletteUse;
/* Device doesn't support colour palettes */
if (!(NtGdiGetDeviceCaps(hDC, RASTERCAPS) & RC_PALETTE)) {
return SYSPAL_ERROR;
}
switch (Usage)
{
case SYSPAL_NOSTATIC:
case SYSPAL_NOSTATIC256:
case SYSPAL_STATIC:
SystemPaletteUse = Usage;
break;
default:
old=SYSPAL_ERROR;
break;
}
return old;
}
/*
Win 2k Graphics API, Black Book. by coriolis.com
Page 62, Note that Steps 3, 5, and 6 are not required for Windows NT(tm)
and Windows 2000(tm).
Step 5. UnrealizeObject(hTrackBrush);
*/
BOOL STDCALL
NtGdiUnrealizeObject(HGDIOBJ hgdiobj)
{
GDIOBJHDR * ptr;
DWORD objectType;
BOOL Ret = FALSE;
/* From Wine: UnrealizeObject does not SetLastError() on a null object */
if(!hgdiobj)
return Ret;
ptr = GDIOBJ_LockObj(GdiHandleTable, hgdiobj, GDI_OBJECT_TYPE_DONTCARE);
if (ptr == 0)
{
SetLastWin32Error(ERROR_INVALID_HANDLE);
return Ret;
}
objectType = GDIOBJ_GetObjectType(hgdiobj);
switch(objectType)
{
/*
msdn.microsoft.com,
"Windows 2000/XP: If hgdiobj is a brush, UnrealizeObject does nothing,
and the function returns TRUE. Use SetBrushOrgEx to set the origin of
a brush."
*/
case GDI_OBJECT_TYPE_BRUSH:
{
DPRINT("GDI_OBJECT_TYPE_BRUSH\n");
Ret = TRUE;
break;
}
default:
DPRINT1("Magic 0x%08x not implemented\n", objectType);
break;
}
GDIOBJ_UnlockObjByPtr(GdiHandleTable, ptr);
return Ret;
}
BOOL STDCALL
NtGdiUpdateColors(HDC hDC)
{
PWINDOW_OBJECT Wnd;
BOOL calledFromUser, ret;
USER_REFERENCE_ENTRY Ref;
calledFromUser = UserIsEntered();
if (!calledFromUser){
UserEnterExclusive();
}
Wnd = UserGetWindowObject(IntWindowFromDC(hDC));
if (Wnd == NULL)
{
SetLastWin32Error(ERROR_INVALID_WINDOW_HANDLE);
if (!calledFromUser){
UserLeave();
}
return FALSE;
}
UserRefObjectCo(Wnd, &Ref);
ret = co_UserRedrawWindow(Wnd, NULL, 0, RDW_INVALIDATE);
UserDerefObjectCo(Wnd);
if (!calledFromUser){
UserLeave();
}
return ret;
}
INT STDCALL COLOR_PaletteLookupPixel(PALETTEENTRY *palPalEntry, INT size,
XLATEOBJ *XlateObj, COLORREF col, BOOL skipReserved)
{
int i, best = 0, diff = 0x7fffffff;
int r, g, b;
for( i = 0; i < size && diff ; i++ )
{
#if 0
if(!(palPalEntry[i].peFlags & PC_SYS_USED) || (skipReserved && palPalEntry[i].peFlags & PC_SYS_RESERVED))
continue;
#endif
r = abs((SHORT)palPalEntry[i].peRed - GetRValue(col));
g = abs((SHORT)palPalEntry[i].peGreen - GetGValue(col));
b = abs((SHORT)palPalEntry[i].peBlue - GetBValue(col));
r = r*r + g*g + b*b;
if( r < diff ) { best = i; diff = r; }
}
if (XlateObj == NULL)
return best;
else
return (XlateObj->pulXlate) ? (INT)XlateObj->pulXlate[best] : best;
}
COLORREF STDCALL COLOR_LookupNearestColor( PALETTEENTRY* palPalEntry, int size, COLORREF color )
{
INT index;
index = COLOR_PaletteLookupPixel(palPalEntry, size, NULL, color, FALSE);
return RGB(
palPalEntry[index].peRed,
palPalEntry[index].peGreen,
palPalEntry[index].peBlue);
}
int STDCALL COLOR_PaletteLookupExactIndex( PALETTEENTRY* palPalEntry, int size,
COLORREF col )
{
int i;
BYTE r = GetRValue(col), g = GetGValue(col), b = GetBValue(col);
for( i = 0; i < size; i++ )
{
if( palPalEntry[i].peFlags & PC_SYS_USED ) /* skips gap */
if(palPalEntry[i].peRed == r && palPalEntry[i].peGreen == g && palPalEntry[i].peBlue == b) return i;
}
return -1;
}
/* EOF */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -