--- /dev/null
+static unsigned char notmask[2] = { 0x0f, 0xf0 };
+static unsigned char altnotmask[2] = { 0xf0, 0x0f };
+
+typedef VOID (*PFN_DIB_PutPixel)(SURFOBJ *, LONG, LONG, ULONG);
+typedef ULONG (*PFN_DIB_GetPixel)(SURFOBJ *, LONG, LONG);
+typedef VOID (*PFN_DIB_HLine) (SURFOBJ *, LONG, LONG, LONG, ULONG);
+typedef VOID (*PFN_DIB_VLine) (SURFOBJ *, LONG, LONG, LONG, ULONG);
+
+VOID DIB_4BPP_PutPixel(PSURFOBJ SurfObj, LONG x, LONG y, BYTE c);
+BYTE DIB_4BPP_GetPixel(PSURFOBJ SurfObj, LONG x, LONG y);
+VOID DIB_4BPP_HLine(PSURFOBJ SurfObj, LONG x1, LONG x2, LONG y, BYTE c);
+VOID DIB_4BPP_VLine(PSURFOBJ SurfObj, LONG x, LONG y1, LONG y2, BYTE c);
+
+VOID DIB_24BPP_PutPixel(PSURFOBJ SurfObj, LONG x, LONG y, RGBTRIPLE c);
+RGBTRIPLE DIB_24BPP_GetPixel(PSURFOBJ SurfObj, LONG x, LONG y);
+VOID DIB_24BPP_HLine(PSURFOBJ SurfObj, LONG x1, LONG x2, LONG y, RGBTRIPLE c);
+VOID DIB_24BPP_VLine(PSURFOBJ SurfObj, LONG x, LONG y1, LONG y2, RGBTRIPLE c);
--- /dev/null
+#undef WIN32_LEAN_AND_MEAN
+#include <windows.h>
+#include <stdlib.h>
+#include <win32k/bitmaps.h>
+#include <win32k/debug.h>
+#include <debug.h>
+#include <ddk/winddi.h>
+#include "..\eng\objects.h"
+#include "dib.h"
+
+VOID DIB_24BPP_PutPixel(PSURFOBJ SurfObj, LONG x, LONG y, RGBTRIPLE c)
+{
+ PBYTE byteaddr = SurfObj->pvBits + y * SurfObj->lDelta;
+ PRGBTRIPLE addr = (PRGBTRIPLE)byteaddr + x;
+
+ *addr = c;
+}
+
+RGBTRIPLE DIB_24BPP_GetPixel(PSURFOBJ SurfObj, LONG x, LONG y)
+{
+ PBYTE byteaddr = SurfObj->pvBits + y * SurfObj->lDelta;
+ PRGBTRIPLE addr = (PRGBTRIPLE)byteaddr + x;
+
+ return *addr;
+}
+
+VOID DIB_24BPP_HLine(PSURFOBJ SurfObj, LONG x1, LONG x2, LONG y, RGBTRIPLE c)
+{
+ PBYTE byteaddr = SurfObj->pvBits + y * SurfObj->lDelta;
+ PRGBTRIPLE addr = (PRGBTRIPLE)byteaddr + x1;
+ LONG cx = x1;
+
+ while(cx <= x2) {
+ *addr = c;
+ ++addr;
+ ++cx;
+ }
+}
+
+VOID DIB_24BPP_VLine(PSURFOBJ SurfObj, LONG x, LONG y1, LONG y2, RGBTRIPLE c)
+{
+ PBYTE byteaddr = SurfObj->pvBits + y1 * SurfObj->lDelta;
+ PRGBTRIPLE addr = (PRGBTRIPLE)byteaddr + x;
+ ULONG lDelta = SurfObj->lDelta;
+
+ byteaddr = (PBYTE)addr;
+ while(y1++ <= y2) {
+ *addr = c;
+
+ byteaddr += lDelta;
+ addr = (PRGBTRIPLE)byteaddr;
+ }
+}
+
+VOID DIB_24BPP_BltTo_24BPP(PSURFOBJ dstpsd, LONG dstx, LONG dsty, LONG w, LONG h,
+ PSURFOBJ srcpsd, LONG srcx, LONG srcy)
+{
+ PRGBTRIPLE dst;
+ PRGBTRIPLE src;
+ PBYTE bytedst;
+ PBYTE bytesrc;
+ int i;
+ int dlDelta = dstpsd->lDelta;
+ int slDelta = srcpsd->lDelta;
+
+ bytedst = (char *)dstpsd->pvBits + dsty * dlDelta;
+ bytesrc = (char *)srcpsd->pvBits + srcy * slDelta;
+ dst = (PRGBTRIPLE)bytedst + dstx;
+ src = (PRGBTRIPLE)bytesrc + srcx;
+
+ while(--h >= 0) {
+ PRGBTRIPLE d = dst;
+ PRGBTRIPLE s = src;
+ LONG dx = dstx;
+ LONG sx = srcx;
+ for(i=0; i<w; ++i) {
+ *d = *s;
+ ++d;
+ ++s;
+ }
+ dst += dlDelta;
+ src += slDelta;
+ }
+}
+
+BOOLEAN DIB_To_24BPP_Bitblt( SURFOBJ *DestSurf, SURFOBJ *SourceSurf,
+ SURFGDI *DestGDI, SURFGDI *SourceGDI,
+ PRECTL DestRect, POINTL *SourcePoint,
+ ULONG Delta, XLATEOBJ *ColorTranslation)
+{
+ ULONG i, j, sx, xColor, f1;
+ PBYTE DestBits, SourceBits_24BPP, DestLine, SourceLine_24BPP;
+ PRGBTRIPLE SPDestBits, SPSourceBits_24BPP, SPDestLine, SPSourceLine_24BPP; // specially for 24-to-24 blit
+ PBYTE SourceBits_4BPP, SourceBits_8BPP, SourceLine_4BPP, SourceLine_8BPP;
+ PWORD SourceBits_16BPP, SourceLine_16BPP;
+ PDWORD SourceBits_32BPP, SourceLine_32BPP;
+
+ DestBits = DestSurf->pvBits + (DestRect->top * DestSurf->lDelta) + DestRect->left * 3;
+
+ switch(SourceGDI->BitsPerPixel)
+ {
+ case 4:
+ SourceBits_4BPP = SourceSurf->pvBits + (SourcePoint->y * SourceSurf->lDelta) + SourcePoint->x;
+
+ for (j=DestRect->top; j<DestRect->bottom; j++)
+ {
+ SourceLine_4BPP = SourceBits_4BPP;
+ DestLine = DestBits;
+ sx = SourcePoint->x;
+ f1 = sx & 1;
+
+ for (i=DestRect->left; i<DestRect->right; i++)
+ {
+ xColor = XLATEOBJ_iXlate(ColorTranslation,
+ (*SourceLine_4BPP & altnotmask[sx&1]) >> (4 * (1-(sx & 1))));
+ *DestLine++ = xColor & 0xff;
+ *(PWORD)DestLine = xColor >> 8;
+ DestLine += 2;
+ if(f1 == 1) { SourceLine_4BPP++; f1 = 0; } else { f1 = 1; }
+ sx++;
+ }
+
+ SourceBits_4BPP += SourceSurf->lDelta;
+ DestBits += DestSurf->lDelta;
+ }
+ break;
+
+ default:
+ DbgPrint("DIB_24BPP_Bitblt: Unhandled Source BPP: %u\n", SourceGDI->BitsPerPixel);
+ return FALSE;
+ }
+
+ return TRUE;
+}
--- /dev/null
+#undef WIN32_LEAN_AND_MEAN
+#include <windows.h>
+#include <stdlib.h>
+#include <win32k/bitmaps.h>
+#include <win32k/debug.h>
+#include <debug.h>
+#include <ddk/winddi.h>
+#include "..\eng\objects.h"
+#include "dib.h"
+
+VOID DIB_4BPP_PutPixel(PSURFOBJ SurfObj, LONG x, LONG y, BYTE c)
+{
+ unsigned char *vp;
+ unsigned char mask;
+ PBYTE addr = SurfObj->pvBits;
+
+ addr += (x>>1) + y * SurfObj->lDelta;
+ *addr = (*addr & notmask[x&1]) | (c << ((1-(x&1))<<2));
+}
+
+BYTE DIB_4BPP_GetPixel(PSURFOBJ SurfObj, LONG x, LONG y)
+{
+ PBYTE addr = SurfObj->pvBits;
+
+ return (addr[(x>>1) + y * SurfObj->lDelta] >> ((1-(x&1))<<2) ) & 0x0f;
+}
+
+VOID DIB_4BPP_HLine(PSURFOBJ SurfObj, LONG x1, LONG x2, LONG y, BYTE c)
+{
+ PBYTE addr = SurfObj->pvBits + (x1>>1) + y * SurfObj->lDelta;
+ LONG cx = x1;
+
+ while(cx <= x2) {
+ *addr = (*addr & notmask[x1&1]) | (c << ((1-(x1&1))<<2));
+ if((++x1 & 1) == 0)
+ ++addr;
+ ++cx;
+ }
+}
+
+VOID DIB_4BPP_VLine(PSURFOBJ SurfObj, LONG x, LONG y1, LONG y2, BYTE c)
+{
+ PBYTE addr = SurfObj->pvBits;
+ int lDelta = SurfObj->lDelta;
+
+ addr += (x>>1) + y1 * lDelta;
+ while(y1++ <= y2) {
+ *addr = (*addr & notmask[x&1]) | (c << ((1-(x&1))<<2));
+ addr += lDelta;
+ }
+}
+
+BOOLEAN DIB_To_4BPP_Bitblt( SURFOBJ *DestSurf, SURFOBJ *SourceSurf,
+ SURFGDI *DestGDI, SURFGDI *SourceGDI,
+ PRECTL DestRect, POINTL *SourcePoint,
+ ULONG Delta, XLATEOBJ *ColorTranslation)
+{
+ ULONG i, j, sx, f1, f2, xColor;
+ PBYTE SourceBits_24BPP, SourceLine_24BPP;
+ PBYTE DestBits, DestLine, SourceBits_4BPP, SourceBits_8BPP, SourceLine_4BPP, SourceLine_8BPP;
+ PWORD SourceBits_16BPP, SourceLine_16BPP;
+ PDWORD SourceBits_32BPP, SourceLine_32BPP;
+
+ DestBits = DestSurf->pvBits + (DestRect->left>>1) + DestRect->top * DestSurf->lDelta;
+
+ switch(SourceGDI->BitsPerPixel)
+ {
+ case 4:
+ SourceBits_4BPP = SourceSurf->pvBits + (SourcePoint->y * SourceSurf->lDelta) + SourcePoint->x;
+
+ for (j=DestRect->top; j<DestRect->bottom; j++)
+ {
+ SourceLine_4BPP = SourceBits_4BPP;
+ DestLine = DestBits;
+ sx = SourcePoint->x;
+ f1 = sx & 1;
+ f2 = DestRect->left & 1;
+
+ // FIXME: handle odd begin pixel
+
+ for (i=DestRect->left; i<DestRect->right; i++)
+ {
+ if(f1 == 1) { SourceLine_4BPP++; f1 = 0; } else { f1 = 1; }
+ if(f2 == 1) { DestLine++; f2 = 0; } else { f2 = 1; *DestLine = *SourceLine_4BPP; }
+ sx++;
+ }
+
+ // FIXME: handle odd end pixel
+
+ SourceBits_4BPP += SourceSurf->lDelta;
+ DestBits += DestSurf->lDelta;
+ }
+ break;
+
+ case 24:
+ SourceBits_24BPP = SourceSurf->pvBits + (SourcePoint->y * SourceSurf->lDelta) + SourcePoint->x * 3;
+
+ for (j=DestRect->top; j<DestRect->bottom; j++)
+ {
+ SourceLine_24BPP = SourceBits_24BPP;
+ DestLine = DestBits;
+ sx = SourcePoint->x;
+ f1 = sx & 1;
+ f2 = DestRect->left & 1;
+
+ for (i=DestRect->left; i<DestRect->right; i++)
+ {
+ xColor = (*(SourceLine_24BPP + 2) << 0x10) +
+ (*(SourceLine_24BPP + 1) << 0x08) +
+ (*(SourceLine_24BPP));
+ *DestLine = (*DestLine & notmask[i&1]) |
+ ((XLATEOBJ_iXlate(ColorTranslation, xColor)) << ((4 * (1-(sx & 1)))));
+ if(f2 == 1) { DestLine++; f2 = 0; } else { f2 = 1; }
+ SourceLine_24BPP+=3;
+ sx++;
+ }
+
+ SourceBits_24BPP += SourceSurf->lDelta;
+ DestBits += DestSurf->lDelta;
+ }
+ break;
+
+ default:
+ DbgPrint("DIB_4BPP_Bitblt: Unhandled Source BPP: %u\n", SourceGDI->BitsPerPixel);
+ return FALSE;
+ }
+
+ return TRUE;
+}
#include "enum.h"
#include "objects.h"
-VOID BitBltCopy(SURFOBJ *DestSurf, SURFOBJ *SourceSurf,
- SURFGDI *DestGDI, SURFGDI *SourceGDI,
- PRECTL DestRect, POINTL *SourcePoint,
- ULONG Delta)
-{
- ULONG dy, leftOfSource, leftOfDest, Width, CopyPos;
-
- // FIXME: Get ColorTranslation passed here and do something with it
-
- leftOfSource = SourcePoint->x * SourceGDI->BytesPerPixel;
- leftOfDest = DestRect->left * DestGDI->BytesPerPixel;
- Width = (DestRect->right - DestRect->left) * DestGDI->BytesPerPixel;
- CopyPos = leftOfDest;
-
- for(dy=DestRect->top; dy<DestRect->bottom; dy++)
- {
- RtlCopyMemory(DestSurf->pvBits+CopyPos,
- SourceSurf->pvBits+CopyPos,
- Width);
-
- CopyPos += Delta;
- }
-}
-
BOOL EngIntersectRect(PRECTL prcDst, PRECTL prcSrc1, PRECTL prcSrc2)
-
{
- static const RECTL rclEmpty = { 0, 0, 0, 0 };
+ static const RECTL rclEmpty = { 0, 0, 0, 0 };
- prcDst->left = max(prcSrc1->left, prcSrc2->left);
- prcDst->right = min(prcSrc1->right, prcSrc2->right);
+ prcDst->left = max(prcSrc1->left, prcSrc2->left);
+ prcDst->right = min(prcSrc1->right, prcSrc2->right);
- if (prcDst->left < prcDst->right)
- {
- prcDst->top = max(prcSrc1->top, prcSrc2->top);
- prcDst->bottom = min(prcSrc1->bottom, prcSrc2->bottom);
+ if (prcDst->left < prcDst->right)
+ {
+ prcDst->top = max(prcSrc1->top, prcSrc2->top);
+ prcDst->bottom = min(prcSrc1->bottom, prcSrc2->bottom);
- if (prcDst->top < prcDst->bottom)
- return(TRUE);
- }
+ if (prcDst->top < prcDst->bottom) return(TRUE);
+ }
- *prcDst = rclEmpty;
+ *prcDst = rclEmpty;
- return(FALSE);
+ return(FALSE);
}
+
BOOL EngBitBlt(SURFOBJ *Dest, SURFOBJ *Source,
SURFOBJ *Mask, CLIPOBJ *ClipRegion,
XLATEOBJ *ColorTranslation, RECTL *DestRect,
POINTL *SourcePoint, POINTL *MaskRect,
BRUSHOBJ *Brush, POINTL *BrushOrigin, ROP4 rop4)
{
- BYTE clippingType;
- RECTL rclTmp;
- POINTL ptlTmp;
- RECT_ENUM RectEnum;
- BOOL EnumMore;
- SURFGDI *DestGDI, *SourceGDI;
- BOOLEAN canCopyBits;
-
- // If we don't have to do anything special, we can punt to DrvCopyBits
- // if it exists
- if( (Mask == NULL) && (MaskRect == NULL) && (Brush == NULL) &&
- (BrushOrigin == NULL) && (rop4 == 0) )
- {
- canCopyBits = TRUE;
- } else
- canCopyBits = FALSE;
-
- // FIXME: Use XLATEOBJ to translate source bitmap into destination bitmap's
- // format. Call DrvDitherColor function where necessary and if available
-
- // FIXME: If canCopyBits == TRUE AND the driver has a DrvCopyBits then
- // punt to EngCopyBits and not the driver's DrvCopyBits just yet so
- // that the EngCopyBits can take care of the clipping drivers
- // DrvCopyBits
-
- // FIXME: Don't punt to DrvBitBlt straight away. Instead, mark a typedef'd
- // function to go there instead of the Engine's bltting function
- // so as to do the clipping for the driver
-
- // Check for CopyBits or BitBlt hooks if one is not a GDI managed bitmap
- if((Dest->iType!=STYPE_BITMAP) || (Source->iType!=STYPE_BITMAP))
- {
- // Destination surface is device managed
- if(Dest->iType!=STYPE_BITMAP)
- {
- DestGDI = AccessInternalObjectFromUserObject(Dest);
-
- if ((DestGDI->CopyBits!=NULL) && (canCopyBits == TRUE))
- {
- return DestGDI->CopyBits(Dest, Source, ClipRegion,
- ColorTranslation, DestRect, SourcePoint);
- }
-
- if (DestGDI->BitBlt!=NULL)
- {
- return DestGDI->BitBlt(Dest, Source, Mask, ClipRegion,
- ColorTranslation, DestRect, SourcePoint,
- MaskRect, Brush, BrushOrigin, rop4);
- }
- }
-
- // Source surface is device managed
- if(Source->iType!=STYPE_BITMAP)
- {
- SourceGDI = AccessInternalObjectFromUserObject(Source);
-
- if ((SourceGDI->CopyBits!=NULL) && (canCopyBits == TRUE))
- {
- return SourceGDI->CopyBits(Dest, Source, ClipRegion,
- ColorTranslation, DestRect, SourcePoint);
- }
-
- if (SourceGDI->BitBlt!=NULL)
- {
- return SourceGDI->BitBlt(Dest, Source, Mask, ClipRegion,
- ColorTranslation, DestRect, SourcePoint,
- MaskRect, Brush, BrushOrigin, rop4);
- }
-
-
- // Should never get here, if it's not GDI managed then the device
- // should take care of it
-
- // FIXME: Error message here
- }
-
- }
-
- DestGDI = AccessInternalObjectFromUserObject(Dest);
- SourceGDI = AccessInternalObjectFromUserObject(Source);
-
- // Determine clipping type
- if (ClipRegion == (CLIPOBJ *) NULL)
- {
- clippingType = DC_TRIVIAL;
- } else {
- clippingType = ClipRegion->iDComplexity;
- }
-
- // We don't handle color translation just yet
-
- if ((rop4 == 0x0000CCCC) &&
- ((ColorTranslation == NULL) || (ColorTranslation->flXlate & XO_TRIVIAL)))
- {
- switch(clippingType)
- {
- case DC_TRIVIAL:
- BitBltCopy(Dest, Source,
- DestGDI, SourceGDI,
- DestRect, SourcePoint, Source->lDelta);
-
- return(TRUE);
-
- case DC_RECT:
-
- // Clip the blt to the clip rectangle
-
- EngIntersectRect(&rclTmp, DestRect, &ClipRegion->rclBounds);
-
- ptlTmp.x = SourcePoint->x + rclTmp.left - DestRect->left;
- ptlTmp.y = SourcePoint->y + rclTmp.top - DestRect->top;
-
- BitBltCopy(Dest, Source,
- DestGDI, SourceGDI,
- &rclTmp, &ptlTmp, Source->lDelta);
-
- return(TRUE);
-
- case DC_COMPLEX:
-
- CLIPOBJ_cEnumStart(ClipRegion, FALSE, CT_RECTANGLES,
- CD_ANY, ENUM_RECT_LIMIT);
-
- do {
- EnumMore = CLIPOBJ_bEnum(ClipRegion,(ULONG) sizeof(RectEnum),
- (PVOID) &RectEnum);
-
- if (RectEnum.c > 0)
- {
- RECTL* prclEnd = &RectEnum.arcl[RectEnum.c];
- RECTL* prcl = &RectEnum.arcl[0];
-
- do {
- EngIntersectRect(prcl, prcl, DestRect);
-
- ptlTmp.x = SourcePoint->x + prcl->left
- - DestRect->left;
- ptlTmp.y = SourcePoint->y + prcl->top
- - DestRect->top;
-
- BitBltCopy(Dest, Source,
- DestGDI, SourceGDI,
- prcl, &ptlTmp, Source->lDelta);
-
- prcl++;
-
- } while (prcl < prclEnd);
- }
-
- } while(EnumMore);
-
- return(TRUE);
- }
- }
-
- return(FALSE);
+ BYTE clippingType;
+ RECTL rclTmp;
+ POINTL ptlTmp;
+ RECT_ENUM RectEnum;
+ BOOL EnumMore;
+ PSURFGDI DestGDI, SourceGDI;
+ HSURF hTemp;
+ PSURFOBJ TempSurf;
+ BOOLEAN canCopyBits;
+ POINTL TempPoint;
+ RECTL TempRect;
+ SIZEL TempSize;
+
+ SourceGDI = AccessInternalObjectFromUserObject(Source);
+
+ // If we don't have to do anything special, we can punt to DrvCopyBits
+ // if it exists
+ if( (Mask == NULL) && (MaskRect == NULL) && (Brush == NULL) &&
+ (BrushOrigin == NULL) && (rop4 == 0) )
+ {
+ canCopyBits = TRUE;
+ } else
+ canCopyBits = FALSE;
+
+ // Check for CopyBits or BitBlt hooks if one is not a GDI managed bitmap, IF:
+ // * The destination bitmap is not managed by the GDI OR
+ if(Dest->iType != STYPE_BITMAP)
+ {
+ // Destination surface is device managed
+ DestGDI = AccessInternalObjectFromUserObject(Dest);
+
+ if (DestGDI->BitBlt!=NULL)
+ {
+ // The destination is device managed, therefore get the source into a format compatible surface
+ TempPoint.x = 0;
+ TempPoint.y = 0;
+ TempRect.top = 0;
+ TempRect.left = 0;
+ TempRect.bottom = DestRect->bottom - DestRect->top;
+ TempRect.right = DestRect->right - DestRect->left;
+ TempSize.cx = TempRect.right;
+ TempSize.cy = TempRect.bottom;
+
+ hTemp = EngCreateBitmap(TempSize,
+ DIB_GetDIBWidthBytes(DestRect->right - DestRect->left, BitsPerFormat(Dest->iBitmapFormat)),
+ Dest->iBitmapFormat, 0, NULL);
+ TempSurf = AccessUserObject(hTemp);
+
+ // FIXME: Skip creating a TempSurf if we have the same BPP and palette
+ EngBitBlt(TempSurf, Source, NULL, NULL, ColorTranslation, &TempRect, SourcePoint, NULL, NULL, NULL, 0);
+
+ return DestGDI->BitBlt(Dest, TempSurf, Mask, ClipRegion,
+ NULL, DestRect, &TempPoint,
+ MaskRect, Brush, BrushOrigin, rop4);
+ }
+ }
+
+ // * The source bitmap is not managed by the GDI and we didn't already obtain it using EngCopyBits from the device
+ if(Source->iType != STYPE_BITMAP && SourceGDI->CopyBits == NULL)
+ {
+ if (SourceGDI->BitBlt!=NULL)
+ {
+ // Request the device driver to return the bitmap in a format compatible with the device
+ return SourceGDI->BitBlt(Dest, Source, Mask, ClipRegion,
+ NULL, DestRect, SourcePoint,
+ MaskRect, Brush, BrushOrigin, rop4);
+
+ // Convert the surface from the driver into the required destination surface
+ }
+ }
+
+ DestGDI = AccessInternalObjectFromUserObject(Dest);
+ SourceGDI = AccessInternalObjectFromUserObject(Source);
+
+ // Determine clipping type
+ if (ClipRegion == (CLIPOBJ *) NULL)
+ {
+ clippingType = DC_TRIVIAL;
+ } else {
+ clippingType = ClipRegion->iDComplexity;
+ }
+
+ // We don't handle color translation just yet [we dont have to.. REMOVE REMOVE REMOVE]
+ switch(clippingType)
+ {
+ case DC_TRIVIAL:
+ CopyBitsCopy(Dest, Source, DestGDI, SourceGDI, DestRect, SourcePoint, Source->lDelta, ColorTranslation);
+ return(TRUE);
+
+ case DC_RECT:
+
+ // Clip the blt to the clip rectangle
+ EngIntersectRect(&rclTmp, DestRect, &ClipRegion->rclBounds);
+
+ ptlTmp.x = SourcePoint->x + rclTmp.left - DestRect->left;
+ ptlTmp.y = SourcePoint->y + rclTmp.top - DestRect->top;
+
+ return(TRUE);
+
+ case DC_COMPLEX:
+
+ CLIPOBJ_cEnumStart(ClipRegion, FALSE, CT_RECTANGLES, CD_ANY, ENUM_RECT_LIMIT);
+
+ do {
+ EnumMore = CLIPOBJ_bEnum(ClipRegion,(ULONG) sizeof(RectEnum), (PVOID) &RectEnum);
+
+ if (RectEnum.c > 0)
+ {
+ RECTL* prclEnd = &RectEnum.arcl[RectEnum.c];
+ RECTL* prcl = &RectEnum.arcl[0];
+
+ do {
+ EngIntersectRect(prcl, prcl, DestRect);
+
+ ptlTmp.x = SourcePoint->x + prcl->left - DestRect->left;
+ ptlTmp.y = SourcePoint->y + prcl->top - DestRect->top;
+
+ prcl++;
+
+ } while (prcl < prclEnd);
+ }
+
+ } while(EnumMore);
+
+ return(TRUE);
+ }
+
+ return(FALSE);
}
PVOID BRUSHOBJ_pvAllocRbrush(IN PBRUSHOBJ BrushObj,
IN ULONG ObjSize)
{
- BrushObj->pvRbrush=EngAllocMem(0, ObjSize, 0);
- return BrushObj->pvRbrush;
+ BrushObj->pvRbrush=EngAllocMem(0, ObjSize, 0);
+ return BrushObj->pvRbrush;
}
PVOID BRUSHOBJ_pvGetRbrush(IN PBRUSHOBJ BrushObj)
{
- return BrushObj->pvRbrush;
+ return BrushObj->pvRbrush;
}
typedef struct _BRUSHINST
{
- // We need to removed ajC0-3 when color pattern code is complete!!!
- //
- BYTE ajC0[8]; // Color bits for plane 0
- BYTE ajC1[8]; // Color bits for plane 1
- BYTE ajC2[8]; // Color bits for plane 2
- BYTE ajC3[8]; // Color bits for plane 3
+ // We need to removed ajC0-3 when color pattern code is complete!!!
+ //
+ BYTE ajC0[8]; // Color bits for plane 0
+ BYTE ajC1[8]; // Color bits for plane 1
+ BYTE ajC2[8]; // Color bits for plane 2
+ BYTE ajC3[8]; // Color bits for plane 3
- BYTE ajPattern[32]; // Color bits for the mask
- USHORT usStyle; // Brush style
- BYTE fjAccel; // Accelerator flags
- BYTE jFgColor; // Current foreground color
- BYTE jBkColor; // Current background color
- BYTE RealWidth;//
- BYTE YShiftValue; //
- BYTE jOldBrushRealized; //
- DWORD Width; // Width of brush
- DWORD Height;
- BYTE *pPattern; //Pointer to realized mono pattern
+ BYTE ajPattern[32]; // Color bits for the mask
+ USHORT usStyle; // Brush style
+ BYTE fjAccel; // Accelerator flags
+ BYTE jFgColor; // Current foreground color
+ BYTE jBkColor; // Current background color
+ BYTE RealWidth;//
+ BYTE YShiftValue; //
+ BYTE jOldBrushRealized; //
+ DWORD Width; // Width of brush
+ DWORD Height;
+ BYTE *pPattern; //Pointer to realized mono pattern
} BRUSHINST;
#define BRI_SOLID 0
CLIPOBJ *EngCreateClipRegion(ULONG NumRects, RECTL Rects[],
ULONG Mode, ULONG Options)
{
- HCLIP NewClip;
- CLIPOBJ *ClipObj;
- CLIPGDI *ClipGDI;
-
- ClipObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(CLIPOBJ), NULL);
- ClipGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(CLIPGDI), NULL);
-
- NewClip = CreateGDIHandle(ClipGDI, ClipObj);
-
- ClipGDI->NumRegionRects = NumRects;
- ClipGDI->RegionRects = Rects;
- ClipObj->iMode = Mode;
- ClipObj->fjOptions = Options;
- ClipObj->iDComplexity = DC_TRIVIAL;
-
- if(NumRects == 1)
- {
- ClipObj->iFComplexity = FC_RECT;
- ClipObj->iDComplexity = DC_RECT;
-
- // FIXME: Is this correct??
- ClipObj->rclBounds = Rects[0];
- } else
- {
- ClipObj->iDComplexity = DC_COMPLEX;
- if(NumRects <= 4)
- {
- ClipObj->iFComplexity = FC_RECT4;
- } else
- {
- ClipObj->iFComplexity = FC_COMPLEX;
- }
- }
-
- return ClipObj;
+ HCLIP NewClip;
+ CLIPOBJ *ClipObj;
+ CLIPGDI *ClipGDI;
+
+ ClipObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(CLIPOBJ), NULL);
+ ClipGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(CLIPGDI), NULL);
+
+ NewClip = CreateGDIHandle(ClipGDI, ClipObj);
+
+ ClipGDI->NumRegionRects = NumRects;
+ ClipGDI->RegionRects = Rects;
+ ClipObj->iMode = Mode;
+ ClipObj->fjOptions = Options;
+ ClipObj->iDComplexity = DC_TRIVIAL;
+
+ if(NumRects == 1)
+ {
+ ClipObj->iFComplexity = FC_RECT;
+ ClipObj->iDComplexity = DC_RECT;
+
+ // FIXME: Is this correct??
+ ClipObj->rclBounds = Rects[0];
+ } else
+ {
+ ClipObj->iDComplexity = DC_COMPLEX;
+ if(NumRects <= 4)
+ {
+ ClipObj->iFComplexity = FC_RECT4;
+ } else
+ {
+ ClipObj->iFComplexity = FC_COMPLEX;
+ }
+ }
+
+ return ClipObj;
}
VOID EngDeleteClipRegion(CLIPOBJ *ClipObj)
{
- HCLIP HClip = AccessHandleFromUserObject(ClipObj);
- CLIPGDI *ClipGDI = AccessInternalObject(HClip);
+ HCLIP HClip = AccessHandleFromUserObject(ClipObj);
+ CLIPGDI *ClipGDI = AccessInternalObject(HClip);
- EngFreeMem(ClipGDI);
- EngFreeMem(ClipObj);
- FreeGDIHandle(HClip);
+ EngFreeMem(ClipGDI);
+ EngFreeMem(ClipObj);
+ FreeGDIHandle(HClip);
}
VOID EngIntersectClipRegion(CLIPOBJ *ClipObj, ULONG NumRects, RECTL *IntersectRects)
{
- CLIPGDI *ClipGDI = AccessInternalObjectFromUserObject(ClipObj);
-
- ClipGDI->NumIntersectRects = NumRects;
- ClipGDI->IntersectRects = IntersectRects;
-
- if(NumRects == 1)
- {
- ClipObj->iDComplexity = DC_RECT;
- ClipObj->rclBounds = IntersectRects[0];
- } else
- {
- ClipObj->iDComplexity = DC_COMPLEX;
- ClipGDI->IntersectRects = IntersectRects;
- }
+ CLIPGDI *ClipGDI = AccessInternalObjectFromUserObject(ClipObj);
+
+ ClipGDI->NumIntersectRects = NumRects;
+ ClipGDI->IntersectRects = IntersectRects;
+
+ if(NumRects == 1)
+ {
+ ClipObj->iDComplexity = DC_RECT;
+ ClipObj->rclBounds = IntersectRects[0];
+ } else
+ {
+ ClipObj->iDComplexity = DC_COMPLEX;
+ ClipGDI->IntersectRects = IntersectRects;
+ }
}
CLIPOBJ *EngCreateClip(VOID)
{
- return EngAllocMem(FL_ZERO_MEMORY, sizeof(CLIPOBJ), NULL);
+ return EngAllocMem(FL_ZERO_MEMORY, sizeof(CLIPOBJ), NULL);
}
VOID EngDeleteClip(CLIPOBJ *ClipRegion)
{
- EngFreeMem(ClipRegion);
+ EngFreeMem(ClipRegion);
}
ULONG CLIPOBJ_cEnumStart(IN PCLIPOBJ ClipObj, IN BOOL ShouldDoAll,
IN ULONG ClipType, IN ULONG BuildOrder,
IN ULONG MaxRects)
{
- CLIPGDI *ClipGDI = AccessInternalObjectFromUserObject(ClipObj);
+ CLIPGDI *ClipGDI = AccessInternalObjectFromUserObject(ClipObj);
- ClipGDI->EnumPos = 0;
- ClipGDI->EnumRects.c = MaxRects;
+ ClipGDI->EnumPos = 0;
+ ClipGDI->EnumRects.c = MaxRects;
- // Return the number of rectangles enumerated
- if(ClipGDI->EnumRects.c>MaxRects)
- {
- ClipGDI->EnumRects.c = 0xFFFFFFFF;
- }
+ // Return the number of rectangles enumerated
+ if(ClipGDI->EnumRects.c>MaxRects)
+ {
+ ClipGDI->EnumRects.c = 0xFFFFFFFF;
+ }
- return ClipGDI->EnumRects.c;
+ return ClipGDI->EnumRects.c;
}
BOOL CLIPOBJ_bEnum(IN PCLIPOBJ ClipObj, IN ULONG ObjSize,
OUT ULONG *EnumRects)
{
- CLIPGDI *ClipGDI = AccessInternalObjectFromUserObject(ClipObj);
+ CLIPGDI *ClipGDI = AccessInternalObjectFromUserObject(ClipObj);
- ClipGDI->EnumPos++;
+ ClipGDI->EnumPos++;
- if(ClipGDI->EnumPos > ClipGDI->EnumRects.c)
- {
- return FALSE;
- } else
- return TRUE;
+ if(ClipGDI->EnumPos > ClipGDI->EnumRects.c)
+ {
+ return FALSE;
+ } else
+ return TRUE;
}
#include <ddk/winddi.h>
#include "objects.h"
#include "enum.h"
+#include "../dib/dib.h"
-VOID CopyBitsCopy(SURFOBJ *DestSurf, SURFOBJ *SourceSurf,
- SURFGDI *DestGDI, SURFGDI *SourceGDI,
- PRECTL DestRect, POINTL *SourcePoint,
- ULONG Delta, XLATEOBJ *ColorTranslation)
+BOOLEAN CopyBitsCopy(SURFOBJ *DestSurf, SURFOBJ *SourceSurf,
+ SURFGDI *DestGDI, SURFGDI *SourceGDI,
+ PRECTL DestRect, POINTL *SourcePoint,
+ ULONG Delta, XLATEOBJ *ColorTranslation)
{
- ULONG dy, leftOfSource, leftOfDest, Width, SourceBPP, DestBPP, RGBulong = 0, idxColor, i, TrivialCopy = 0;
- BYTE *SourcePos, *SourceInitial, *DestPos, *DestInitial;
-
- // FIXME: Get ColorTranslation passed here and do something with it
-
- if(ColorTranslation == NULL)
- {
- TrivialCopy = 1;
- } else if(ColorTranslation->flXlate & XO_TRIVIAL)
- {
- TrivialCopy = 1;
- }
-
- leftOfSource = SourcePoint->x * SourceGDI->BytesPerPixel;
- leftOfDest = DestRect->left * DestGDI->BytesPerPixel;
- Width = (DestRect->right - DestRect->left) * DestGDI->BytesPerPixel;
-
- if(TrivialCopy == 1)
- {
- for(dy=DestRect->top; dy<DestRect->bottom; dy++)
- {
- memcpy(DestSurf->pvBits+Delta*dy+leftOfDest,
- SourceSurf->pvBits+Delta*dy+leftOfSource,
- Width);
- }
- } else
- if(ColorTranslation->flXlate & XO_TABLE)
- {
- SourceBPP = bytesPerPixel(SourceSurf->iBitmapFormat);
- DestBPP = bytesPerPixel(DestSurf->iBitmapFormat);
-
- SourcePos = SourceSurf->pvBits +
- (SourcePoint->y * SourceSurf->lDelta) + (SourcePoint->x * SourceBPP);
- SourceInitial = SourcePos;
-
- DestPos = DestSurf->pvBits +
- ((DestRect->bottom - DestRect->top) * DestSurf->lDelta) + (DestRect->left * DestBPP);
- DestInitial = DestPos;
-
- for(i=DestRect->left; i<DestRect->right; i++)
- {
- memcpy(&RGBulong, SourcePos, SourceBPP);
- idxColor = XLATEOBJ_iXlate(ColorTranslation, RGBulong);
- memcpy(DestPos, &idxColor, DestBPP);
-
- SourcePos+=SourceBPP;
- DestPos+=DestBPP;
- }
- SourcePos = SourceInitial + SourceSurf->lDelta;
- DestPos = DestInitial + DestSurf->lDelta;
- }
+ ULONG DestWidth, DestHeight, CurrentDestLine, CurrentSourceLine, CurrentDestCol, CurrentSourceCol, i, TranslationPixel;
+
+ PFN_DIB_GetPixel Source_DIB_GetPixel;
+ PFN_DIB_PutPixel Dest_DIB_PutPixel;
+
+ DestWidth = DestRect->right - DestRect->left;
+ DestHeight = DestRect->bottom - DestRect->top;
+ CurrentSourceCol = SourcePoint->x;
+ CurrentSourceLine = SourcePoint->y;
+
+ // Assign GetPixel DIB function according to bytes per pixel
+ switch(DestGDI->BitsPerPixel)
+ {
+ case 4:
+ return DIB_To_4BPP_Bitblt(DestSurf, SourceSurf, DestGDI, SourceGDI,
+ DestRect, SourcePoint, Delta, ColorTranslation);
+ break;
+
+ case 24:
+ return DIB_To_24BPP_Bitblt(DestSurf, SourceSurf, DestGDI, SourceGDI,
+ DestRect, SourcePoint, Delta, ColorTranslation);
+ break;
+
+ default:
+ return FALSE;
+ }
+
+ return TRUE;
}
BOOL EngCopyBits(SURFOBJ *Dest, SURFOBJ *Source,
CLIPOBJ *Clip, XLATEOBJ *ColorTranslation,
RECTL *DestRect, POINTL *SourcePoint)
{
- SURFGDI *DestGDI, *SourceGDI;
- BYTE clippingType;
- RECTL rclTmp;
- POINTL ptlTmp;
- RECT_ENUM RectEnum;
- BOOL EnumMore;
-
- // FIXME: Do color translation -- refer to eng\bitblt.c
-
- // FIXME: Don't punt to the driver's DrvCopyBits immediately. Instead,
- // mark the copy block function to be DrvCopyBits instead of the
- // GDI's copy bit function so as to remove clipping from the
- // driver's responsibility
-
- // If one of the surfaces isn't managed by the GDI
- if((Dest->iType!=STYPE_BITMAP) || (Source->iType!=STYPE_BITMAP))
- {
-
- // Destination surface is device managed
- if(Dest->iType!=STYPE_BITMAP)
+ SURFGDI *DestGDI, *SourceGDI;
+ BYTE clippingType;
+ RECTL rclTmp;
+ POINTL ptlTmp;
+ RECT_ENUM RectEnum;
+ BOOL EnumMore;
+
+ // FIXME: Don't punt to the driver's DrvCopyBits immediately. Instead,
+ // mark the copy block function to be DrvCopyBits instead of the
+ // GDI's copy bit function so as to remove clipping from the
+ // driver's responsibility
+
+ // If one of the surfaces isn't managed by the GDI
+ if((Dest->iType!=STYPE_BITMAP) || (Source->iType!=STYPE_BITMAP))
+ {
+ // Destination surface is device managed
+ if(Dest->iType!=STYPE_BITMAP)
+ {
+ DestGDI = (PSURFGDI)AccessInternalObjectFromUserObject(Dest);
+
+ if (DestGDI->CopyBits!=NULL)
{
- DestGDI = AccessInternalObjectFromUserObject(Dest);
-
- if (DestGDI->CopyBits!=NULL)
- {
- return DestGDI->CopyBits(Dest, Source, Clip,
- ColorTranslation, DestRect, SourcePoint);
- }
+ return DestGDI->CopyBits(Dest, Source, Clip, ColorTranslation, DestRect, SourcePoint);
}
+ }
- // Source surface is device managed
- if(Source->iType!=STYPE_BITMAP)
- {
- SourceGDI = AccessInternalObjectFromUserObject(Source);
+ // Source surface is device managed
+ if(Source->iType!=STYPE_BITMAP)
+ {
+ SourceGDI = (PSURFGDI)AccessInternalObjectFromUserObject(Source);
- if (SourceGDI->CopyBits!=NULL)
- {
- return SourceGDI->CopyBits(Dest, Source, Clip,
- ColorTranslation, DestRect, SourcePoint);
- }
+ if (SourceGDI->CopyBits!=NULL)
+ {
+ return SourceGDI->CopyBits(Dest, Source, Clip, ColorTranslation, DestRect, SourcePoint);
}
+ }
- // If CopyBits wasn't hooked, BitBlt must be
- return EngBitBlt(Dest, Source,
- NULL, Clip, ColorTranslation, DestRect, SourcePoint,
- NULL, NULL, NULL, NULL);
- }
-
- // Determine clipping type
- if (Clip == (CLIPOBJ *) NULL)
- {
- clippingType = DC_TRIVIAL;
- } else {
- clippingType = Clip->iDComplexity;
- }
-
- // We only handle XO_TABLE translations at the momement
- if ((ColorTranslation == NULL) || (ColorTranslation->flXlate & XO_TRIVIAL) ||
- (ColorTranslation->flXlate & XO_TABLE))
- {
- SourceGDI = AccessInternalObjectFromUserObject(Source);
- DestGDI = AccessInternalObjectFromUserObject(Dest);
-
- switch(clippingType)
- {
- case DC_TRIVIAL:
- CopyBitsCopy(Dest, Source,
- DestGDI, SourceGDI,
- DestRect, SourcePoint, Source->lDelta, ColorTranslation);
+ // If CopyBits wasn't hooked, BitBlt must be
+ return EngBitBlt(Dest, Source,
+ NULL, Clip, ColorTranslation, DestRect, SourcePoint,
+ NULL, NULL, NULL, NULL);
+ }
- return(TRUE);
+ // Determine clipping type
+ if (Clip == (CLIPOBJ *) NULL)
+ {
+ clippingType = DC_TRIVIAL;
+ } else {
+ clippingType = Clip->iDComplexity;
+ }
- case DC_RECT:
+ // We only handle XO_TABLE translations at the momement
+ if ((ColorTranslation == NULL) || (ColorTranslation->flXlate & XO_TRIVIAL) ||
+ (ColorTranslation->flXlate & XO_TABLE))
+ {
+ SourceGDI = (PSURFGDI)AccessInternalObjectFromUserObject(Source);
+ DestGDI = (PSURFGDI)AccessInternalObjectFromUserObject(Dest);
- // Clip the blt to the clip rectangle
+ switch(clippingType)
+ {
+ case DC_TRIVIAL:
+ CopyBitsCopy(Dest, Source, DestGDI, SourceGDI, DestRect, SourcePoint, Source->lDelta, ColorTranslation);
+ return(TRUE);
- EngIntersectRect(&rclTmp, DestRect, &Clip->rclBounds);
+ case DC_RECT:
+ // Clip the blt to the clip rectangle
+ EngIntersectRect(&rclTmp, DestRect, &Clip->rclBounds);
- ptlTmp.x = SourcePoint->x + rclTmp.left - DestRect->left;
- ptlTmp.y = SourcePoint->y + rclTmp.top - DestRect->top;
+ ptlTmp.x = SourcePoint->x + rclTmp.left - DestRect->left;
+ ptlTmp.y = SourcePoint->y + rclTmp.top - DestRect->top;
- CopyBitsCopy(Dest, Source,
- DestGDI, SourceGDI,
- &rclTmp, &ptlTmp, Source->lDelta, ColorTranslation);
+ CopyBitsCopy(Dest, Source, DestGDI, SourceGDI, &rclTmp, &ptlTmp, Source->lDelta, ColorTranslation);
- return(TRUE);
+ return(TRUE);
- case DC_COMPLEX:
+ case DC_COMPLEX:
- CLIPOBJ_cEnumStart(Clip, FALSE, CT_RECTANGLES,
- CD_ANY, ENUM_RECT_LIMIT);
+ CLIPOBJ_cEnumStart(Clip, FALSE, CT_RECTANGLES, CD_ANY, ENUM_RECT_LIMIT);
- do {
- EnumMore = CLIPOBJ_bEnum(Clip,(ULONG) sizeof(RectEnum),
- (PVOID) &RectEnum);
+ do {
+ EnumMore = CLIPOBJ_bEnum(Clip,(ULONG) sizeof(RectEnum), (PVOID) &RectEnum);
- if (RectEnum.c > 0)
- {
- RECTL* prclEnd = &RectEnum.arcl[RectEnum.c];
- RECTL* prcl = &RectEnum.arcl[0];
+ if (RectEnum.c > 0)
+ {
+ RECTL* prclEnd = &RectEnum.arcl[RectEnum.c];
+ RECTL* prcl = &RectEnum.arcl[0];
- do {
- EngIntersectRect(prcl, prcl, DestRect);
+ do {
+ EngIntersectRect(prcl, prcl, DestRect);
- ptlTmp.x = SourcePoint->x + prcl->left
- - DestRect->left;
- ptlTmp.y = SourcePoint->y + prcl->top
- - DestRect->top;
+ ptlTmp.x = SourcePoint->x + prcl->left - DestRect->left;
+ ptlTmp.y = SourcePoint->y + prcl->top - DestRect->top;
- CopyBitsCopy(Dest, Source,
- DestGDI, SourceGDI,
- prcl, &ptlTmp, Source->lDelta, ColorTranslation);
+ if(!CopyBitsCopy(Dest, Source, DestGDI, SourceGDI,
+ prcl, &ptlTmp, Source->lDelta, ColorTranslation)) return FALSE;
- prcl++;
+ prcl++;
- } while (prcl < prclEnd);
- }
+ } while (prcl < prclEnd);
+ }
- } while(EnumMore);
+ } while(EnumMore);
- return(TRUE);
- }
- }
+ return(TRUE);
+ }
+ }
- return FALSE;
+ return FALSE;
}
#include <ddk/ntddk.h>
DWORD STDCALL EngDeviceIoControl(
- HANDLE hDevice,
- DWORD dwIoControlCode,
- LPVOID lpInBuffer,
- DWORD nInBufferSize,
- LPVOID lpOutBuffer,
- DWORD nOutBufferSize,
- DWORD *lpBytesReturned)
+ HANDLE hDevice,
+ DWORD dwIoControlCode,
+ LPVOID lpInBuffer,
+ DWORD nInBufferSize,
+ LPVOID lpOutBuffer,
+ DWORD nOutBufferSize,
+ DWORD *lpBytesReturned)
{
- PIRP Irp;
- NTSTATUS Status;
- KEVENT Event;
- IO_STATUS_BLOCK Iosb;
- PDRIVER_OBJECT DriverObject;
-
- DriverObject = hDevice;
-
- KeInitializeEvent(&Event, SynchronizationEvent, FALSE);
-
- Irp = IoBuildDeviceIoControlRequest(dwIoControlCode,
- DriverObject->DeviceObject,
- lpInBuffer,
- nInBufferSize,
- lpOutBuffer,
- nOutBufferSize,
- FALSE,
- &Event,
- &Iosb);
-
- Status = IoCallDriver(DriverObject->DeviceObject, Irp);
-
- if (Status == STATUS_PENDING)
- {
- (void) KeWaitForSingleObject(&Event, Executive, KernelMode, TRUE, 0);
- }
-
- return (Status);
+ PIRP Irp;
+ NTSTATUS Status;
+ KEVENT Event;
+ IO_STATUS_BLOCK Iosb;
+ PDRIVER_OBJECT DriverObject;
+
+ DriverObject = hDevice;
+
+ KeInitializeEvent(&Event, SynchronizationEvent, FALSE);
+
+ Irp = IoBuildDeviceIoControlRequest(dwIoControlCode, DriverObject->DeviceObject, lpInBuffer, nInBufferSize,
+ lpOutBuffer, nOutBufferSize, FALSE, &Event, &Iosb);
+
+ Status = IoCallDriver(DriverObject->DeviceObject, Irp);
+
+ if (Status == STATUS_PENDING)
+ {
+ (void) KeWaitForSingleObject(&Event, Executive, KernelMode, TRUE, 0);
+ }
+
+ return (Status);
}
IN ULONG BuildOrder,
IN ULONG MaxRects)
{
- // Sets the parameters for enumerating rectables in the given clip region
+ // Sets the parameters for enumerating rectables in the given clip region
- ULONG enumCount = 0;
- ENUMRECTS enumRects;
+ ULONG enumCount = 0;
+ ENUMRECTS enumRects;
- // MUCH WORK TO DO HERE
+ // MUCH WORK TO DO HERE
- // Return the number of rectangles enumerated
- if(enumCount>MaxRects)
- {
- enumCount = 0xFFFFFFFF;
- }
- return enumCount;
+ // Return the number of rectangles enumerated
+ if(enumCount>MaxRects)
+ {
+ enumCount = 0xFFFFFFFF;
+ }
+ return enumCount;
}
BOOL CLIPOBJ_bEnum(IN PCLIPOBJ ClipObj,
typedef struct _RECT_ENUM
{
- ULONG c;
- RECTL arcl[ENUM_RECT_LIMIT];
+ ULONG c;
+ RECTL arcl[ENUM_RECT_LIMIT];
} RECT_ENUM;
ULONG CreateGDIHandle(PVOID InternalObject, PVOID UserObject)
{
- ULONG NewHandle = HandleCounter++;
+ ULONG NewHandle = HandleCounter++;
- GDIHandles[NewHandle].InternalObject = InternalObject;
- GDIHandles[NewHandle].UserObject = UserObject;
+ GDIHandles[NewHandle].InternalObject = InternalObject;
+ GDIHandles[NewHandle].UserObject = UserObject;
- return NewHandle;
+ return NewHandle;
}
VOID FreeGDIHandle(ULONG Handle)
{
- GDIHandles[Handle].InternalObject = NULL;
- GDIHandles[Handle].UserObject = NULL;
+ GDIHandles[Handle].InternalObject = NULL;
+ GDIHandles[Handle].UserObject = NULL;
}
PVOID AccessInternalObject(ULONG Handle)
{
- return GDIHandles[Handle].InternalObject;
+ return GDIHandles[Handle].InternalObject;
}
PVOID AccessUserObject(ULONG Handle)
{
- return GDIHandles[Handle].UserObject;
+ return GDIHandles[Handle].UserObject;
}
PVOID AccessInternalObjectFromUserObject(PVOID UserObject)
{
- ULONG i;
+ ULONG i;
- for(i=0; i<MAX_GDI_HANDLES; i++)
- {
- if(GDIHandles[i].UserObject == UserObject)
- return GDIHandles[i].InternalObject;
- }
+ for(i=0; i<MAX_GDI_HANDLES; i++)
+ {
+ if(GDIHandles[i].UserObject == UserObject) return GDIHandles[i].InternalObject;
+ }
- return NULL;
+ return NULL;
}
ULONG AccessHandleFromUserObject(PVOID UserObject)
{
- ULONG i;
+ ULONG i;
- for(i=0; i<MAX_GDI_HANDLES; i++)
- {
- if(GDIHandles[i].UserObject == UserObject)
- return i;
- }
+ for(i=0; i<MAX_GDI_HANDLES; i++)
+ {
+ if(GDIHandles[i].UserObject == UserObject) return i;
+ }
- return INVALID_HANDLE;
+ return INVALID_HANDLE;
}
*/
typedef struct _GDI_HANDLE {
- ULONG Handle;
- PVOID InternalObject;
- PVOID UserObject;
+ ULONG Handle;
+ PVOID InternalObject;
+ PVOID UserObject;
} GDI_HANDLE, *PGDI_HANDLE;
#define INVALID_HANDLE 0
#include <ddk/winddi.h>
#include "objects.h"
+#include "../dib/dib.h"
// POSSIBLE FIXME: Switch X and Y's so that drawing a line doesn't try to draw from 150 to 50 (negative dx)
-VOID LinePoint(SURFOBJ *Surface, SURFGDI *SurfGDI,
- LONG x, LONG y, ULONG iColor)
+BOOL EngLineTo(SURFOBJ *Surface, CLIPOBJ *Clip, BRUSHOBJ *Brush,
+ LONG x1, LONG y1, LONG x2, LONG y2,
+ RECTL *RectBounds, MIX mix)
{
- ULONG offset;
+ SURFGDI *SurfGDI;
+ LONG x, y, d, deltax, deltay, i, length, xchange, ychange, error, hx, vy;
- offset = (Surface->lDelta*y)+(x*SurfGDI->BytesPerPixel);
+ // These functions are assigned if we're working with a DIB
+ // The assigned functions depend on the bitsPerPixel of the DIB
+ PFN_DIB_PutPixel DIB_PutPixel;
+ PFN_DIB_HLine DIB_HLine;
+ PFN_DIB_VLine DIB_VLine;
- memcpy(Surface->pvBits+offset,
- &iColor, SurfGDI->BytesPerPixel);
-}
-
-BOOL EngHLine(SURFOBJ *Surface, SURFGDI *SurfGDI,
- LONG x, LONG y, LONG len, ULONG iColor)
-{
- ULONG offset, ix;
+ SurfGDI = AccessInternalObjectFromUserObject(Surface);
- offset = (Surface->lDelta*y)+(x*SurfGDI->BytesPerPixel);
+ if(Surface->iType!=STYPE_BITMAP)
+ {
+ // Call the driver's DrvLineTo
+ return SurfGDI->LineTo(Surface, Clip, Brush, x1, y1, x2, y2, RectBounds, mix);
+ }
- for(ix=0; ix<len*SurfGDI->BytesPerPixel; ix+=SurfGDI->BytesPerPixel)
- memcpy(Surface->pvBits+offset+ix,
- &iColor, SurfGDI->BytesPerPixel);
+ // Assign DIB functions according to bytes per pixel
+ switch(BitsPerFormat(Surface->iBitmapFormat))
+ {
+ case 4:
+ DIB_PutPixel = DIB_4BPP_PutPixel;
+ DIB_HLine = DIB_4BPP_HLine;
+ DIB_VLine = DIB_4BPP_VLine;
+ break;
+
+ case 24:
+ DIB_PutPixel = DIB_24BPP_PutPixel;
+ DIB_HLine = DIB_24BPP_HLine;
+ DIB_VLine = DIB_24BPP_VLine;
+ break;
+
+ default:
+ DbgPrint("EngLineTo: unsupported DIB format %u (bitsPerPixel:%u)\n", Surface->iBitmapFormat,
+ BitsPerFormat(Surface->iBitmapFormat));
+ return FALSE;
+ }
+
+ // FIXME: Implement clipping
+
+ x=x1;
+ y=y1;
+ deltax=x2-x1;
+ deltay=y2-y1;
+
+ if(deltax<0)
+ {
+ xchange=-1;
+ deltax=-deltax;
+ hx = x2;
+ } else
+ {
+ xchange=1;
+ hx = x1;
+ }
- return TRUE;
-}
+ if(deltay<0)
+ {
+ ychange=-1;
+ deltay=-deltay;
+ vy = y2;
+ } else
+ {
+ ychange=1;
+ vy = y1;
+ }
-BOOL EngLineTo(SURFOBJ *Surface, CLIPOBJ *Clip, BRUSHOBJ *Brush,
- LONG x1, LONG y1, LONG x2, LONG y2,
- RECTL *RectBounds, MIX mix)
-{
- SURFGDI *SurfGDI;
- LONG x, y, d, deltax, deltay, i, length, xchange, ychange, error;
-
- SurfGDI = AccessInternalObjectFromUserObject(Surface);
-
- if(Surface->iType!=STYPE_BITMAP)
- {
- // Call the driver's DrvLineTo
- return SurfGDI->LineTo(Surface, Clip, Brush, x1, y1, x2, y2,
- RectBounds, mix);
- }
-
- // FIXME: Implement clipping
-
- if(y1==y2) return EngHLine(Surface, SurfGDI, x1, y1, (x2-x1), Brush->iSolidColor);
-
- x=x1;
- y=y1;
- deltax=x2-x1;
- deltay=y2-y1;
-
- if(deltax<0)
- {
- xchange=-1;
- deltax=-deltax;
- } else
- {
- xchange=1;
- }
-
- if(deltay<0)
- {
- ychange=-1;
- deltay=-deltay;
- } else
- {
- ychange=1;
- };
+ if(y1==y2) { DIB_HLine(Surface, hx, hx + deltax, y1, Brush->iSolidColor); return TRUE; }
+ if(x1==x2) { DIB_VLine(Surface, x1, vy, vy + deltay, Brush->iSolidColor); return TRUE; }
error=0;
i=0;
if(deltax<deltay)
{
- length=deltay+1;
- while(i<length)
- {
- LinePoint(Surface, SurfGDI, x, y, Brush->iSolidColor);
- y=y+ychange;
- error=error+deltax;
-
- if(error>deltay)
- {
- x=x+xchange;
- error=error-deltay;
- }
- i=i+1;
- }
+ length=deltay+1;
+ while(i<length)
+ {
+ DIB_PutPixel(Surface, x, y, Brush->iSolidColor);
+ y=y+ychange;
+ error=error+deltax;
+
+ if(error>deltay)
+ {
+ x=x+xchange;
+ error=error-deltay;
+ }
+ i=i+1;
+ }
} else
{
length=deltax+1;
while(i<length)
{
- LinePoint(Surface, SurfGDI, x, y, Brush->iSolidColor);
- x=x+xchange;
- error=error+deltay;
- if(error>deltax)
- {
- y=y+ychange;
- error=error-deltax;
- }
- i=i+1;
+ DIB_PutPixel(Surface, x, y, Brush->iSolidColor);
+ x=x+xchange;
+ error=error+deltay;
+ if(error>deltax)
+ {
+ y=y+ychange;
+ error=error-deltax;
}
- }
+ i=i+1;
+ }
+ }
- return TRUE;
+ return TRUE;
}
PVOID STDCALL EngAllocMem(ULONG Flags, ULONG MemSize, ULONG Tag)
{
- PVOID newMem;
+ PVOID newMem;
- newMem = ExAllocatePoolWithTag(NonPagedPool, MemSize, Tag); // FIXME: Use PagedPool when it is implemented
+ newMem = ExAllocatePoolWithTag(NonPagedPool, MemSize, Tag); // FIXME: Use PagedPool when it is implemented
- if(Flags == FL_ZERO_MEMORY)
- {
- RtlZeroMemory(newMem, MemSize);
- }
+ if(Flags == FL_ZERO_MEMORY)
+ {
+ RtlZeroMemory(newMem, MemSize);
+ }
- return newMem;
+ return newMem;
}
VOID STDCALL EngFreeMem(PVOID Mem)
{
- ExFreePool(Mem);
+ ExFreePool(Mem);
}
PVOID STDCALL EngAllocUserMem(ULONG cj, ULONG tag)
{
-/* PVOID newMem;
+/* PVOID newMem;
- return ZwAllocateVirtualMemory(mycurrentprocess, newMem, 0, cj,
- MEM_COMMIT, PAGE_READWRITE); */
+ return ZwAllocateVirtualMemory(mycurrentprocess, newMem, 0, cj,
+ MEM_COMMIT, PAGE_READWRITE); */
- return NULL;
+ return NULL;
}
VOID STDCALL EngFreeUserMem(PVOID pv)
{
-/* ZwFreeVirtualMemory (mycurrentprocess, pv, 0, MEM_DECOMMIT); */
+/* ZwFreeVirtualMemory (mycurrentprocess, pv, 0, MEM_DECOMMIT); */
}
-
} BRUSHGDI;
typedef struct _CLIPGDI {
- ULONG NumRegionRects;
- ULONG NumIntersectRects;
- RECTL *RegionRects;
- RECTL *IntersectRects;
+ ULONG NumRegionRects;
+ ULONG NumIntersectRects;
+ RECTL *RegionRects;
+ RECTL *IntersectRects;
- ULONG EnumPos;
- ENUMRECTS EnumRects;
+ ULONG EnumPos;
+ ENUMRECTS EnumRects;
} CLIPGDI, *PCLIPGDI;
typedef struct _DRVFUNCTIONSGDI {
- HDEV hdev;
- DRVFN Functions[INDEX_LAST];
+ HDEV hdev;
+ DRVFN Functions[INDEX_LAST];
} DRVFUNCTIONSGDI;
typedef struct _FLOATGDI {
} FONTGDI;
typedef struct _PALGDI {
- ULONG Mode; // PAL_INDEXED, PAL_BITFIELDS, PAL_RGB, PAL_BGR
- ULONG NumColors;
- ULONG *IndexedColors;
- ULONG RedMask;
- ULONG GreenMask;
- ULONG BlueMask;
+ ULONG Mode; // PAL_INDEXED, PAL_BITFIELDS, PAL_RGB, PAL_BGR
+ ULONG NumColors;
+ ULONG *IndexedColors;
+ ULONG RedMask;
+ ULONG GreenMask;
+ ULONG BlueMask;
} PALGDI, *PPALGDI;
typedef struct _PATHGDI {
typedef HBITMAP (*PFN_CreateDeviceBitmap)(DHPDEV, SIZEL, ULONG);
+typedef BOOL (*PFN_SetPalette)(DHPDEV, PALOBJ*, ULONG, ULONG, ULONG);
+
typedef struct _SURFGDI {
- BYTE BytesPerPixel;
-
- PFN_BitBlt BitBlt;
- PFN_StretchBlt StretchBlt;
- PFN_TextOut TextOut;
- PFN_Paint Paint;
- PFN_StrokePath StrokePath;
- PFN_FillPath FillPath;
- PFN_StrokeAndFillPath StrokeAndFillPath;
- PFN_LineTo LineTo;
- PFN_CopyBits CopyBits;
- PFN_Synchronize Synchronize;
- BOOL SynchronizeAccess;
- PFN_CreateDeviceBitmap CreateDeviceBitmap;
+ INT BitsPerPixel;
+
+ PFN_BitBlt BitBlt;
+ PFN_StretchBlt StretchBlt;
+ PFN_TextOut TextOut;
+ PFN_Paint Paint;
+ PFN_StrokePath StrokePath;
+ PFN_FillPath FillPath;
+ PFN_StrokeAndFillPath StrokeAndFillPath;
+ PFN_LineTo LineTo;
+ PFN_CopyBits CopyBits;
+ PFN_Synchronize Synchronize;
+ BOOL SynchronizeAccess;
+ PFN_CreateDeviceBitmap CreateDeviceBitmap;
+ PFN_SetPalette SetPalette;
} SURFGDI, *PSURFGDI;
typedef struct _XFORMGDI {
} XFORMGDI;
typedef struct _XLATEGDI {
- HPALETTE DestPal;
- HPALETTE SourcePal;
+ HPALETTE DestPal;
+ HPALETTE SourcePal;
- ULONG *translationTable;
+ ULONG *translationTable;
} XLATEGDI;
// List of GDI objects
BOOL FillSolid(SURFOBJ *Surface, PRECTL Dimensions, ULONG iColor)
{
- ULONG x, y, LineWidth, leftOfBitmap;
- SURFGDI *SurfaceGDI;
+ ULONG x, y, LineWidth, leftOfBitmap;
+ SURFGDI *SurfaceGDI;
- SurfaceGDI = AccessInternalObjectFromUserObject(Surface);
- LineWidth = Dimensions->right - Dimensions->left;
+ SurfaceGDI = AccessInternalObjectFromUserObject(Surface);
+ LineWidth = Dimensions->right - Dimensions->left;
- for (y = Dimensions->top; y < Dimensions->bottom; y++)
- {
- EngHLine(Surface, SurfaceGDI, Dimensions->left, y, LineWidth, iColor);
- }
+ for (y = Dimensions->top; y < Dimensions->bottom; y++)
+ {
+// EngHLine(Surface, SurfaceGDI, Dimensions->left, y, LineWidth, iColor);
+ }
- return TRUE;
+ return TRUE;
}
BOOL EngPaintRgn(SURFOBJ *Surface, CLIPOBJ *ClipRegion, ULONG iColor, MIX Mix,
BRUSHINST *BrushInst, POINTL *BrushPoint)
{
- RECT_ENUM RectEnum;
- BOOL EnumMore;
+ RECT_ENUM RectEnum;
+ BOOL EnumMore;
- switch(ClipRegion->iMode) {
+ switch(ClipRegion->iMode) {
- case TC_RECTANGLES:
+ case TC_RECTANGLES:
- /* Rectangular clipping can be handled without enumeration.
- Note that trivial clipping is not possible, since the clipping
- region defines the area to fill */
+ /* Rectangular clipping can be handled without enumeration.
+ Note that trivial clipping is not possible, since the clipping
+ region defines the area to fill */
- if (ClipRegion->iDComplexity == DC_RECT)
- {
- FillSolid(Surface, &ClipRegion->rclBounds, iColor);
- } else {
+ if (ClipRegion->iDComplexity == DC_RECT)
+ {
+ FillSolid(Surface, &ClipRegion->rclBounds, iColor);
+ } else {
- /* Enumerate all the rectangles and draw them */
+ /* Enumerate all the rectangles and draw them */
+ CLIPOBJ_cEnumStart(ClipRegion, FALSE, CT_RECTANGLES, CD_ANY, ENUM_RECT_LIMIT);
- CLIPOBJ_cEnumStart(ClipRegion, FALSE, CT_RECTANGLES, CD_ANY,
- ENUM_RECT_LIMIT);
+ do {
+ EnumMore = CLIPOBJ_bEnum(ClipRegion, sizeof(RectEnum), (PVOID) &RectEnum);
+ FillSolid(Surface, &RectEnum.arcl[0], iColor);
+ } while (EnumMore);
+ }
- do {
- EnumMore = CLIPOBJ_bEnum(ClipRegion, sizeof(RectEnum), (PVOID) &RectEnum);
+ return(TRUE);
- FillSolid(Surface, &RectEnum.arcl[0], iColor);
-
- } while (EnumMore);
- }
-
- return(TRUE);
-
- default:
- return(FALSE);
- }
+ default:
+ return(FALSE);
+ }
}
BOOL EngPaint(IN SURFOBJ *Surface, IN CLIPOBJ *ClipRegion,
IN BRUSHOBJ *Brush, IN POINTL *BrushOrigin,
IN MIX Mix)
{
- SURFGDI *SurfGDI;
+ SURFGDI *SurfGDI;
- // Is the surface's Paint function hooked?
- SurfGDI = AccessInternalObjectFromUserObject(Surface);
+ // Is the surface's Paint function hooked?
+ SurfGDI = AccessInternalObjectFromUserObject(Surface);
- if((Surface->iType!=STYPE_BITMAP) && (SurfGDI->Paint!=NULL))
- {
- // Call the driver's DrvPaint
- return SurfGDI->Paint(Surface, ClipRegion, Brush, BrushOrigin, Mix);
- }
+ if((Surface->iType!=STYPE_BITMAP) && (SurfGDI->Paint!=NULL))
+ {
+ // Call the driver's DrvPaint
+ return SurfGDI->Paint(Surface, ClipRegion, Brush, BrushOrigin, Mix);
+ }
- // FIXME: We only support a brush's solid color attribute
- return(EngPaintRgn(Surface, ClipRegion, Brush->iSolidColor, Mix, NULL,
- BrushOrigin));
+ // FIXME: We only support a brush's solid color attribute
+ return(EngPaintRgn(Surface, ClipRegion, Brush->iSolidColor, Mix, NULL, BrushOrigin));
}
BOOL EngEraseSurface(SURFOBJ *Surface, RECTL *Rect, ULONG iColor)
{
- return FillSolid(Surface, Rect, iColor);
+ return FillSolid(Surface, Rect, iColor);
}
ULONG Green,
ULONG Blue)
{
- HPALETTE NewPalette;
- PALOBJ *PalObj;
- PALGDI *PalGDI;
-
- PalObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(PALOBJ), NULL);
- PalGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(PALGDI), NULL);
-
- NewPalette = CreateGDIHandle(PalGDI, PalObj);
-
- PalGDI->Mode = Mode;
-
- if(Mode==PAL_INDEXED)
- {
- PalGDI->NumColors = NumColors;
- PalGDI->IndexedColors = Colors;
- } else
- if(Mode==PAL_BITFIELDS)
- {
- PalGDI->RedMask = Red;
- PalGDI->GreenMask = Green;
- PalGDI->BlueMask = Blue;
- }
-
- return NewPalette;
+ HPALETTE NewPalette;
+ PALOBJ *PalObj;
+ PALGDI *PalGDI;
+
+ PalObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(PALOBJ), NULL);
+ PalGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(PALGDI), NULL);
+
+ NewPalette = CreateGDIHandle(PalGDI, PalObj);
+
+ PalGDI->Mode = Mode;
+
+ if(Colors != NULL)
+ {
+ PalGDI->IndexedColors = ExAllocatePool(NonPagedPool, sizeof(ULONG)*NumColors);
+ RtlCopyMemory(PalGDI->IndexedColors, Colors, sizeof(ULONG)*NumColors);
+ }
+
+ if(Mode==PAL_INDEXED)
+ {
+ PalGDI->NumColors = NumColors;
+ PalGDI->IndexedColors = Colors;
+ } else
+ if(Mode==PAL_BITFIELDS)
+ {
+ PalGDI->RedMask = Red;
+ PalGDI->GreenMask = Green;
+ PalGDI->BlueMask = Blue;
+ }
+
+ return NewPalette;
}
BOOL EngDeletePalette(IN HPALETTE Palette)
{
- PALOBJ *PalObj;
- PALGDI *PalGDI;
+ PALOBJ *PalObj;
+ PALGDI *PalGDI;
- PalGDI = AccessInternalObject(Palette);
- PalObj = AccessInternalObject(Palette);
+ PalGDI = AccessInternalObject(Palette);
+ PalObj = AccessInternalObject(Palette);
- EngFreeMem(PalGDI);
- EngFreeMem(PalObj);
- FreeGDIHandle(Palette);
+ EngFreeMem(PalGDI);
+ EngFreeMem(PalObj);
+ FreeGDIHandle(Palette);
- return TRUE;
+ return TRUE;
}
ULONG PALOBJ_cGetColors(PALOBJ *PalObj, ULONG Start, ULONG Colors,
ULONG *PaletteEntry)
{
- ULONG i, entry;
- PALGDI *PalGDI;
+ ULONG i, entry;
+ PALGDI *PalGDI;
- PalGDI = AccessInternalObjectFromUserObject(PalObj);
+ PalGDI = AccessInternalObjectFromUserObject(PalObj);
- for(i=Start; i<Colors; i++)
- {
- PaletteEntry[i] = PalGDI->IndexedColors[i];
- }
+ for(i=Start; i<Colors; i++)
+ {
+ PaletteEntry[i] = PalGDI->IndexedColors[i];
+ }
- return Colors;
+ return Colors;
}
* PROGRAMER: Jason Filby
* REVISION HISTORY:
* 3/7/1999: Created
+ * 9/11/2000: Updated to handle real pixel packed bitmaps (UPDATE TO DATE COMPLETED)
+ * TESTING TO BE DONE:
+ * - Create a GDI bitmap with all formats, perform all drawing operations on them, render to VGA surface
+ * refer to \test\microwin\src\engine\devdraw.c for info on correct pixel plotting for various formats
*/
#include <ddk/winddi.h>
#include <win32k/dc.h>
#include "objects.h"
-BYTE bytesPerPixel(ULONG Format)
+INT BitsPerFormat(ULONG Format)
{
- // FIXME: GDI bitmaps are supposed to be pixel-packed. Right now if the
- // pixel size if < 1 byte we expand it to 1 byte
-
- if(Format==BMF_1BPP)
- {
- return 1;
- } else
- if((Format==BMF_4BPP) || (Format==BMF_4RLE))
- {
- return 1;
- } else
- if((Format==BMF_8BPP) || (Format==BMF_8RLE))
- {
- return 1;
- } else
- if(Format==BMF_16BPP)
- {
- return 2;
- } else
- if(Format==BMF_24BPP)
- {
- return 3;
- } else
- if(Format==BMF_32BPP)
- {
- return 4;
- }
-
- return 0;
+ switch(Format)
+ {
+ case BMF_1BPP: return 1;
+ case BMF_4BPP:
+ case BMF_4RLE: return 4;
+ case BMF_8BPP:
+ case BMF_8RLE: return 8;
+ case BMF_16BPP: return 16;
+ case BMF_24BPP: return 24;
+ case BMF_32BPP: return 32;
+ default: return 0;
+ }
+}
+
+ULONG BitmapFormat(WORD Bits, DWORD Compression)
+{
+ switch(Compression)
+ {
+ case BI_RGB:
+ switch(Bits)
+ {
+ case 1: return BMF_1BPP;
+ case 4: return BMF_4BPP;
+ case 8: return BMF_8BPP;
+ case 16: return BMF_16BPP;
+ case 24: return BMF_24BPP;
+ case 32: return BMF_32BPP;
+ }
+
+ case BI_RLE4: return BMF_4RLE;
+ case BI_RLE8: return BMF_8RLE;
+
+ default: return 0;
+ }
}
VOID InitializeHooks(SURFGDI *SurfGDI)
{
- SurfGDI->BitBlt = NULL;
- SurfGDI->CopyBits = NULL;
- SurfGDI->CreateDeviceBitmap = NULL;
+ SurfGDI->BitBlt = NULL;
+ SurfGDI->CopyBits = NULL;
+ SurfGDI->CreateDeviceBitmap = NULL;
+ SurfGDI->SetPalette = NULL;
}
HBITMAP EngCreateDeviceBitmap(DHSURF dhsurf, SIZEL Size, ULONG Format)
{
- HBITMAP NewBitmap;
- SURFOBJ *SurfObj;
-
- NewBitmap = EngCreateBitmap(Size, bytesPerPixel(Format) * Size.cx, Format, 0, NULL);
- SurfObj = AccessUserObject(NewBitmap);
- SurfObj->dhpdev = dhsurf;
+ HBITMAP NewBitmap;
+ SURFOBJ *SurfObj;
- return NewBitmap;
+ NewBitmap = EngCreateBitmap(Size, DIB_GetDIBWidthBytes(Size.cx, BitsPerFormat(Format)), Format, 0, NULL);
+ SurfObj = (PVOID)AccessUserObject(NewBitmap);
+ SurfObj->dhpdev = dhsurf;
- return 0;
+ return NewBitmap;
}
HBITMAP EngCreateBitmap(IN SIZEL Size,
IN ULONG Flags,
IN PVOID Bits)
{
- HBITMAP NewBitmap;
- SURFOBJ *SurfObj;
- SURFGDI *SurfGDI;
-
- SurfObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFOBJ), NULL);
- SurfGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFGDI), NULL);
-
- NewBitmap = CreateGDIHandle(SurfGDI, SurfObj);
-
- InitializeHooks(SurfGDI);
- SurfGDI->BytesPerPixel = bytesPerPixel(Format);
-
- SurfObj->lDelta = ((bytesPerPixel(Format) * Width) + 31) & ~31; // round up 4 bytes
- SurfObj->cjBits = SurfObj->lDelta * Size.cy;
-
- if(Bits!=NULL)
- {
- SurfObj->pvBits = Bits;
- } else
- {
- if(Flags & BMF_USERMEM)
+ HBITMAP NewBitmap;
+ SURFOBJ *SurfObj;
+ SURFGDI *SurfGDI;
+
+ SurfObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFOBJ), 0);
+ SurfGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFGDI), 0);
+
+ NewBitmap = (PVOID)CreateGDIHandle(SurfGDI, SurfObj);
+
+ InitializeHooks(SurfGDI);
+ SurfGDI->BitsPerPixel = BitsPerFormat(Format);
+ SurfObj->lDelta = Width;
+ SurfObj->cjBits = SurfObj->lDelta * Size.cy;
+
+ if(Bits!=NULL)
+ {
+ SurfObj->pvBits = Bits;
+ } else
+ {
+ if(Flags & BMF_USERMEM)
+ {
+ SurfObj->pvBits = EngAllocUserMem(SurfObj->cjBits, 0);
+ } else {
+ if(Flags & BMF_NOZEROINIT)
{
- SurfObj->pvBits = EngAllocUserMem(SurfObj->cjBits, 0);
+ SurfObj->pvBits = EngAllocMem(0, SurfObj->cjBits, 0);
} else {
- if(Flags & BMF_NOZEROINIT)
- {
- SurfObj->pvBits = EngAllocMem(0, SurfObj->cjBits, 0);
- } else {
- SurfObj->pvBits = EngAllocMem(FL_ZERO_MEMORY, SurfObj->cjBits, 0);
- }
+ SurfObj->pvBits = EngAllocMem(FL_ZERO_MEMORY, SurfObj->cjBits, 0);
}
- }
+ }
+ }
- SurfObj->dhsurf = 0; // device managed surface
- SurfObj->hsurf = 0;
- SurfObj->sizlBitmap = Size;
- SurfObj->iBitmapFormat = Format;
- SurfObj->iType = STYPE_BITMAP;
+ SurfObj->dhsurf = 0; // device managed surface
+ SurfObj->hsurf = 0;
+ SurfObj->sizlBitmap = Size;
+ SurfObj->iBitmapFormat = Format;
+ SurfObj->iType = STYPE_BITMAP;
- // Use flags to determine bitmap type -- TOP_DOWN or whatever
+ // Use flags to determine bitmap type -- TOP_DOWN or whatever
- return NewBitmap;
+ return NewBitmap;
}
HSURF EngCreateDeviceSurface(DHSURF dhsurf, SIZEL Size, ULONG Format)
{
- HSURF NewSurface;
- SURFOBJ *SurfObj;
- SURFGDI *SurfGDI;
-
- SurfObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFOBJ), NULL);
- SurfGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFGDI), NULL);
+ HSURF NewSurface;
+ SURFOBJ *SurfObj;
+ SURFGDI *SurfGDI;
- NewSurface = CreateGDIHandle(SurfGDI, SurfObj);
+ SurfObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFOBJ), NULL);
+ SurfGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(SURFGDI), NULL);
- InitializeHooks(SurfGDI);
+ NewSurface = CreateGDIHandle(SurfGDI, SurfObj);
- SurfGDI->BytesPerPixel = bytesPerPixel(Format);
+ InitializeHooks(SurfGDI);
- SurfObj->dhsurf = dhsurf;
- SurfObj->hsurf = dhsurf; // FIXME: Is this correct??
- SurfObj->sizlBitmap = Size;
- SurfObj->iBitmapFormat = Format;
- SurfObj->lDelta = SurfGDI->BytesPerPixel * Size.cx;
- SurfObj->iType = STYPE_DEVICE;
+ SurfGDI->BitsPerPixel = BitsPerFormat(Format);
+ SurfObj->dhsurf = dhsurf;
+ SurfObj->hsurf = dhsurf; // FIXME: Is this correct??
+ SurfObj->sizlBitmap = Size;
+ SurfObj->iBitmapFormat = Format;
+ SurfObj->lDelta = DIB_GetDIBWidthBytes(Size.cx, BitsPerFormat(Format));
+ SurfObj->iType = STYPE_DEVICE;
- return NewSurface;
+ return NewSurface;
}
PFN DriverFunction(DRVENABLEDATA *DED, ULONG DriverFunc)
{
- ULONG i;
-
- for(i=0; i<DED->c; i++)
- {
- if(DED->pdrvfn[i].iFunc == DriverFunc)
- return DED->pdrvfn[i].pfn;
- }
- return NULL;
+ ULONG i;
+
+ for(i=0; i<DED->c; i++)
+ {
+ if(DED->pdrvfn[i].iFunc == DriverFunc)
+ return DED->pdrvfn[i].pfn;
+ }
+ return NULL;
}
BOOL EngAssociateSurface(HSURF Surface, HDEV Dev, ULONG Hooks)
{
- SURFOBJ *SurfObj;
- SURFGDI *SurfGDI;
-
-// it looks like this Dev is actually a pointer to the DC!
- PDC Dc = (PDC)Dev;
-DbgPrint("Associate 1\n");
-// DRVENABLEDATA *DED;
-
- SurfGDI = AccessInternalObject(Surface);
- SurfObj = AccessUserObject(Surface);
-
-// DED = AccessInternalObject(Dev);
-
- // Associate the hdev
- SurfObj->hdev = Dev;
-
- // Hook up specified functions
- if(Hooks & HOOK_BITBLT) SurfGDI->BitBlt = Dc->DriverFunctions.BitBlt;
- if(Hooks & HOOK_STRETCHBLT) SurfGDI->StretchBlt = Dc->DriverFunctions.StretchBlt;
- if(Hooks & HOOK_TEXTOUT) SurfGDI->TextOut = Dc->DriverFunctions.TextOut;
- if(Hooks & HOOK_PAINT) SurfGDI->Paint = Dc->DriverFunctions.Paint;
- if(Hooks & HOOK_STROKEPATH) SurfGDI->StrokePath = Dc->DriverFunctions.StrokePath;
- if(Hooks & HOOK_FILLPATH) SurfGDI->FillPath = Dc->DriverFunctions.FillPath;
- if(Hooks & HOOK_STROKEANDFILLPATH) SurfGDI->StrokeAndFillPath = Dc->DriverFunctions.StrokeAndFillPath;
- if(Hooks & HOOK_LINETO) SurfGDI->LineTo = Dc->DriverFunctions.LineTo;
- if(Hooks & HOOK_COPYBITS) SurfGDI->CopyBits = Dc->DriverFunctions.CopyBits;
- if(Hooks & HOOK_SYNCHRONIZE) SurfGDI->Synchronize = Dc->DriverFunctions.Synchronize;
- if(Hooks & HOOK_SYNCHRONIZEACCESS) SurfGDI->SynchronizeAccess = TRUE;
-
- SurfGDI->CreateDeviceBitmap = Dc->DriverFunctions.CreateDeviceBitmap;
-
- return TRUE;
+ SURFOBJ *SurfObj;
+ SURFGDI *SurfGDI;
+
+ PDC Dc = (PDC)Dev;
+
+ SurfGDI = (PVOID)AccessInternalObject(Surface);
+ SurfObj = (PVOID)AccessUserObject(Surface);
+
+ // Associate the hdev
+ SurfObj->hdev = Dev;
+
+ // Hook up specified functions
+ if(Hooks & HOOK_BITBLT) SurfGDI->BitBlt = Dc->DriverFunctions.BitBlt;
+ if(Hooks & HOOK_STRETCHBLT) SurfGDI->StretchBlt = Dc->DriverFunctions.StretchBlt;
+ if(Hooks & HOOK_TEXTOUT) SurfGDI->TextOut = Dc->DriverFunctions.TextOut;
+ if(Hooks & HOOK_PAINT) SurfGDI->Paint = Dc->DriverFunctions.Paint;
+ if(Hooks & HOOK_STROKEPATH) SurfGDI->StrokePath = Dc->DriverFunctions.StrokePath;
+ if(Hooks & HOOK_FILLPATH) SurfGDI->FillPath = Dc->DriverFunctions.FillPath;
+ if(Hooks & HOOK_STROKEANDFILLPATH) SurfGDI->StrokeAndFillPath = Dc->DriverFunctions.StrokeAndFillPath;
+ if(Hooks & HOOK_LINETO) SurfGDI->LineTo = Dc->DriverFunctions.LineTo;
+ if(Hooks & HOOK_COPYBITS) SurfGDI->CopyBits = Dc->DriverFunctions.CopyBits;
+ if(Hooks & HOOK_SYNCHRONIZE) SurfGDI->Synchronize = Dc->DriverFunctions.Synchronize;
+ if(Hooks & HOOK_SYNCHRONIZEACCESS) SurfGDI->SynchronizeAccess = TRUE;
+
+ SurfGDI->CreateDeviceBitmap = Dc->DriverFunctions.CreateDeviceBitmap;
+ SurfGDI->SetPalette = Dc->DriverFunctions.SetPalette;
+
+ return TRUE;
}
BOOL EngDeleteSurface(HSURF Surface)
{
- SURFOBJ *SurfObj;
- SURFGDI *SurfGDI;
+ SURFOBJ *SurfObj;
+ SURFGDI *SurfGDI;
- SurfGDI = AccessInternalObject(Surface);
- SurfObj = AccessUserObject(Surface);
+ SurfGDI = AccessInternalObject(Surface);
+ SurfObj = AccessUserObject(Surface);
- EngFreeMem(SurfGDI);
- EngFreeMem(SurfObj);
- FreeGDIHandle(Surface);
+ EngFreeMem(SurfGDI);
+ EngFreeMem(SurfObj);
+ FreeGDIHandle(Surface);
- return TRUE;
+ return TRUE;
}
SURFOBJ *EngLockSurface(HSURF Surface)
{
- // FIXME: Call GDI_LockObject (see subsys/win32k/objects/gdi.c)
-
- return AccessUserObject(Surface);
+ // FIXME: Call GDI_LockObject (see subsys/win32k/objects/gdi.c)
+ return AccessUserObject(Surface);
}
ULONG RGBtoULONG(BYTE Red, BYTE Green, BYTE Blue)
{
- return ((Red & 0xff) << 16) | ((Green & 0xff) << 8) | (Blue & 0xff);
+ return ((Red & 0xff) << 16) | ((Green & 0xff) << 8) | (Blue & 0xff);
}
ULONG BGRtoULONG(BYTE Blue, BYTE Green, BYTE Red)
{
- return ((Blue & 0xff) << 16) | ((Green & 0xff) << 8) | (Red & 0xff);
+ return ((Blue & 0xff) << 16) | ((Green & 0xff) << 8) | (Red & 0xff);
}
INT abs(INT nm)
{
- if(nm<0)
- {
- return nm * -1;
- } else
- {
- return nm;
- }
+ if(nm<0)
+ {
+ return nm * -1;
+ } else
+ {
+ return nm;
+ }
}
// FIXME: If the caller knows that the destinations are indexed and not RGB
// then we should cache more than one value. Same with the source.
+// Takes indexed palette and a
ULONG ClosestColorMatch(ULONG SourceColor, ULONG *DestColors,
ULONG NumColors)
{
- PVIDEO_CLUTDATA cSourceColor;
- PVIDEO_CLUTDATA cDestColors;
- ULONG bestMatch = 256, idx = 0, i;
- ULONG rt;
+ PVIDEO_CLUTDATA cSourceColor;
+ PVIDEO_CLUTDATA cDestColors;
+ ULONG bestMatch = 256, idx = 0, i;
+ ULONG rt;
- // Simple cache -- only one value because we don't want to waste time
- // if the colors aren't very sequential
+ // Simple cache -- only one value because we don't want to waste time
+ // if the colors aren't very sequential
- if(SourceColor == CCMLastSourceColor)
- {
- return CCMLastColorMatch;
- }
+ if(SourceColor == CCMLastSourceColor)
+ {
+ return CCMLastColorMatch;
+ }
- cSourceColor = &SourceColor;
+ cSourceColor = &SourceColor;
- for (i=0; i<NumColors; i++)
- {
- cDestColors = &DestColors[i];
+ for (i=0; i<NumColors; i++)
+ {
+ cDestColors = &DestColors[i];
- rt = ( abs(cSourceColor->Red - cDestColors->Red) +
- abs(cSourceColor->Green - cDestColors->Green) +
- abs(cSourceColor->Blue - cDestColors->Blue) ) / 3;
+ rt = ( abs(cSourceColor->Red - cDestColors->Red) +
+ abs(cSourceColor->Green - cDestColors->Green) +
+ abs(cSourceColor->Blue - cDestColors->Blue) ) / 3;
- if(rt<=bestMatch)
- {
- idx = i;
- bestMatch = rt;
- }
- }
+ if(rt<=bestMatch)
+ {
+ idx = i;
+ bestMatch = rt;
+ }
+ }
- CCMLastSourceColor = SourceColor;
- CCMLastColorMatch = idx;
+ CCMLastSourceColor = SourceColor;
+ CCMLastColorMatch = idx;
- return idx;
+ return idx;
}
VOID IndexedToIndexedTranslationTable(ULONG *TranslationTable,
PALGDI *PalDest, PALGDI *PalSource)
{
- ULONG i;
+ ULONG i;
- for(i=0; i<PalSource->NumColors; i++)
- {
- TranslationTable[i] = ClosestColorMatch(PalSource->IndexedColors[i],
- PalDest->IndexedColors, PalDest->NumColors);
- }
+ for(i=0; i<PalSource->NumColors; i++)
+ {
+ TranslationTable[i] = ClosestColorMatch(PalSource->IndexedColors[i], PalDest->IndexedColors, PalDest->NumColors);
+ }
}
XLATEOBJ *EngCreateXlate(USHORT DestPalType, USHORT SourcePalType,
HPALETTE PaletteDest, HPALETTE PaletteSource)
{
- // FIXME: Add support for BGR conversions
-
- HPALETTE NewXlate;
- XLATEOBJ *XlateObj;
- XLATEGDI *XlateGDI;
- PALGDI *SourcePalGDI, *DestPalGDI;
- ULONG IndexedColors;
-
- XlateObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(XLATEOBJ), NULL);
- XlateGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(XLATEGDI), NULL);
-
- NewXlate = CreateGDIHandle(XlateGDI, XlateObj);
-
- if(SourcePalType == PAL_INDEXED)
- {
- SourcePalGDI = AccessInternalObject(PaletteSource);
- } else
- if(DestPalType == PAL_INDEXED)
- {
- DestPalGDI = AccessInternalObject(PaletteDest);
- }
-
- XlateObj->iSrcType = SourcePalType;
- XlateObj->iDstType = DestPalType;
-
- // Store handles of palettes in internal Xlate GDI object (or NULLs)
- XlateGDI->DestPal = PaletteDest;
- XlateGDI->SourcePal = PaletteSource;
-
- XlateObj->flXlate = 0;
-
- // If source and destination palettes are the same or if they're RGB/BGR
- if( (PaletteDest == PaletteSource) ||
- ((DestPalType == PAL_RGB) && (SourcePalType == PAL_RGB)) ||
- ((DestPalType == PAL_BGR) && (SourcePalType == PAL_BGR)) )
- {
- XlateObj->flXlate |= XO_TRIVIAL;
- }
-
- // Prepare the translation table
- if( (SourcePalType == PAL_INDEXED) || (SourcePalType == PAL_RGB) )
- {
- XlateObj->flXlate |= XO_TABLE;
-
- if (SourcePalType == PAL_INDEXED) IndexedColors = SourcePalGDI->NumColors;
- if (DestPalType == PAL_INDEXED) IndexedColors = DestPalGDI->NumColors;
-
- XlateGDI->translationTable = EngAllocMem(
- FL_ZERO_MEMORY, sizeof(ULONG)*IndexedColors, NULL);
- }
-
- // Source palette is indexed
- if(XlateObj->iSrcType == PAL_INDEXED)
- {
- if(XlateObj->iDstType == PAL_INDEXED)
- {
- // Converting from indexed to indexed
- IndexedToIndexedTranslationTable(XlateGDI->translationTable,
- DestPalGDI, SourcePalGDI);
- } else
+ // FIXME: Add support for BGR conversions
+
+ HPALETTE NewXlate;
+ XLATEOBJ *XlateObj;
+ XLATEGDI *XlateGDI;
+ PALGDI *SourcePalGDI, *DestPalGDI;
+ ULONG IndexedColors;
+
+ XlateObj = EngAllocMem(FL_ZERO_MEMORY, sizeof(XLATEOBJ), NULL);
+ XlateGDI = EngAllocMem(FL_ZERO_MEMORY, sizeof(XLATEGDI), NULL);
+
+ NewXlate = CreateGDIHandle(XlateGDI, XlateObj);
+
+ if(SourcePalType == PAL_INDEXED)
+ {
+ SourcePalGDI = AccessInternalObject(PaletteSource);
+ } else
+ if(DestPalType == PAL_INDEXED)
+ {
+ DestPalGDI = AccessInternalObject(PaletteDest);
+ }
+
+ XlateObj->iSrcType = SourcePalType;
+ XlateObj->iDstType = DestPalType;
+
+ // Store handles of palettes in internal Xlate GDI object (or NULLs)
+ XlateGDI->DestPal = PaletteDest;
+ XlateGDI->SourcePal = PaletteSource;
+
+ XlateObj->flXlate = 0;
+
+ // If source and destination palettes are the same or if they're RGB/BGR
+ if( (PaletteDest == PaletteSource) ||
+ ((DestPalType == PAL_RGB) && (SourcePalType == PAL_RGB)) ||
+ ((DestPalType == PAL_BGR) && (SourcePalType == PAL_BGR)) )
+ {
+ XlateObj->flXlate |= XO_TRIVIAL;
+ return XlateObj;
+ }
+
+ // Prepare the translation table
+ if( (SourcePalType == PAL_INDEXED) || (SourcePalType == PAL_RGB) )
+ {
+ XlateObj->flXlate |= XO_TABLE;
+
+ if (SourcePalType == PAL_INDEXED) IndexedColors = SourcePalGDI->NumColors;
+ if (DestPalType == PAL_INDEXED) IndexedColors = DestPalGDI->NumColors;
+
+ XlateGDI->translationTable = EngAllocMem(FL_ZERO_MEMORY, sizeof(ULONG)*IndexedColors, NULL);
+ }
+
+ // Source palette is indexed
+ if(XlateObj->iSrcType == PAL_INDEXED)
+ {
+ if(XlateObj->iDstType == PAL_INDEXED)
+ {
+ // Converting from indexed to indexed
+ IndexedToIndexedTranslationTable(XlateGDI->translationTable, DestPalGDI, SourcePalGDI);
+ } else
if(XlateObj->iDstType == PAL_RGB)
{
- // FIXME: Is this necessary? I think the driver has to call this
- // function anyways if pulXlate is NULL and Source is PAL_INDEXED
+ // FIXME: Is this necessary? I think the driver has to call this
+ // function anyways if pulXlate is NULL and Source is PAL_INDEXED
- // Converting from indexed to RGB
+ // Converting from indexed to RGB
- XLATEOBJ_cGetPalette(XlateObj, XO_SRCPALETTE,
- SourcePalGDI->NumColors,
- XlateGDI->translationTable);
+ XLATEOBJ_cGetPalette(XlateObj, XO_SRCPALETTE,
+ SourcePalGDI->NumColors,
+ XlateGDI->translationTable);
}
- XlateObj->pulXlate = XlateGDI->translationTable;
- }
+ XlateObj->pulXlate = XlateGDI->translationTable;
+ }
- // Source palette is RGB
- if(XlateObj->iSrcType == PAL_RGB)
- {
- if(XlateObj->iDstType == PAL_INDEXED)
- {
- // FIXME: Is this necessary? I think the driver has to call this
- // function anyways if pulXlate is NULL and Dest is PAL_INDEXED
-
- // Converting from RGB to indexed
- XLATEOBJ_cGetPalette(XlateObj, XO_DESTPALETTE,
- DestPalGDI->NumColors,
- XlateGDI->translationTable);
- }
- }
+ // Source palette is RGB
+ if(XlateObj->iSrcType == PAL_RGB)
+ {
+ if(XlateObj->iDstType == PAL_INDEXED)
+ {
+ // FIXME: Is this necessary? I think the driver has to call this
+ // function anyways if pulXlate is NULL and Dest is PAL_INDEXED
- // FIXME: Add support for XO_TO_MONO
+ // Converting from RGB to indexed
+ XLATEOBJ_cGetPalette(XlateObj, XO_DESTPALETTE, DestPalGDI->NumColors, XlateGDI->translationTable);
+ }
+ }
- return XlateObj;
+ // FIXME: Add support for XO_TO_MONO
+ return XlateObj;
}
EngDeleteXlate(XLATEOBJ *XlateObj)
{
- HPALETTE HXlate = AccessHandleFromUserObject(XlateObj);
- XLATEGDI *XlateGDI = AccessInternalObject(HXlate);
+ HPALETTE HXlate = AccessHandleFromUserObject(XlateObj);
+ XLATEGDI *XlateGDI = AccessInternalObject(HXlate);
- if(XlateGDI->translationTable!=NULL)
- {
- EngFreeMem(XlateGDI->translationTable);
- }
+ if(XlateGDI->translationTable!=NULL)
+ {
+ EngFreeMem(XlateGDI->translationTable);
+ }
- EngFreeMem(XlateGDI);
- EngFreeMem(XlateObj);
- FreeGDIHandle(HXlate);
+ EngFreeMem(XlateGDI);
+ EngFreeMem(XlateObj);
+ FreeGDIHandle(HXlate);
}
ULONG *XLATEOBJ_piVector(XLATEOBJ *XlateObj)
{
- XLATEGDI *XlateGDI = AccessInternalObjectFromUserObject(XlateObj);
+ XLATEGDI *XlateGDI = AccessInternalObjectFromUserObject(XlateObj);
+ if(XlateObj->iSrcType == PAL_INDEXED)
+ {
+ return XlateGDI->translationTable;
+ }
- if(XlateObj->iSrcType == PAL_INDEXED)
- {
- return XlateGDI->translationTable;
- }
-
- return NULL;
+ return NULL;
}
ULONG XLATEOBJ_iXlate(XLATEOBJ *XlateObj, ULONG Color)
{
- PALGDI *PalGDI;
- XLATEGDI *XlateGDI = AccessInternalObjectFromUserObject(XlateObj);
-
- if(XlateObj->iSrcType == PAL_RGB)
- {
- // FIXME: should we cache colors used often?
- // FIXME: won't work if destination isn't indexed
-
- // Extract the destination palette
- PalGDI = AccessInternalObject(XlateGDI->DestPal);
-
- // Return closest match for the given RGB color
- return ClosestColorMatch(Color, PalGDI->IndexedColors, PalGDI->NumColors);
- } else
-
- if(XlateObj->iSrcType == PAL_INDEXED)
- {
- return XlateGDI->translationTable[Color];
- }
-
- return 0;
+ PALGDI *PalGDI;
+ XLATEGDI *XlateGDI = AccessInternalObjectFromUserObject(XlateObj);
+
+ if(XlateObj->flXlate & XO_TRIVIAL)
+ {
+ return Color;
+ } else
+ if(XlateObj->iSrcType == PAL_RGB)
+ {
+ // FIXME: should we cache colors used often?
+ // FIXME: won't work if destination isn't indexed
+
+ // Extract the destination palette
+ PalGDI = AccessInternalObject(XlateGDI->DestPal);
+
+ // Return closest match for the given RGB color
+ return ClosestColorMatch(Color, PalGDI->IndexedColors, PalGDI->NumColors);
+ } else
+ if(XlateObj->iSrcType == PAL_INDEXED)
+ {
+ return XlateGDI->translationTable[Color];
+ }
+
+ return 0;
}
ULONG XLATEOBJ_cGetPalette(XLATEOBJ *XlateObj,
ULONG PalOutType, ULONG cPal, ULONG *OutPal)
{
- ULONG i;
- HPALETTE HPal;
- XLATEGDI *XlateGDI;
- PALGDI *PalGDI;
-
- XlateGDI = AccessInternalObjectFromUserObject(XlateObj);
-
- if(PalOutType == XO_SRCPALETTE)
- {
- HPal = XlateGDI->SourcePal;
- } else
- if(PalOutType == XO_DESTPALETTE)
- {
- HPal = XlateGDI->DestPal;
- }
-
- PalGDI = AccessInternalObject(HPal);
- RtlCopyMemory(OutPal, PalGDI->IndexedColors, sizeof(ULONG)*cPal);
-
- return i;
+ ULONG i;
+ HPALETTE HPal;
+ XLATEGDI *XlateGDI;
+ PALGDI *PalGDI;
+
+ XlateGDI = AccessInternalObjectFromUserObject(XlateObj);
+
+ if(PalOutType == XO_SRCPALETTE)
+ {
+ HPal = XlateGDI->SourcePal;
+ } else
+ if(PalOutType == XO_DESTPALETTE)
+ {
+ HPal = XlateGDI->DestPal;
+ }
+
+ PalGDI = AccessInternalObject(HPal);
+ RtlCopyMemory(OutPal, PalGDI->IndexedColors, sizeof(ULONG)*cPal);
+
+ return i;
}
surfgdi = ExAllocatePool(NonPagedPool, sizeof(SURFGDI));
hCharCellBitmap = W32kCreateBitmap(8, 8, 1, 8, NULL); // 8x8, 1 plane, 8 bits per pel
+
pbo = BITMAPOBJ_HandleToPtr(hCharCellBitmap);
- BitmapToSurf(surfgdi, CharCellSurfObj, pbo); // Make the bitmap a surface
+// VOID BitmapToSurf(HDC hdc, PSURFGDI SurfGDI, PSURFOBJ SurfObj, PBITMAPOBJ Bitmap)
+ BitmapToSurf(0, surfgdi, CharCellSurfObj, pbo); // Make the bitmap a surface
}
void grWriteCellChar(PSURFOBJ target,
-/* $Id: loader.c,v 1.5 2000/08/26 16:21:28 ekohl Exp $
+/* $Id: loader.c,v 1.6 2001/03/31 15:35:07 jfilby Exp $
*
*/
#include <ddk/ntddk.h>
#include <ddk/winddi.h>
-
HANDLE
STDCALL
EngLoadImage (LPWSTR DriverName)
{
- SYSTEM_GDI_DRIVER_INFORMATION GdiDriverInfo;
- NTSTATUS Status;
-
- RtlInitUnicodeString (&GdiDriverInfo.DriverName,
- DriverName);
- Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation,
- &GdiDriverInfo,
- sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
- if (!NT_SUCCESS(Status))
- return NULL;
-
- return (HANDLE)GdiDriverInfo.ImageAddress;
+ SYSTEM_GDI_DRIVER_INFORMATION GdiDriverInfo;
+ NTSTATUS Status;
+
+ RtlInitUnicodeString(&GdiDriverInfo.DriverName, DriverName);
+ Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation, &GdiDriverInfo, sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
+ if (!NT_SUCCESS(Status)) return NULL;
+
+ return (HANDLE)GdiDriverInfo.ImageAddress;
}
STDCALL
EngLoadModule(LPWSTR ModuleName)
{
- SYSTEM_GDI_DRIVER_INFORMATION GdiDriverInfo;
- NTSTATUS Status;
+ SYSTEM_GDI_DRIVER_INFORMATION GdiDriverInfo;
+ NTSTATUS Status;
- // FIXME: should load as readonly
+ // FIXME: should load as readonly
- RtlInitUnicodeString (&GdiDriverInfo.DriverName,
- ModuleName);
- Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation,
- &GdiDriverInfo,
- sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
- if (!NT_SUCCESS(Status))
- return NULL;
+ RtlInitUnicodeString (&GdiDriverInfo.DriverName, ModuleName);
+ Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation, &GdiDriverInfo, sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
+ if (!NT_SUCCESS(Status)) return NULL;
- return (HANDLE)GdiDriverInfo.ImageAddress;
+ return (HANDLE)GdiDriverInfo.ImageAddress;
}
/* EOF */
-/* $Id: dllmain.c,v 1.17 2000/09/08 19:39:31 ekohl Exp $
+/* $Id: dllmain.c,v 1.18 2001/03/31 15:35:08 jfilby Exp $
*
* Entry Point for win32k.sys
*/
NTSTATUS
STDCALL
DllMain (
- IN PDRIVER_OBJECT DriverObject,
- IN PUNICODE_STRING RegistryPath
- )
+ IN PDRIVER_OBJECT DriverObject,
+ IN PUNICODE_STRING RegistryPath)
{
- BOOLEAN Result;
+ BOOLEAN Result;
- DbgPrint("Win32 kernel mode driver\n");
+ DbgPrint("Win32 kernel mode driver\n");
- /*
- * Register user mode call interface
- * (system service table index = 1)
- */
- Result = KeAddSystemServiceTable (Win32kSSDT,
- NULL,
- NUMBER_OF_SYSCALLS,
- Win32kSSPT,
- 1);
- if (Result == FALSE)
- {
- DbgPrint("Adding system services failed!\n");
- return STATUS_UNSUCCESSFUL;
- }
+ /*
+ * Register user mode call interface
+ * (system service table index = 1)
+ */
+ Result = KeAddSystemServiceTable (Win32kSSDT, NULL, NUMBER_OF_SYSCALLS, Win32kSSPT, 1);
+ if (Result == FALSE)
+ {
+ DbgPrint("Adding system services failed!\n");
+ return STATUS_UNSUCCESSFUL;
+ }
- DbgPrint("System services added successfully!\n");
- return STATUS_SUCCESS;
+ DbgPrint("System services added successfully!\n");
+ return STATUS_SUCCESS;
}
STDCALL
W32kInitialize (VOID)
{
+ // FIXME: Retrieve name from registry
+ EngLoadImage(L"\\SystemRoot\\system32\\drivers\\vidport.sys");
- // FIXME: Retrieve name from registry
- EngLoadImage(L"\\SystemRoot\\system32\\drivers\\vidport.sys");
+ // Create surface used to draw the internal font onto
+ CreateCellCharSurface();
- // Create surface used to draw the internal font onto
- CreateCellCharSurface();
+ // Create stock objects, ie. precreated objects commonly used by win32 applications
+ CreateStockObjects();
- return TRUE;
+ // Initialize FreeType library
+ if(!InitFontSupport()) return FALSE;
+
+ return TRUE;
}
/* EOF */
-# $Id: makefile,v 1.27 2000/11/20 19:59:14 ekohl Exp $
+# $Id: makefile,v 1.28 2001/03/31 15:35:07 jfilby Exp $
#
# WIN32K.SYS build spec
#
TARGET=win32k
+# from atheos appserver makefile
+COPTS = -pipe -O3 -I./freetype2-beta8/include -c -Wall
+
CFLAGS = -I.
+#define FT_FLAT_COMPILE
+
ENG_OBJECTS= eng/debug.o eng/mem.o eng/brush.o eng/bitblt.o eng/clip.o eng/copybits.o \
eng/device.o eng/handle.o eng/lineto.o eng/paint.o eng/palette.o \
eng/surface.o eng/xlate.o
objects/line.o objects/metafile.o objects/paint.o \
objects/path.o objects/pen.o objects/print.o \
objects/region.o objects/text.o objects/wingl.o \
- objects/bezier.o objects/objconv.o
-FREETYPE_OBJECTS = freetype/grfont.o
-
+ objects/bezier.o objects/objconv.o objects/dib.o objects/palette.o
+DIB_OBJECTS = dib/dib4bpp.o dib/dib24bpp.o
+FREETYPE_OBJECTS = freetype/grfont.o freetype/ctype.o \
+ freetype/ftsystem.o freetype/ftdebug.o freetype/ftinit.o freetype/ftbase.o \
+ freetype/ftglyph.o freetype/ftmm.o freetype/autohint.o freetype/cff.o \
+ freetype/type1cid.o freetype/psnames.o freetype/raster1.o freetype/sfnt.o \
+ freetype/smooth.o freetype/truetype.o freetype/winfnt.o freetype/type1z.o
RESOURCE_OBJECT = $(TARGET).coff
STUBS_OBJECTS = stubs/stubs.o
OBJECTS = $(ENG_OBJECTS) $(MAIN_OBJECTS) $(MISC_OBJECTS) $(LDR_OBJECTS) $(OBJECTS_OBJECTS) \
- $(RESOURCE_OBJECT) $(STUBS_OBJECTS) $(MATH_OBJECTS) $(FLOAT_OBJECTS) $(FREETYPE_OBJECTS)
+ $(RESOURCE_OBJECT) $(STUBS_OBJECTS) $(MATH_OBJECTS) $(FLOAT_OBJECTS) $(FREETYPE_OBJECTS) \
+ $(DIB_OBJECTS)
all: $(TARGET).sys
#WIN32_LEAN_AND_MEAN = yes
#WARNINGS_ARE_ERRORS = yes
include ../../rules.mak
-
-/* $Id: driver.c,v 1.15 2000/08/26 16:22:04 ekohl Exp $
+/* $Id: driver.c,v 1.16 2001/03/31 15:35:08 jfilby Exp $
*
* GDI Driver support routines
* (mostly swiped from Wine)
{
PGRAPHICS_DRIVER Driver = ExAllocatePool(NonPagedPool, sizeof(*Driver));
DPRINT( "DRIVER_RegisterDriver( Name: %S )\n", Name );
- if (!Driver)
- {
- return FALSE;
- }
+ if (!Driver) return FALSE;
Driver->ReferenceCount = 0;
Driver->EnableDriver = EnableDriver;
if (Name)
- {
- Driver->Name = ExAllocatePool(PagedPool,
- (wcslen(Name) + 1) * sizeof(WCHAR));
- wcscpy(Driver->Name, Name);
- Driver->Next = DriverList;
- DriverList = Driver;
- return TRUE;
- }
+ {
+ Driver->Name = ExAllocatePool(PagedPool, (wcslen(Name) + 1) * sizeof(WCHAR));
+ wcscpy(Driver->Name, Name);
+ Driver->Next = DriverList;
+ DriverList = Driver;
+ return TRUE;
+ }
if (GenericDriver != NULL)
- {
- ExFreePool(Driver);
-
- return FALSE;
- }
+ {
+ ExFreePool(Driver);
+ return FALSE;
+ }
GenericDriver = Driver;
return TRUE;
/* First see if the driver hasn't already been loaded */
while (Driver && Name)
+ {
+ if (!_wcsicmp( Driver->Name, Name))
{
- if (!_wcsicmp( Driver->Name, Name))
- {
- return Driver->EnableDriver;
- }
- Driver = Driver->Next;
+ return Driver->EnableDriver;
}
+ Driver = Driver->Next;
+ }
/* If not, then load it */
- RtlInitUnicodeString (&GdiDriverInfo.DriverName,
- (LPWSTR)Name);
- Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation,
- &GdiDriverInfo,
- sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
- if (!NT_SUCCESS(Status))
- return NULL;
+ RtlInitUnicodeString (&GdiDriverInfo.DriverName, (LPWSTR)Name);
+ Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation, &GdiDriverInfo, sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
+ if (!NT_SUCCESS(Status)) return NULL;
DRIVER_RegisterDriver( L"DISPLAY", GdiDriverInfo.EntryPoint);
return (PGD_ENABLEDRIVER)GdiDriverInfo.EntryPoint;
PMP_DRIVERENTRY PMP_DriverEntry;
/* Phase 1 */
- RtlInitUnicodeString (&GdiDriverInfo.DriverName,
- L"\\SystemRoot\\system32\\drivers\\vgamp.sys");
- Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation,
- &GdiDriverInfo,
- sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
+ RtlInitUnicodeString (&GdiDriverInfo.DriverName, L"\\SystemRoot\\system32\\drivers\\vgamp.sys");
+ Status = ZwSetSystemInformation (SystemLoadGdiDriverInformation, &GdiDriverInfo, sizeof(SYSTEM_GDI_DRIVER_INFORMATION));
if (!NT_SUCCESS(Status))
return NULL;
/* Phase 2 */
if (Name[0] != '\\')
+ {
+ lName = ExAllocatePool(NonPagedPool, wcslen(Name) * sizeof(WCHAR) + 10 * sizeof(WCHAR));
+ wcscpy(lName, L"\\??\\");
+ if (!wcscmp (Name, L"DISPLAY"))
{
- lName = ExAllocatePool(NonPagedPool, wcslen(Name) * sizeof(WCHAR) +
- 10 * sizeof(WCHAR));
- wcscpy(lName, L"\\??\\");
- if (!wcscmp (Name, L"DISPLAY"))
- {
- /* FIXME: Read this information from the registry ??? */
- wcscat(lName, L"DISPLAY1");
- }
- else
- {
- wcscat(lName, Name);
- }
+ /* FIXME: Read this information from the registry ??? */
+ wcscat(lName, L"DISPLAY1");
}
- else
+ else
{
- lName = ExAllocatePool(NonPagedPool, wcslen(Name) * sizeof(WCHAR));
- wcscpy(lName, Name);
+ wcscat(lName, Name);
}
+ }
+ else
+ {
+ lName = ExAllocatePool(NonPagedPool, wcslen(Name) * sizeof(WCHAR));
+ wcscpy(lName, Name);
+ }
/* Phase 3 */
DriverObject = ExAllocatePool(NonPagedPool,sizeof(DRIVER_OBJECT));
PGRAPHICS_DRIVER Driver = NULL;
if (Name)
+ {
+ if (DriverList != NULL)
{
- if (DriverList != NULL)
+ if (!_wcsicmp(DriverList->Name, Name))
+ {
+ Driver = DriverList;
+ DriverList = DriverList->Next;
+ }
+ else
+ {
+ Driver = DriverList;
+ while (Driver->Next && _wcsicmp(Driver->Name, Name))
{
- if (!_wcsicmp(DriverList->Name, Name))
- {
- Driver = DriverList;
- DriverList = DriverList->Next;
- }
- else
- {
- Driver = DriverList;
- while (Driver->Next && _wcsicmp(Driver->Name, Name))
- {
- Driver = Driver->Next;
- }
- }
+ Driver = Driver->Next;
}
+ }
}
+ }
else
- {
- if (GenericDriver != NULL)
- {
- Driver = GenericDriver;
- GenericDriver = NULL;
- }
+ {
+ if (GenericDriver != NULL)
+ {
+ Driver = GenericDriver;
+ GenericDriver = NULL;
}
+ }
if (Driver != NULL)
- {
- ExFreePool(Driver->Name);
- ExFreePool(Driver);
+ {
+ ExFreePool(Driver->Name);
+ ExFreePool(Driver);
- return TRUE;
- }
+ return TRUE;
+ }
else
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
}
INT DRIVER_ReferenceDriver (LPCWSTR Name)
GRAPHICS_DRIVER *Driver = DriverList;
while (Driver && Name)
+ {
+ DPRINT( "Comparting %S to %S\n", Driver->Name, Name );
+ if (!_wcsicmp( Driver->Name, Name))
{
- DPRINT( "Comparting %S to %S\n", Driver->Name, Name );
- if (!_wcsicmp( Driver->Name, Name))
- {
- return ++Driver->ReferenceCount;
- }
- Driver = Driver->Next;
+ return ++Driver->ReferenceCount;
}
+ Driver = Driver->Next;
+ }
DPRINT( "Driver %S not found to reference, generic count: %d\n", Name, GenericDriver->ReferenceCount );
assert( GenericDriver != 0 );
return ++GenericDriver->ReferenceCount;
GRAPHICS_DRIVER *Driver = DriverList;
while (Driver && Name)
+ {
+ DPRINT( "Comparting %S to %S\n", Driver->Name, Name );
+ if (!_wcsicmp( Driver->Name, Name))
{
- DPRINT( "Comparting %S to %S\n", Driver->Name, Name );
- if (!_wcsicmp( Driver->Name, Name))
- {
- return --Driver->ReferenceCount;
- }
- Driver = Driver->Next;
+ return --Driver->ReferenceCount;
}
+ Driver = Driver->Next;
+ }
DPRINT( "Driver '%S' not found to dereference, generic count: %d\n", Name, GenericDriver->ReferenceCount );
assert( GenericDriver != 0 );
return --GenericDriver->ReferenceCount;
* */
#define BEZIERMIDDLE(Mid, P1, P2) \
- (Mid).x=((P1).x+(P2).x + 1)/2;\
- (Mid).y=((P1).y+(P2).y + 1)/2;
+ (Mid).x=((P1).x+(P2).x + 1)/2;\
+ (Mid).y=((P1).y+(P2).y + 1)/2;
/**********************************************************
* BezierCheck helper function to check
*/
static BOOL BezierCheck( int level, POINT *Points)
{
- INT dx, dy;
- dx=Points[3].x-Points[0].x;
- dy=Points[3].y-Points[0].y;
- if(abs(dy)<=abs(dx)){/* shallow line */
- /* check that control points are between begin and end */
- if(Points[1].x < Points[0].x){
- if(Points[1].x < Points[3].x)
- return FALSE;
- }else
- if(Points[1].x > Points[3].x)
- return FALSE;
- if(Points[2].x < Points[0].x){
- if(Points[2].x < Points[3].x)
- return FALSE;
- }else
- if(Points[2].x > Points[3].x)
- return FALSE;
- dx=BEZIERSHIFTDOWN(dx);
- if(!dx) return TRUE;
- if(abs(Points[1].y-Points[0].y-(dy/dx)*
- BEZIERSHIFTDOWN(Points[1].x-Points[0].x)) > BEZIERPIXEL ||
- abs(Points[2].y-Points[0].y-(dy/dx)*
- BEZIERSHIFTDOWN(Points[2].x-Points[0].x)) > BEZIERPIXEL )
- return FALSE;
- else
- return TRUE;
- }else{ /* steep line */
- /* check that control points are between begin and end */
- if(Points[1].y < Points[0].y){
- if(Points[1].y < Points[3].y)
- return FALSE;
- }else
- if(Points[1].y > Points[3].y)
- return FALSE;
- if(Points[2].y < Points[0].y){
- if(Points[2].y < Points[3].y)
- return FALSE;
- }else
- if(Points[2].y > Points[3].y)
- return FALSE;
- dy=BEZIERSHIFTDOWN(dy);
- if(!dy) return TRUE;
- if(abs(Points[1].x-Points[0].x-(dx/dy)*
- BEZIERSHIFTDOWN(Points[1].y-Points[0].y)) > BEZIERPIXEL ||
- abs(Points[2].x-Points[0].x-(dx/dy)*
- BEZIERSHIFTDOWN(Points[2].y-Points[0].y)) > BEZIERPIXEL )
- return FALSE;
- else
- return TRUE;
+ INT dx, dy;
+
+ dx=Points[3].x-Points[0].x;
+ dy=Points[3].y-Points[0].y;
+ if(abs(dy)<=abs(dx)) {/* shallow line */
+ /* check that control points are between begin and end */
+ if(Points[1].x < Points[0].x){
+ if(Points[1].x < Points[3].x) return FALSE;
+ }else
+ if(Points[1].x > Points[3].x) return FALSE;
+ if(Points[2].x < Points[0].x) {
+ if(Points[2].x < Points[3].x) return FALSE;
+ } else
+ if(Points[2].x > Points[3].x) return FALSE;
+ dx=BEZIERSHIFTDOWN(dx);
+ if(!dx) return TRUE;
+ if(abs(Points[1].y-Points[0].y-(dy/dx)*
+ BEZIERSHIFTDOWN(Points[1].x-Points[0].x)) > BEZIERPIXEL ||
+ abs(Points[2].y-Points[0].y-(dy/dx)*
+ BEZIERSHIFTDOWN(Points[2].x-Points[0].x)) > BEZIERPIXEL) return FALSE;
+ else
+ return TRUE;
+ } else{ /* steep line */
+ /* check that control points are between begin and end */
+ if(Points[1].y < Points[0].y){
+ if(Points[1].y < Points[3].y) return FALSE;
+ } else
+ if(Points[1].y > Points[3].y) return FALSE;
+ if(Points[2].y < Points[0].y){
+ if(Points[2].y < Points[3].y) return FALSE;
+ } else
+ if(Points[2].y > Points[3].y) return FALSE;
+ dy=BEZIERSHIFTDOWN(dy);
+ if(!dy) return TRUE;
+ if(abs(Points[1].x-Points[0].x-(dx/dy)*
+ BEZIERSHIFTDOWN(Points[1].y-Points[0].y)) > BEZIERPIXEL ||
+ abs(Points[2].x-Points[0].x-(dx/dy)*
+ BEZIERSHIFTDOWN(Points[2].y-Points[0].y)) > BEZIERPIXEL ) return FALSE;
+ else
+ return TRUE;
}
}
static void GDI_InternalBezier( POINT *Points, POINT **PtsOut, INT *dwOut,
INT *nPtsOut, INT level )
{
- if(*nPtsOut == *dwOut) {
- *dwOut *= 2;
- *PtsOut = ExAllocatePool(NonPagedPool, *dwOut * sizeof(POINT));
- }
+ if(*nPtsOut == *dwOut) {
+ *dwOut *= 2;
+ *PtsOut = ExAllocatePool(NonPagedPool, *dwOut * sizeof(POINT));
+ }
- if(!level || BezierCheck(level, Points)) {
- if(*nPtsOut == 0) {
- (*PtsOut)[0].x = BEZIERSHIFTDOWN(Points[0].x);
- (*PtsOut)[0].y = BEZIERSHIFTDOWN(Points[0].y);
- *nPtsOut = 1;
- }
- (*PtsOut)[*nPtsOut].x = BEZIERSHIFTDOWN(Points[3].x);
- (*PtsOut)[*nPtsOut].y = BEZIERSHIFTDOWN(Points[3].y);
- (*nPtsOut) ++;
- } else {
- POINT Points2[4]; /* for the second recursive call */
- Points2[3]=Points[3];
- BEZIERMIDDLE(Points2[2], Points[2], Points[3]);
- BEZIERMIDDLE(Points2[0], Points[1], Points[2]);
- BEZIERMIDDLE(Points2[1],Points2[0],Points2[2]);
+ if(!level || BezierCheck(level, Points)) {
+ if(*nPtsOut == 0) {
+ (*PtsOut)[0].x = BEZIERSHIFTDOWN(Points[0].x);
+ (*PtsOut)[0].y = BEZIERSHIFTDOWN(Points[0].y);
+ *nPtsOut = 1;
+ }
+ (*PtsOut)[*nPtsOut].x = BEZIERSHIFTDOWN(Points[3].x);
+ (*PtsOut)[*nPtsOut].y = BEZIERSHIFTDOWN(Points[3].y);
+ (*nPtsOut) ++;
+ } else {
+ POINT Points2[4]; /* for the second recursive call */
+ Points2[3]=Points[3];
+ BEZIERMIDDLE(Points2[2], Points[2], Points[3]);
+ BEZIERMIDDLE(Points2[0], Points[1], Points[2]);
+ BEZIERMIDDLE(Points2[1],Points2[0],Points2[2]);
- BEZIERMIDDLE(Points[1], Points[0], Points[1]);
- BEZIERMIDDLE(Points[2], Points[1], Points2[0]);
- BEZIERMIDDLE(Points[3], Points[2], Points2[1]);
+ BEZIERMIDDLE(Points[1], Points[0], Points[1]);
+ BEZIERMIDDLE(Points[2], Points[1], Points2[0]);
+ BEZIERMIDDLE(Points[3], Points[2], Points2[1]);
- Points2[0]=Points[3];
+ Points2[0]=Points[3];
- /* do the two halves */
- GDI_InternalBezier(Points, PtsOut, dwOut, nPtsOut, level-1);
- GDI_InternalBezier(Points2, PtsOut, dwOut, nPtsOut, level-1);
- }
+ /* do the two halves */
+ GDI_InternalBezier(Points, PtsOut, dwOut, nPtsOut, level-1);
+ GDI_InternalBezier(Points2, PtsOut, dwOut, nPtsOut, level-1);
+ }
}
/***********************************************************************
*/
POINT *GDI_Bezier( const POINT *Points, INT count, INT *nPtsOut )
{
- POINT *out;
- INT Bezier, dwOut = BEZIER_INITBUFSIZE, i;
+ POINT *out;
+ INT Bezier, dwOut = BEZIER_INITBUFSIZE, i;
- if((count - 1) % 3 != 0) {
- return NULL;
- }
- *nPtsOut = 0;
- out = ExAllocatePool(NonPagedPool, dwOut * sizeof(POINT));
- for(Bezier = 0; Bezier < (count-1)/3; Bezier++) {
- POINT ptBuf[4];
- memcpy(ptBuf, Points + Bezier * 3, sizeof(POINT) * 4);
- for(i = 0; i < 4; i++) {
- ptBuf[i].x = BEZIERSHIFTUP(ptBuf[i].x);
- ptBuf[i].y = BEZIERSHIFTUP(ptBuf[i].y);
- }
- GDI_InternalBezier( ptBuf, &out, &dwOut, nPtsOut, BEZIERMAXDEPTH );
+ if((count - 1) % 3 != 0) {
+ return NULL;
+ }
+ *nPtsOut = 0;
+ out = ExAllocatePool(NonPagedPool, dwOut * sizeof(POINT));
+ for(Bezier = 0; Bezier < (count-1)/3; Bezier++) {
+ POINT ptBuf[4];
+ memcpy(ptBuf, Points + Bezier * 3, sizeof(POINT) * 4);
+ for(i = 0; i < 4; i++) {
+ ptBuf[i].x = BEZIERSHIFTUP(ptBuf[i].x);
+ ptBuf[i].y = BEZIERSHIFTUP(ptBuf[i].y);
}
+ GDI_InternalBezier( ptBuf, &out, &dwOut, nPtsOut, BEZIERMAXDEPTH );
+ }
- return out;
+ return out;
}
-
-
#undef WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <stdlib.h>
#include <win32k/bitmaps.h>
//#include <win32k/debug.h>
+#include "../eng/objects.h"
#define NDEBUG
#include <debug.h>
INT YSrc,
DWORD ROP)
{
- PDC DCDest = DC_HandleToPtr(hDCDest);
- PDC DCSrc = DC_HandleToPtr(hDCSrc);
- PSURFOBJ SurfDest;
- PSURFOBJ SurfSrc;
- RECTL DestRect;
- POINTL SourcePoint;
- PBITMAPOBJ DestBitmapObj;
- PBITMAPOBJ SrcBitmapObj;
- BOOL Status, SurfDestAlloc, SurfSrcAlloc;
+ PDC DCDest = DC_HandleToPtr(hDCDest);
+ PDC DCSrc = DC_HandleToPtr(hDCSrc);
+ PSURFOBJ SurfDest, SurfSrc;
+ PSURFGDI SurfGDIDest, SurfGDISrc;
+ RECTL DestRect;
+ POINTL SourcePoint;
+ PBITMAPOBJ DestBitmapObj;
+ PBITMAPOBJ SrcBitmapObj;
+ BOOL Status, SurfDestAlloc, SurfSrcAlloc;
+ PPALOBJ DCLogPal;
+ PPALGDI PalDestGDI, PalSourceGDI;
+ PXLATEOBJ XlateObj = NULL;
+ HPALETTE SourcePalette, DestPalette;
DestRect.left = XDest;
DestRect.top = YDest;
SurfDestAlloc = FALSE;
SurfSrcAlloc = FALSE;
-DPRINT("Get surfdest.. ");
+ // Determine surfaces to be used in the bitblt
+ SurfDest = AccessUserObject(DCDest->Surface);
+ SurfSrc = AccessUserObject(DCSrc->Surface);
- // Get the SurfDest
- if(DCDest->Surface != NULL)
- {
- // Use the DC's surface if it has one
- SurfDest = AccessUserObject(DCDest->Surface);
- } else
- return FALSE;
+ SurfGDIDest = AccessInternalObjectFromUserObject(SurfDest);
+ SurfGDISrc = AccessInternalObjectFromUserObject(SurfSrc);
+
+ // Retrieve the logical palette of the destination DC
+ DCLogPal = AccessUserObject(DCDest->w.hPalette);
-DPRINT("Get surfsrc.. ");
+ if(DCLogPal)
+ if(DCLogPal->logicalToSystem)
+ XlateObj = DCLogPal->logicalToSystem;
- // Get the SurfSrc
- if(DCSrc->Surface != NULL)
+ // If the source and destination formats differ, create an XlateObj [what if we already have one??]
+ if((BitsPerFormat(SurfDest->iBitmapFormat) != BitsPerFormat(SurfSrc->iBitmapFormat)) && (XlateObj == NULL))
{
-DPRINT("from DC's surface\n");
+ if(DCDest->w.hPalette != 0)
+ {
+ DestPalette = DCDest->w.hPalette;
+ } else
+ DestPalette = W32kGetStockObject(DEFAULT_PALETTE);
- // Use the DC's surface if it has one
- SurfSrc = AccessUserObject(DCSrc->Surface);
- } else
- return FALSE;
+ if(DCSrc->w.hPalette != 0)
+ {
+ SourcePalette = DCSrc->w.hPalette;
+ } else
+ SourcePalette = W32kGetStockObject(DEFAULT_PALETTE);
+
+ PalDestGDI = AccessInternalObject(DestPalette);
+ PalSourceGDI = AccessInternalObject(SourcePalette);
+ XlateObj = EngCreateXlate(PalDestGDI->Mode, PalSourceGDI->Mode, DestPalette, SourcePalette);
+ }
-DPRINT("Go to EngBitBlt\n");
- Status = EngBitBlt(SurfDest, SurfSrc, NULL, NULL, NULL,
- &DestRect, &SourcePoint, NULL, NULL, NULL, NULL); // FIXME: Color translation (xlateobj)
+ // Perform the bitblt operation
+
+ Status = EngBitBlt(SurfDest, SurfSrc, NULL, NULL, XlateObj, &DestRect, &SourcePoint, NULL, NULL, NULL, NULL);
if(SurfDestAlloc == TRUE) ExFreePool(SurfDest);
if(SurfSrcAlloc == TRUE) ExFreePool(SurfSrc);
/* Check parameters */
if (!Height || !Width)
- {
- return 0;
- }
+ {
+ return 0;
+ }
if (Planes != 1)
- {
- UNIMPLEMENTED;
- return 0;
- }
+ {
+ UNIMPLEMENTED;
+ return 0;
+ }
if (Height < 0)
- {
- Height = -Height;
- }
+ {
+ Height = -Height;
+ }
if (Width < 0)
- {
- Width = -Width;
- }
+ {
+ Width = -Width;
+ }
/* Create the BITMAPOBJ */
bmp = BITMAPOBJ_AllocBitmap ();
if (!bmp)
- {
- return 0;
- }
+ {
+ return 0;
+ }
DPRINT("W32kCreateBitmap:%dx%d, %d (%d BPP) colors returning %08x\n", Width, Height,
1 << (Planes * BitsPerPel), BitsPerPel, bmp);
- bmp->size.cx = 0;
- bmp->size.cy = 0;
+ bmp->size.cx = Width;
+ bmp->size.cy = Height;
bmp->bitmap.bmType = 0;
bmp->bitmap.bmWidth = Width;
bmp->bitmap.bmHeight = Height;
bmp->bitmap.bmBits = ExAllocatePool(PagedPool, bmp->bitmap.bmWidthBytes * bmp->bitmap.bmHeight);
if (Bits) /* Set bitmap bits */
- {
- W32kSetBitmapBits(hBitmap,
- Height * bmp->bitmap.bmWidthBytes,
- Bits);
- }
-
+ {
+ W32kSetBitmapBits(hBitmap, Height * bmp->bitmap.bmWidthBytes, Bits);
+ }
return hBitmap;
}
hbmpRet = 0;
dc = DC_HandleToPtr (hDC);
- DPRINT("W32kCreateCompatibleBitmap(%04x,%d,%d, bpp:%d) = \n", hDC, Width, Height, dc->w.bitsPerPixel);
+ DbgPrint("W32kCreateCompatibleBitmap(%04x,%d,%d, bpp:%d) = \n", hDC, Width, Height, dc->w.bitsPerPixel);
if (!dc)
- {
- return 0;
- }
+ {
+ return 0;
+ }
if ((Width >= 0x10000) || (Height >= 0x10000))
- {
- DPRINT("got bad width %d or height %d, please look for reason\n",
- Width, Height);
- }
+ {
+ DPRINT("got bad width %d or height %d, please look for reason\n", Width, Height);
+ }
else
+ {
+ /* MS doc says if width or height is 0, return 1-by-1 pixel, monochrome bitmap */
+ if (!Width || !Height)
{
- /* MS doc says if width or height is 0, return 1-by-1 pixel, monochrome bitmap */
- if (!Width || !Height)
- {
- hbmpRet = W32kCreateBitmap (1, 1, 1, 1, NULL);
- }
- else
- {
- hbmpRet = W32kCreateBitmap (Width,
- Height,
- 1,
- dc->w.bitsPerPixel,
- NULL);
- }
+ hbmpRet = W32kCreateBitmap (1, 1, 1, 1, NULL);
+ }
+ else
+ {
+ hbmpRet = W32kCreateBitmap(Width, Height, 1, dc->w.bitsPerPixel, NULL);
}
+ }
DPRINT ("\t\t%04x\n", hbmpRet);
DC_UnlockDC (hDC);
-
+
return hbmpRet;
}
BM->bmBits);
}
-HBITMAP STDCALL W32kCreateDIBitmap(HDC hDC,
- CONST BITMAPINFOHEADER *bmih,
- DWORD Init,
- CONST VOID *bInit,
- CONST BITMAPINFO *bmi,
- UINT Usage)
-{
- UNIMPLEMENTED;
-}
-
-HBITMAP STDCALL W32kCreateDIBSection(HDC hDC,
- CONST BITMAPINFO *bmi,
- UINT Usage,
- VOID *Bits,
- HANDLE hSection,
- DWORD dwOffset)
-{
- UNIMPLEMENTED;
-}
-
HBITMAP STDCALL W32kCreateDiscardableBitmap(HDC hDC,
INT Width,
INT Height)
UNIMPLEMENTED;
}
-LONG STDCALL W32kGetBitmapBits(HBITMAP hBitmap,
- LONG Count,
- LPVOID Bits)
-{
- PBITMAPOBJ bmp;
- LONG height, ret;
-
- bmp = BITMAPOBJ_HandleToPtr (hBitmap);
- if (!bmp)
- {
- return 0;
- }
-
- /* If the bits vector is null, the function should return the read size */
- if (Bits == NULL)
- {
- return bmp->bitmap.bmWidthBytes * bmp->bitmap.bmHeight;
- }
-
- if (Count < 0)
- {
- DPRINT ("(%ld): Negative number of bytes passed???\n", Count);
- Count = -Count;
- }
-
- /* Only get entire lines */
- height = Count / bmp->bitmap.bmWidthBytes;
- if (height > bmp->bitmap.bmHeight)
- {
- height = bmp->bitmap.bmHeight;
- }
- Count = height * bmp->bitmap.bmWidthBytes;
- if (Count == 0)
- {
- DPRINT("Less then one entire line requested\n");
- BITMAPOBJ_UnlockBitmap (hBitmap);
- return 0;
- }
-
- DPRINT("(%08x, %ld, %p) %dx%d %d colors fetched height: %ld\n",
- hBitmap, Count, Bits, bmp->bitmap.bmWidth, bmp->bitmap.bmHeight,
- 1 << bmp->bitmap.bmBitsPixel, height );
-#if 0
- /* FIXME: Call DDI CopyBits here if available */
- if(bmp->DDBitmap)
- {
- DPRINT("Calling device specific BitmapBits\n");
- if(bmp->DDBitmap->funcs->pBitmapBits)
- {
- ret = bmp->DDBitmap->funcs->pBitmapBits(hbitmap, bits, count,
- DDB_GET);
- }
- else
- {
- ERR_(bitmap)("BitmapBits == NULL??\n");
- ret = 0;
- }
- }
- else
-#endif
- {
- if(!bmp->bitmap.bmBits)
- {
- DPRINT ("Bitmap is empty\n");
- ret = 0;
- }
- else
- {
- memcpy(Bits, bmp->bitmap.bmBits, Count);
- ret = Count;
- }
- }
- BITMAPOBJ_UnlockBitmap (hBitmap);
-
- return ret;
-}
-
BOOL STDCALL W32kGetBitmapDimensionEx(HBITMAP hBitmap,
LPSIZE Dimension)
{
bmp = BITMAPOBJ_HandleToPtr (hBitmap);
if (bmp == NULL)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
*Dimension = bmp->size;
BITMAPOBJ_UnlockBitmap (hBitmap);
return TRUE;
}
-UINT STDCALL W32kGetDIBColorTable(HDC hDC,
- UINT StartIndex,
- UINT Entries,
- RGBQUAD *Colors)
-{
- UNIMPLEMENTED;
-}
-
-INT STDCALL W32kGetDIBits(HDC hDC,
- HBITMAP hBitmap,
- UINT StartScan,
- UINT ScanLines,
- LPVOID Bits,
- LPBITMAPINFO bi,
- UINT Usage)
-{
- UNIMPLEMENTED;
-}
-
COLORREF STDCALL W32kGetPixel(HDC hDC,
INT XPos,
INT YPos)
bmp = BITMAPOBJ_HandleToPtr (hBitmap);
if (bmp == NULL || Bits == NULL)
- {
- return 0;
- }
+ {
+ return 0;
+ }
if (Bytes < 0)
- {
- DPRINT ("(%ld): Negative number of bytes passed???\n", Bytes );
- Bytes = -Bytes;
- }
+ {
+ DPRINT ("(%ld): Negative number of bytes passed???\n", Bytes );
+ Bytes = -Bytes;
+ }
/* Only get entire lines */
height = Bytes / bmp->bitmap.bmWidthBytes;
if (height > bmp->bitmap.bmHeight)
- {
- height = bmp->bitmap.bmHeight;
- }
+ {
+ height = bmp->bitmap.bmHeight;
+ }
Bytes = height * bmp->bitmap.bmWidthBytes;
DPRINT ("(%08x, bytes:%ld, bits:%p) %dx%d %d colors fetched height: %ld\n",
hBitmap,
#if 0
/* FIXME: call DDI specific function here if available */
if(bmp->DDBitmap)
+ {
+ DPRINT ("Calling device specific BitmapBits\n");
+ if (bmp->DDBitmap->funcs->pBitmapBits)
{
- DPRINT ("Calling device specific BitmapBits\n");
- if (bmp->DDBitmap->funcs->pBitmapBits)
- {
- ret = bmp->DDBitmap->funcs->pBitmapBits(hBitmap,
- (void *) Bits,
- Bytes,
- DDB_SET);
- }
- else
- {
- DPRINT ("BitmapBits == NULL??\n");
- ret = 0;
- }
+ ret = bmp->DDBitmap->funcs->pBitmapBits(hBitmap, (void *) Bits, Bytes, DDB_SET);
}
+ else
+ {
+ DPRINT ("BitmapBits == NULL??\n");
+ ret = 0;
+ }
+ }
else
#endif
{
/* FIXME: Alloc enough for entire bitmap */
if (bmp->bitmap.bmBits == NULL)
- {
- bmp->bitmap.bmBits = ExAllocatePool (PagedPool, Bytes);
- }
+ {
+ bmp->bitmap.bmBits = ExAllocatePool (PagedPool, Bytes);
+ }
if(!bmp->bitmap.bmBits)
- {
- DPRINT ("Unable to allocate bit buffer\n");
- ret = 0;
- }
+ {
+ DPRINT ("Unable to allocate bit buffer\n");
+ ret = 0;
+ }
else
- {
- memcpy(bmp->bitmap.bmBits, Bits, Bytes);
- ret = Bytes;
- }
+ {
+ memcpy(bmp->bitmap.bmBits, Bits, Bytes);
+ ret = Bytes;
+ }
}
BITMAPOBJ_UnlockBitmap (hBitmap);
bmp = BITMAPOBJ_HandleToPtr (hBitmap);
if (bmp == NULL)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
if (Size)
- {
- *Size = bmp->size;
- }
+ {
+ *Size = bmp->size;
+ }
bmp->size.cx = Width;
bmp->size.cy = Height;
BITMAPOBJ_UnlockBitmap (hBitmap);
return TRUE;
}
-UINT STDCALL W32kSetDIBColorTable(HDC hDC,
- UINT StartIndex,
- UINT Entries,
- CONST RGBQUAD *Colors)
-{
- UNIMPLEMENTED;
-}
-
-INT STDCALL W32kSetDIBits(HDC hDC,
- HBITMAP hBitmap,
- UINT StartScan,
- UINT ScanLines,
- CONST VOID *Bits,
- CONST BITMAPINFO *bmi,
- UINT ColorUse)
-{
- UNIMPLEMENTED;
-}
-
-INT STDCALL W32kSetDIBitsToDevice(HDC hDC,
- INT XDest,
- INT YDest,
- DWORD Width,
- DWORD Height,
- INT XSrc,
- INT YSrc,
- UINT StartScan,
- UINT ScanLines,
- CONST VOID *Bits,
- CONST BITMAPINFO *bmi,
- UINT ColorUse)
-{
- UNIMPLEMENTED;
-}
-
COLORREF STDCALL W32kSetPixel(HDC hDC,
INT X,
INT Y,
UNIMPLEMENTED;
}
-INT STDCALL W32kStretchDIBits(HDC hDC,
- INT XDest,
- INT YDest,
- INT DestWidth,
- INT DestHeight,
- INT XSrc,
- INT YSrc,
- INT SrcWidth,
- INT SrcHeight,
- CONST VOID *Bits,
- CONST BITMAPINFO *BitsInfo,
- UINT Usage,
- DWORD ROP)
-{
- UNIMPLEMENTED;
-}
-
/* Internal Functions */
INT
BITMAPOBJ_GetWidthBytes (INT bmWidth, INT bpp)
{
switch(bpp)
- {
+ {
case 1:
return 2 * ((bmWidth+15) >> 4);
default:
DPRINT ("stub");
- }
+ }
return -1;
}
bmp = BITMAPOBJ_HandleToPtr (hBitmap);
if (bmp == NULL)
- {
- return 0;
- }
+ {
+ return 0;
+ }
res = 0;
bm = bmp->bitmap;
bm.bmBits = NULL;
res = W32kCreateBitmapIndirect(&bm);
if(res)
- {
- char *buf;
+ {
+ char *buf;
- buf = ExAllocatePool (NonPagedPool, bm.bmWidthBytes * bm.bmHeight);
- W32kGetBitmapBits (hBitmap, bm.bmWidthBytes * bm.bmHeight, buf);
- W32kSetBitmapBits (res, bm.bmWidthBytes * bm.bmHeight, buf);
- ExFreePool (buf);
- }
+ buf = ExAllocatePool (NonPagedPool, bm.bmWidthBytes * bm.bmHeight);
+ W32kGetBitmapBits (hBitmap, bm.bmWidthBytes * bm.bmHeight, buf);
+ W32kSetBitmapBits (res, bm.bmWidthBytes * bm.bmHeight, buf);
+ ExFreePool (buf);
+ }
BITMAPOBJ_UnlockBitmap (hBitmap);
return res;
}
-/***********************************************************************
- * DIB_GetDIBWidthBytes
- *
- * Return the width of a DIB bitmap in bytes. DIB bitmap data is 32-bit aligned.
- * http://www.microsoft.com/msdn/sdk/platforms/doc/sdk/win32/struc/src/str01.htm
- * 11/16/1999 (RJJ) lifted from wine
- */
-int DIB_GetDIBWidthBytes(int width, int depth)
+INT BITMAP_GetObject(BITMAPOBJ * bmp, INT count, LPVOID buffer)
{
- int words;
-
- switch(depth)
- {
- case 1: words = (width + 31) / 32; break;
- case 4: words = (width + 7) / 8; break;
- case 8: words = (width + 3) / 4; break;
- case 15:
- case 16: words = (width + 1) / 2; break;
- case 24: words = (width * 3 + 3)/4; break;
-
- default:
- DPRINT("(%d): Unsupported depth\n", depth );
- /* fall through */
- case 32:
- words = width;
- }
- return 4 * words;
-}
-
-/***********************************************************************
- * DIB_GetDIBImageBytes
- *
- * Return the number of bytes used to hold the image in a DIB bitmap.
- * 11/16/1999 (RJJ) lifted from wine
- */
-
-int DIB_GetDIBImageBytes (int width, int height, int depth)
-{
- return DIB_GetDIBWidthBytes( width, depth ) * (height < 0 ? -height : height);
-}
-
-/***********************************************************************
- * DIB_BitmapInfoSize
- *
- * Return the size of the bitmap info structure including color table.
- * 11/16/1999 (RJJ) lifted from wine
- */
-
-int DIB_BitmapInfoSize (const BITMAPINFO * info, WORD coloruse)
-{
- int colors;
-
- if (info->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
+ if(bmp->dib)
+ {
+ if(count < sizeof(DIBSECTION))
{
- BITMAPCOREHEADER *core = (BITMAPCOREHEADER *)info;
- colors = (core->bcBitCount <= 8) ? 1 << core->bcBitCount : 0;
- return sizeof(BITMAPCOREHEADER) + colors *
- ((coloruse == DIB_RGB_COLORS) ? sizeof(RGBTRIPLE) : sizeof(WORD));
+ if (count > sizeof(BITMAP)) count = sizeof(BITMAP);
}
- else /* assume BITMAPINFOHEADER */
+ else
{
- colors = info->bmiHeader.biClrUsed;
- if (!colors && (info->bmiHeader.biBitCount <= 8))
- colors = 1 << info->bmiHeader.biBitCount;
- return sizeof(BITMAPINFOHEADER) + colors *
- ((coloruse == DIB_RGB_COLORS) ? sizeof(RGBQUAD) : sizeof(WORD));
+ if (count > sizeof(DIBSECTION)) count = sizeof(DIBSECTION);
}
+ memcpy(buffer, bmp->dib, count);
+ return count;
+ }
+ else
+ {
+ if (count > sizeof(BITMAP)) count = sizeof(BITMAP);
+ memcpy(buffer, &bmp->bitmap, count);
+ return count;
+ }
}
-
-/* $Id: brush.c,v 1.10 2000/06/29 23:35:53 dwelch Exp $
+/* $Id: brush.c,v 1.11 2001/03/31 15:35:08 jfilby Exp $
*/
PBRUSHOBJ brushPtr;
HBRUSH hBrush;
- hBrush = BRUSHOBJ_AllocBrush ();
+ brushPtr = BRUSHOBJ_AllocBrush();
+ hBrush = BRUSHOBJ_PtrToHandle (brushPtr);
if (hBrush == NULL)
- {
- return 0;
- }
+ {
+ return 0;
+ }
- brushPtr = BRUSHOBJ_HandleToPtr (hBrush);
brushPtr->logbrush.lbStyle = lb->lbStyle;
brushPtr->logbrush.lbColor = lb->lbColor;
brushPtr->logbrush.lbHatch = lb->lbHatch;
+
BRUSHOBJ_UnlockBrush (hBrush);
DPRINT("%08x\n", hBrush);
/* Make a copy of the bitmap */
if (!(info = (BITMAPINFO *)GlobalLock( hbitmap )))
- {
- return 0;
- }
+ {
+ return 0;
+ }
- if (info->bmiHeader.biCompression)
- size = info->bmiHeader.biSizeImage;
- else
- size = DIB_GetDIBImageBytes(info->bmiHeader.biWidth,
- info->bmiHeader.biHeight,
- info->bmiHeader.biBitCount);
- size += DIB_BitmapInfoSize( info, coloruse );
-
- if (!(logbrush.lbHatch = (INT)GlobalAlloc16( GMEM_MOVEABLE, size )))
- {
- GlobalUnlock16( hbitmap );
- return 0;
- }
- newInfo = (BITMAPINFO *) GlobalLock16( (HGLOBAL16)logbrush.lbHatch );
- memcpy( newInfo, info, size );
- GlobalUnlock16( (HGLOBAL16)logbrush.lbHatch );
- GlobalUnlock( hbitmap );
- return W32kCreateBrushIndirect( &logbrush );
+ if (info->bmiHeader.biCompression) size = info->bmiHeader.biSizeImage;
+ else
+ size = DIB_GetDIBImageBytes(info->bmiHeader.biWidth, info->bmiHeader.biHeight, info->bmiHeader.biBitCount);
+ size += DIB_BitmapInfoSize(info, coloruse);
+
+ if (!(logbrush.lbHatch = (INT)GlobalAlloc16( GMEM_MOVEABLE, size )))
+ {
+ GlobalUnlock16( hbitmap );
+ return 0;
+ }
+ newInfo = (BITMAPINFO *) GlobalLock16((HGLOBAL16)logbrush.lbHatch);
+ memcpy(newInfo, info, size);
+ GlobalUnlock16((HGLOBAL16)logbrush.lbHatch);
+ GlobalUnlock(hbitmap);
+ return W32kCreateBrushIndirect(&logbrush);
#endif
}
info = (BITMAPINFO *) PackedDIB;
if (info == NULL)
- {
- return 0;
- }
+ {
+ return 0;
+ }
DPRINT ("%p %ldx%ld %dbpp\n",
info,
info->bmiHeader.biWidth,
/* Make a copy of the bitmap */
if (info->bmiHeader.biCompression)
- {
- size = info->bmiHeader.biSizeImage;
- }
+ {
+ size = info->bmiHeader.biSizeImage;
+ }
else
{
- size = DIB_GetDIBImageBytes (info->bmiHeader.biWidth,
- info->bmiHeader.biHeight,
- info->bmiHeader.biBitCount);
- }
+ size = DIB_GetDIBImageBytes (info->bmiHeader.biWidth, info->bmiHeader.biHeight, info->bmiHeader.biBitCount);
+ }
size += DIB_BitmapInfoSize (info, Usage);
- logbrush.lbHatch = (INT)
- GDIOBJ_PtrToHandle (GDIOBJ_AllocObject (size, GO_MAGIC_DONTCARE),
- GO_MAGIC_DONTCARE);
+ logbrush.lbHatch = (INT)GDIOBJ_PtrToHandle (GDIOBJ_AllocObject (size, GO_MAGIC_DONTCARE), GO_MAGIC_DONTCARE);
if (logbrush.lbHatch == 0)
- {
- return 0;
- }
- newInfo = (PBITMAPINFO) GDIOBJ_HandleToPtr ((HGDIOBJ) logbrush.lbHatch,
- GO_MAGIC_DONTCARE);
- memcpy (newInfo, info, size);
- GDIOBJ_UnlockObject ((HGDIOBJ) logbrush.lbHatch);
+ {
+ return 0;
+ }
+ newInfo = (PBITMAPINFO) GDIOBJ_HandleToPtr ((HGDIOBJ) logbrush.lbHatch, GO_MAGIC_DONTCARE);
+ memcpy(newInfo, info, size);
+ GDIOBJ_UnlockObject((HGDIOBJ)logbrush.lbHatch);
return W32kCreateBrushIndirect (&logbrush);
}
DPRINT("%d %06lx\n", Style, Color);
if (Style < 0 || Style >= NB_HATCH_STYLES)
- {
- return 0;
- }
+ {
+ return 0;
+ }
logbrush.lbStyle = BS_HATCHED;
logbrush.lbColor = Color;
logbrush.lbHatch = Style;
DPRINT ("%04x\n", hBitmap);
logbrush.lbHatch = (INT) BITMAPOBJ_CopyBitmap (hBitmap);
if(!logbrush.lbHatch)
- {
- return 0;
- }
+ {
+ return 0;
+ }
else
- {
- return W32kCreateBrushIndirect( &logbrush );
- }
+ {
+ return W32kCreateBrushIndirect( &logbrush );
+ }
}
HBRUSH STDCALL W32kCreateSolidBrush(COLORREF Color)
{
- LOGBRUSH logbrush;
+ LOGBRUSH logbrush;
- logbrush.lbStyle = BS_SOLID;
- logbrush.lbColor = Color;
- logbrush.lbHatch = 0;
+ logbrush.lbStyle = BS_SOLID;
+ logbrush.lbColor = Color;
+ logbrush.lbHatch = 0;
- return W32kCreateBrushIndirect(&logbrush);
+ return W32kCreateBrushIndirect(&logbrush);
}
BOOL STDCALL W32kFixBrushOrgEx(VOID)
+// FIXME: Use PXLATEOBJ logicalToSystem instead of int *mapping
#undef WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <ddk/ntddk.h>
+#include <ddk/winddi.h>
+#include <win32k/dc.h>
#include <win32k/color.h>
+#include "../eng/objects.h"
// #define NDEBUG
#include <win32k/debug1.h>
+int COLOR_gapStart = 256;
+int COLOR_gapEnd = -1;
+int COLOR_gapFilled = 0;
+int COLOR_max = 256;
+
+static HPALETTE hPrimaryPalette = 0; // used for WM_PALETTECHANGED
+static HPALETTE hLastRealizedPalette = 0; // UnrealizeObject() needs it
+
+const PALETTEENTRY COLOR_sysPalTemplate[NB_RESERVED_COLORS] =
+{
+ // first 10 entries in the system palette
+ // red green blue flags
+ { 0x00, 0x00, 0x00, PC_SYS_USED },
+ { 0x80, 0x00, 0x00, PC_SYS_USED },
+ { 0x00, 0x80, 0x00, PC_SYS_USED },
+ { 0x80, 0x80, 0x00, PC_SYS_USED },
+ { 0x00, 0x00, 0x80, PC_SYS_USED },
+ { 0x80, 0x00, 0x80, PC_SYS_USED },
+ { 0x00, 0x80, 0x80, PC_SYS_USED },
+ { 0xc0, 0xc0, 0xc0, PC_SYS_USED },
+ { 0xc0, 0xdc, 0xc0, PC_SYS_USED },
+ { 0xa6, 0xca, 0xf0, PC_SYS_USED },
+
+ // ... c_min/2 dynamic colorcells
+ // ... gap (for sparse palettes)
+ // ... c_min/2 dynamic colorcells
+
+ { 0xff, 0xfb, 0xf0, PC_SYS_USED },
+ { 0xa0, 0xa0, 0xa4, PC_SYS_USED },
+ { 0x80, 0x80, 0x80, PC_SYS_USED },
+ { 0xff, 0x00, 0x00, PC_SYS_USED },
+ { 0x00, 0xff, 0x00, PC_SYS_USED },
+ { 0xff, 0xff, 0x00, PC_SYS_USED },
+ { 0x00, 0x00, 0xff, PC_SYS_USED },
+ { 0xff, 0x00, 0xff, PC_SYS_USED },
+ { 0x00, 0xff, 0xff, PC_SYS_USED },
+ { 0xff, 0xff, 0xff, PC_SYS_USED } // last 10
+};
+
+const PALETTEENTRY* COLOR_GetSystemPaletteTemplate(void)
+{
+ return COLOR_sysPalTemplate;
+}
+
BOOL STDCALL W32kAnimatePalette(HPALETTE hpal,
UINT StartIndex,
UINT Entries,
CONST PPALETTEENTRY ppe)
{
+/*
+ if( hPal != W32kGetStockObject(DEFAULT_PALETTE) )
+ {
+ PALETTEOBJ* palPtr = (PALETTEOBJ *)GDI_GetObjPtr(hPal, PALETTE_MAGIC);
+ if (!palPtr) return FALSE;
+
+ if( (StartIndex + NumEntries) <= palPtr->logpalette.palNumEntries )
+ {
+ UINT u;
+ for( u = 0; u < NumEntries; u++ )
+ palPtr->logpalette.palPalEntry[u + StartIndex] = PaletteColors[u];
+ PALETTE_Driver->pSetMapping(palPtr, StartIndex, NumEntries, hPal != hPrimaryPalette );
+ GDI_ReleaseObj(hPal);
+ return TRUE;
+ }
+ GDI_ReleaseObj(hPal);
+ }
+ return FALSE;
+*/
UNIMPLEMENTED;
}
HPALETTE STDCALL W32kCreateHalftonePalette(HDC hDC)
{
- UNIMPLEMENTED;
+ int i, r, g, b;
+ struct {
+ WORD Version;
+ WORD NumberOfEntries;
+ PALETTEENTRY aEntries[256];
+ } Palette;
+
+ Palette.Version = 0x300;
+ Palette.NumberOfEntries = 256;
+ W32kGetSystemPaletteEntries(hDC, 0, 256, Palette.aEntries);
+
+ for (r = 0; r < 6; r++) {
+ for (g = 0; g < 6; g++) {
+ for (b = 0; b < 6; b++) {
+ i = r + g*6 + b*36 + 10;
+ Palette.aEntries[i].peRed = r * 51;
+ Palette.aEntries[i].peGreen = g * 51;
+ Palette.aEntries[i].peBlue = b * 51;
+ }
+ }
+ }
+
+ for (i = 216; i < 246; i++) {
+ int v = (i - 216) * 8;
+ Palette.aEntries[i].peRed = v;
+ Palette.aEntries[i].peGreen = v;
+ Palette.aEntries[i].peBlue = v;
+ }
+
+ return W32kCreatePalette((LOGPALETTE *)&Palette);
}
-HPALETTE STDCALL W32kCreatePalette(CONST PLOGPALETTE lgpl)
+HPALETTE STDCALL W32kCreatePalette(CONST PLOGPALETTE palette)
{
- UNIMPLEMENTED;
+ PPALOBJ PalObj;
+ HPALETTE NewPalette = EngCreatePalette(PAL_INDEXED, palette->palNumEntries, palette->palPalEntry, 0, 0, 0);
+ ULONG size;
+
+ PalObj = AccessUserObject(NewPalette);
+
+ size = sizeof(LOGPALETTE) + (palette->palNumEntries - 1) * sizeof(PALETTEENTRY);
+ memcpy(&PalObj->logpalette, palette, size);
+ PALETTE_ValidateFlags(PalObj->logpalette.palPalEntry, PalObj->logpalette.palNumEntries);
+ PalObj->logicalToSystem = NULL;
+
+ return NewPalette;
}
BOOL STDCALL W32kGetColorAdjustment(HDC hDC,
COLORREF STDCALL W32kGetNearestColor(HDC hDC,
COLORREF Color)
{
- UNIMPLEMENTED;
+ COLORREF nearest = CLR_INVALID;
+ PDC dc;
+ PPALOBJ palObj;
+
+ if(DC_HandleToPtr(hDC))
+ {
+ HPALETTE hpal = (dc->w.hPalette)? dc->w.hPalette : W32kGetStockObject(DEFAULT_PALETTE);
+ palObj = AccessUserObject(hpal);
+ if (!palObj) {
+// GDI_ReleaseObj(hdc);
+ return nearest;
+ }
+
+ nearest = COLOR_LookupNearestColor(palObj->logpalette.palPalEntry,
+ palObj->logpalette.palNumEntries, Color);
+
+// GDI_ReleaseObj( hpal );
+// GDI_ReleaseObj( hdc );
+ }
+
+ return nearest;
}
UINT STDCALL W32kGetNearestPaletteIndex(HPALETTE hpal,
COLORREF Color)
{
- UNIMPLEMENTED;
+ PPALOBJ palObj = AccessUserObject(hpal);
+ UINT index = 0;
+
+ if( palObj )
+ {
+ // Return closest match for the given RGB color
+ index = COLOR_PaletteLookupPixel(palObj->logpalette.palPalEntry, palObj->logpalette.palNumEntries, NULL, Color, FALSE);
+// GDI_ReleaseObj( hpalette );
+ }
+
+ return index;
}
UINT STDCALL W32kGetPaletteEntries(HPALETTE hpal,
UINT Entries,
LPPALETTEENTRY pe)
{
- UNIMPLEMENTED;
+ PPALOBJ palPtr;
+ UINT numEntries;
+
+ palPtr = AccessUserObject(hpal);
+ if (!palPtr) return 0;
+
+ numEntries = palPtr->logpalette.palNumEntries;
+ if (StartIndex + Entries > numEntries) Entries = numEntries - StartIndex;
+ if (pe)
+ {
+ if (StartIndex >= numEntries)
+ {
+// GDI_ReleaseObj( hpalette );
+ return 0;
+ }
+ memcpy(pe, &palPtr->logpalette.palPalEntry[StartIndex], Entries * sizeof(PALETTEENTRY));
+ for(numEntries = 0; numEntries < Entries ; numEntries++)
+ if (pe[numEntries].peFlags & 0xF0)
+ pe[numEntries].peFlags = 0;
+ }
+
+// GDI_ReleaseObj( hpalette );
+ return Entries;
}
UINT STDCALL W32kGetSystemPaletteEntries(HDC hDC,
UINT Entries,
LPPALETTEENTRY pe)
{
- UNIMPLEMENTED;
+ UINT i;
+ PDC dc;
+/*
+ if (!(dc = AccessUserObject(hdc))) return 0;
+
+ if (!pe)
+ {
+ Entries = dc->devCaps->sizePalette;
+ goto done;
+ }
+
+ if (StartIndex >= dc->devCaps->sizePalette)
+ {
+ Entries = 0;
+ goto done;
+ }
+
+ if (StartIndex + Entries >= dc->devCaps->sizePalette) Entries = dc->devCaps->sizePalette - StartIndex;
+
+ for (i = 0; i < Entries; i++)
+ {
+ *(COLORREF*)(entries + i) = COLOR_GetSystemPaletteEntry(StartIndex + i);
+ }
+
+ done:
+// GDI_ReleaseObj(hdc);
+ return count; */
}
UINT STDCALL W32kGetSystemPaletteUse(HDC hDC)
}
UINT STDCALL W32kRealizePalette(HDC hDC)
+/*
+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.
+*/
{
- UNIMPLEMENTED;
+ PPALOBJ palPtr, sysPtr;
+ PPALGDI palGDI, sysGDI;
+ int realized = 0;
+ PDC dc = AccessUserObject(hDC);
+ HPALETTE systemPalette;
+ PSURFGDI SurfGDI;
+ BOOLEAN success;
+
+ if (!dc) return 0;
+
+ palPtr = AccessUserObject(dc->w.hPalette);
+ SurfGDI = AccessInternalObjectFromUserObject(dc->Surface);
+ systemPalette = W32kGetStockObject(STOCK_DEFAULT_PALETTE);
+ sysPtr = AccessInternalObject(systemPalette);
+ palGDI = AccessInternalObject(dc->w.hPalette);
+ sysGDI = AccessInternalObject(systemPalette);
+
+ // Step 1: Create mapping of system palette\DC palette
+ realized = PALETTE_SetMapping(palPtr, 0, palPtr->logpalette.palNumEntries,
+ (dc->w.hPalette != hPrimaryPalette) ||
+ (dc->w.hPalette == W32kGetStockObject(DEFAULT_PALETTE)));
+
+ // 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
+ DbgPrint("win32k: realizepalette unimplemented step 2 for DC_MEMORY");
+ } else {
+ if(SurfGDI->SetPalette)
+ {
+ success = SurfGDI->SetPalette(dc->PDev, sysPtr, 0, 0, sysPtr->logpalette.palNumEntries);
+ }
+ }
+
+ // Step 3: Create the XLATEOBJ for device managed DCs
+ if(dc->w.flags != DC_MEMORY)
+ {
+ // Device managed DC
+ palPtr->logicalToSystem = EngCreateXlate(sysGDI->Mode, palGDI->Mode, systemPalette, dc->w.hPalette);
+ }
+
+// GDI_ReleaseObj(dc->w.hPalette);
+// GDI_ReleaseObj(hdc);
+
+ return realized;
}
BOOL STDCALL W32kResizePalette(HPALETTE hpal,
UINT Entries)
{
+/* PPALOBJ palPtr = (PPALOBJ)AccessUserObject(hPal);
+ UINT cPrevEnt, prevVer;
+ INT prevsize, size = sizeof(LOGPALETTE) + (cEntries - 1) * sizeof(PALETTEENTRY);
+ PXLATEOBJ 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)
+ {
+ PXLATEOBJ 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;
}
HPALETTE hpal,
BOOL ForceBackground)
{
- UNIMPLEMENTED;
+ PDC dc = AccessUserObject(hDC);
+ HPALETTE oldPal;
+
+ oldPal = dc->w.hPalette;
+ dc->w.hPalette = hpal;
+
+ // FIXME: mark the palette as a [fore\back]ground pal
+
+ return oldPal;
}
BOOL STDCALL W32kSetColorAdjustment(HDC hDC,
UINT Entries,
CONST LPPALETTEENTRY pe)
{
- UNIMPLEMENTED;
+ PPALOBJ palPtr;
+ INT numEntries;
+
+ palPtr = AccessUserObject(hpal);
+ if (!palPtr) return 0;
+
+ numEntries = palPtr->logpalette.palNumEntries;
+ if (Start >= numEntries)
+ {
+// GDI_ReleaseObj( hpalette );
+ return 0;
+ }
+ if (Start + Entries > numEntries) Entries = numEntries - Start;
+ memcpy(&palPtr->logpalette.palPalEntry[Start], pe, Entries * sizeof(PALETTEENTRY));
+ PALETTE_ValidateFlags(palPtr->logpalette.palPalEntry, palPtr->logpalette.palNumEntries);
+ ExFreePool(palPtr->logicalToSystem);
+ palPtr->logicalToSystem = NULL;
+// GDI_ReleaseObj( hpalette );
+ return Entries;
}
UINT STDCALL W32kSetSystemPaletteUse(HDC hDC,
BOOL STDCALL W32kUpdateColors(HDC hDC)
{
- UNIMPLEMENTED;
+ PDC dc;
+ HWND hWnd;
+ int size;
+/*
+ if (!(dc = AccessUserObject(hDC))) return 0;
+ size = dc->devCaps->sizePalette;
+// GDI_ReleaseObj( hDC );
+
+ if (Callout.WindowFromDC)
+ {
+ hWnd = Callout.WindowFromDC( hDC );
+
+ // Docs say that we have to remap current drawable pixel by pixel
+ // but it would take forever given the speed of XGet/PutPixel.
+ if (hWnd && size) Callout.RedrawWindow( hWnd, NULL, 0, RDW_INVALIDATE );
+ } */
+ return 0x666;
+}
+
+int COLOR_PaletteLookupPixel(PALETTEENTRY *palPalEntry, int size,
+ PXLATEOBJ XlateObj, COLORREF col, BOOL skipReserved)
+{
+ int i, best = 0, diff = 0x7fffffff;
+ int r, g, b;
+
+ for( i = 0; i < size && diff ; i++ )
+ {
+ if(!(palPalEntry[i].peFlags & PC_SYS_USED) || (skipReserved && palPalEntry[i].peFlags & PC_SYS_RESERVED))
+ continue;
+
+ r = palPalEntry[i].peRed - GetRValue(col);
+ g = palPalEntry[i].peGreen - GetGValue(col);
+ b = palPalEntry[i].peBlue - GetBValue(col);
+
+ r = r*r + g*g + b*b;
+
+ if( r < diff ) { best = i; diff = r; }
+ }
+ return (XlateObj->pulXlate) ? XlateObj->pulXlate[best] : best;
}
+COLORREF COLOR_LookupNearestColor( PALETTEENTRY* palPalEntry, int size, COLORREF color )
+{
+ unsigned char spec_type = color >> 24;
+ int i;
+ PALETTEENTRY *COLOR_sysPal = ReturnSystemPalette();
+
+ // we need logical palette for PALETTERGB and PALETTEINDEX colorrefs
+
+ if( spec_type == 2 ) /* PALETTERGB */
+ color = *(COLORREF*)(palPalEntry + COLOR_PaletteLookupPixel(palPalEntry,size,NULL,color,FALSE));
+
+ else if( spec_type == 1 ) /* PALETTEINDEX */
+ {
+ if( (i = color & 0x0000ffff) >= size )
+ {
+ DbgPrint("RGB(%lx) : idx %d is out of bounds, assuming NULL\n", color, i);
+ color = *(COLORREF*)palPalEntry;
+ }
+ else color = *(COLORREF*)(palPalEntry + i);
+ }
+
+ color &= 0x00ffffff;
+ return (0x00ffffff & *(COLORREF*)(COLOR_sysPal + COLOR_PaletteLookupPixel(COLOR_sysPal, 256, NULL, color, FALSE)));
+}
+
+int 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;
+}
/* Check for illegal parameters */
if (!XFormResult || !xform1 || !xform2)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
/* Create the result in a temporary XFORM, since xformResult may be
* equal to xform1 or xform2 */
- xformTemp.eM11 = xform1->eM11 * xform2->eM11 +
- xform1->eM12 * xform2->eM21;
- xformTemp.eM12 = xform1->eM11 * xform2->eM12 +
- xform1->eM12 * xform2->eM22;
- xformTemp.eM21 = xform1->eM21 * xform2->eM11 +
- xform1->eM22 * xform2->eM21;
- xformTemp.eM22 = xform1->eM21 * xform2->eM12 +
- xform1->eM22 * xform2->eM22;
- xformTemp.eDx = xform1->eDx * xform2->eM11 +
- xform1->eDy * xform2->eM21 + xform2->eDx;
- xformTemp.eDy = xform1->eDx * xform2->eM12 +
- xform1->eDy * xform2->eM22 + xform2->eDy;
+ xformTemp.eM11 = xform1->eM11 * xform2->eM11 + xform1->eM12 * xform2->eM21;
+ xformTemp.eM12 = xform1->eM11 * xform2->eM12 + xform1->eM12 * xform2->eM22;
+ xformTemp.eM21 = xform1->eM21 * xform2->eM11 + xform1->eM22 * xform2->eM21;
+ xformTemp.eM22 = xform1->eM21 * xform2->eM12 + xform1->eM22 * xform2->eM22;
+ xformTemp.eDx = xform1->eDx * xform2->eM11 + xform1->eDy * xform2->eM21 + xform2->eDx;
+ xformTemp.eDy = xform1->eDx * xform2->eM12 + xform1->eDy * xform2->eM22 + xform2->eDy;
/* Copy the result to xformResult */
*XFormResult = xformTemp;
dc = DC_HandleToPtr (hDC);
if (!dc)
- {
- return 0;
- }
+ {
+ return 0;
+ }
GraphicsMode = dc->w.GraphicsMode;
DC_UnlockDC (hDC);
dc = DC_HandleToPtr (hDC);
if (!dc)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
if (!XForm)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
*XForm = dc->w.xformWorld2Wnd;
DC_UnlockDC (hDC);
dc = DC_HandleToPtr (hDC);
if (!dc)
- {
-// SetLastError( ERROR_INVALID_HANDLE );
- return FALSE;
- }
+ {
+// SetLastError( ERROR_INVALID_HANDLE );
+ return FALSE;
+ }
if (!XForm)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
/* Check that graphics mode is GM_ADVANCED */
if (dc->w.GraphicsMode!=GM_ADVANCED)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
switch (Mode)
- {
+ {
case MWT_IDENTITY:
dc->w.xformWorld2Wnd.eM11 = 1.0f;
dc->w.xformWorld2Wnd.eM12 = 0.0f;
break;
case MWT_LEFTMULTIPLY:
- W32kCombineTransform(&dc->w.xformWorld2Wnd,
- XForm,
- &dc->w.xformWorld2Wnd );
+ W32kCombineTransform(&dc->w.xformWorld2Wnd, XForm, &dc->w.xformWorld2Wnd );
break;
case MWT_RIGHTMULTIPLY:
- W32kCombineTransform(&dc->w.xformWorld2Wnd,
- &dc->w.xformWorld2Wnd,
- XForm);
+ W32kCombineTransform(&dc->w.xformWorld2Wnd, &dc->w.xformWorld2Wnd, XForm);
break;
default:
return FALSE;
- }
+ }
DC_UpdateXforms (dc);
DC_UnlockDC (hDC);
dc = DC_HandleToPtr (hDC);
if (!dc)
- {
- return 0;
- }
+ {
+ return 0;
+ }
/* One would think that setting the graphics mode to GM_COMPATIBLE
* would also reset the world transformation matrix to the unity
*/
if ((Mode != GM_COMPATIBLE) && (Mode != GM_ADVANCED))
- {
- return 0;
- }
+ {
+ return 0;
+ }
ret = dc->w.GraphicsMode;
dc->w.GraphicsMode = Mode;
DC_UnlockDC (hDC);
dc = DC_HandleToPtr (hDC);
if (!dc)
- {
-// SetLastError( ERROR_INVALID_HANDLE );
- return FALSE;
- }
+ {
+// SetLastError( ERROR_INVALID_HANDLE );
+ return FALSE;
+ }
if (!XForm)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
/* Check that graphics mode is GM_ADVANCED */
if (dc->w.GraphicsMode != GM_ADVANCED)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
dc->w.xformWorld2Wnd = *XForm;
DC_UpdateXforms (dc);
DC_UnlockDC (hDC);
-/* $Id: dc.c,v 1.18 2000/07/07 01:20:53 phreak Exp $
+/* $Id: dc.c,v 1.19 2001/03/31 15:35:08 jfilby Exp $
*
* DC.C - Device context functions
*
#include <windows.h>
#include <ddk/ntddk.h>
-/* FIXME: Surely we should just have one include file that includes all of these.. */
#include <win32k/bitmaps.h>
#include <win32k/coord.h>
#include <win32k/driver.h>
// #define NDEBUG
#include <win32k/debug1.h>
-void TestEngXxx(PDC Dc)
-{
- BRUSHOBJ brushobj;
- HBITMAP GDIbmp;
- SURFOBJ *SurfObj, *GDIsurf;
- XLATEOBJ *RGBtoVGA16, *VGA16toRGB;
- RECTL DestBlt, myrect;
- SIZEL GDISize;
- CLIPOBJ *clipobj;
- POINTL SourcePnt;
- INT i;
-
- brushobj.iSolidColor = 1;
- SurfObj = AccessUserObject(Dc->Surface);
-
- /* Create a GDI managed bitmap */
- GDISize.cx = 100;
- GDISize.cy = 100;
-
- GDIbmp = EngCreateBitmap(GDISize, GDISize.cx * 3, BMF_24BPP, BMF_TOPDOWN,
- NULL);
-
- // Get GDI surface's object
- GDIsurf = AccessUserObject(GDIbmp);
-
- /* Create color translation Xlates */
-
- // Create color translation for RGB to the VGA's 16 colors
- RGBtoVGA16 = EngCreateXlate(PAL_INDEXED, PAL_RGB,
- Dc->DevInfo.hpalDefault, NULL);
-
- // Create color translation for RGB to the VGA's 16 colors
- VGA16toRGB = EngCreateXlate(PAL_RGB, PAL_INDEXED,
- NULL, Dc->DevInfo.hpalDefault);
-
- /* Line Tests */
-
- // Diagonals
- EngLineTo(SurfObj, NULL, &brushobj, 0, 0, 639, 479, NULL, NULL);
- EngLineTo(SurfObj, NULL, &brushobj, 639, 0, 0, 479, NULL, NULL);
-
- // Border
- EngLineTo(SurfObj, NULL, &brushobj, 0, 0, 639, 0, NULL, NULL);
- EngLineTo(SurfObj, NULL, &brushobj, 639, 0, 639, 479, NULL, NULL);
- EngLineTo(SurfObj, NULL, &brushobj, 639, 479, 0, 479, NULL, NULL);
- EngLineTo(SurfObj, NULL, &brushobj, 0, 479, 0, 0, NULL, NULL);
-
- /* Paint Tests */
-
- // Colored blocks
- for (i=0; i<16; i++)
- {
- myrect.left=10+i*20;
- myrect.top=10;
- myrect.right=30+i*20;
- myrect.bottom=30;
- clipobj = EngCreateClipRegion(1, &myrect, TC_RECTANGLES, NULL);
- brushobj.iSolidColor = i;
- EngPaint(SurfObj, clipobj, &brushobj, NULL, 0xFF);
- EngDeleteClipRegion(clipobj);
- }
-
- /* BitBlt */
-
- // Blt VGA to GDI
- DestBlt.left=0; DestBlt.top=0; DestBlt.right=100, DestBlt.bottom=100;
- SourcePnt.x=10; SourcePnt.y=10;
- EngBitBlt(GDIsurf, SurfObj, NULL, NULL, VGA16toRGB, &DestBlt, &SourcePnt,
- NULL, NULL, NULL, NULL);
-
- // Blt to VGA again
- DestBlt.left=300; DestBlt.top=300; DestBlt.right=400, DestBlt.bottom=400;
- SourcePnt.x=0; SourcePnt.y=0;
- EngBitBlt(SurfObj, GDIsurf, NULL, NULL, RGBtoVGA16, &DestBlt, &SourcePnt,
- NULL, NULL, NULL, NULL);
-}
-
/* FIXME: DCs should probably be thread safe */
/*
func_type ft; \
PDC dc = DC_HandleToPtr( hdc ); \
if (!dc) \
- { \
- return 0; \
- } \
+ { \
+ return 0; \
+ } \
ft = dc->dc_field; \
DC_UnlockDC(dc); \
return ft; \
{ \
PDC dc = DC_HandleToPtr( hdc ); \
if (!dc) \
- { \
- return FALSE; \
- } \
+ { \
+ return FALSE; \
+ } \
((LPPOINT)pt)->x = dc->ret_x; \
((LPPOINT)pt)->y = dc->ret_y; \
DC_UnlockDC(dc); \
INT prevMode; \
PDC dc = DC_HandleToPtr( hdc ); \
if(!dc) \
- { \
- return 0; \
- } \
- if ((mode < min_val) || (mode > max_val)) \
- { \
- return 0; \
- } \
- prevMode = dc->dc_field; \
- dc->dc_field = mode; \
- DC_UnlockDC(hdc); \
- return prevMode; \
+ { \
+ return 0; \
+ } \
+ if ((mode < min_val) || (mode > max_val)) \
+ { \
+ return 0; \
+ } \
+ prevMode = dc->dc_field; \
+ dc->dc_field = mode; \
+ DC_UnlockDC(hdc); \
+ return prevMode; \
}
// --------------------------------------------------------- File Statics
+static HDC hDISPLAY_DC = NULL; // handle to the DISPLAY HDC
static void W32kSetDCState16(HDC hDC, HDC hDCSave);
// ----------------------------------------------------- Public Functions
+HDC RetrieveDisplayHDC()
+{
+ return hDISPLAY_DC;
+}
+
BOOL STDCALL W32kCancelDC(HDC hDC)
{
UNIMPLEMENTED;
HDC STDCALL W32kCreateCompatableDC(HDC hDC)
{
- PDC NewDC, OrigDC;
+ PDC NewDC, OrigDC = NULL;
HBITMAP hBitmap;
- OrigDC = DC_HandleToPtr(hDC);
- if (OrigDC == NULL)
+ if(hDC == NULL)
+ {
+ // The OrigDC is one the DC created to reference the DISPLAY (we assume such a DC exists)
+ if(hDISPLAY_DC != NULL)
+ OrigDC = DC_HandleToPtr(hDISPLAY_DC);
+ } else {
+ OrigDC = DC_HandleToPtr(hDC);
+ if (OrigDC == NULL)
{
return 0;
}
-
+ }
+
/* Allocate a new DC based on the original DC's device */
NewDC = DC_AllocDC(OrigDC->DriverName);
+
if (NewDC == NULL)
- {
- DC_UnlockDC(OrigDC);
-
- return NULL;
- }
- DRIVER_ReferenceDriver (NewDC->DriverName);
-
+ {
+ DC_UnlockDC(OrigDC);
+ return NULL;
+ DRIVER_ReferenceDriver (NewDC->DriverName);
+ }
+
/* Copy information from original DC to new DC */
NewDC->hSelf = NewDC;
/* FIXME: Should this DC request its own PDEV? */
NewDC->PDev = OrigDC->PDev;
-
NewDC->DMW = OrigDC->DMW;
memcpy(NewDC->FillPatternSurfaces,
OrigDC->FillPatternSurfaces,
NewDC->DevInfo = OrigDC->DevInfo;
/* FIXME: Should this DC request its own surface? */
+ /* Yes, in fact, a 1x1 monochrome surface (to be implemented..) */
NewDC->Surface = OrigDC->Surface;
- NewDC->DriverFunctions = OrigDC->DriverFunctions;
/* DriverName is copied in the AllocDC routine */
NewDC->DeviceDriver = OrigDC->DeviceDriver;
NewDC->wndOrgX = OrigDC->wndOrgX;
/* Create default bitmap */
if (!(hBitmap = W32kCreateBitmap( 1, 1, 1, 1, NULL )))
- {
- DC_FreeDC(NewDC);
- DC_UnlockDC(OrigDC);
+ {
+ DC_FreeDC(NewDC);
+ DC_UnlockDC(OrigDC);
- return NULL;
- }
+ return NULL;
+ }
NewDC->w.flags = DC_MEMORY;
- NewDC->w.bitsPerPixel = 1; /* FIXME: OrigDC->w.bitsPerPixel ? */
+ NewDC->w.bitsPerPixel = 1;
NewDC->w.hBitmap = hBitmap;
NewDC->w.hFirstBitmap = hBitmap;
+ NewDC->w.hPalette = OrigDC->w.hPalette;
DC_UnlockDC(NewDC);
DC_UnlockDC(OrigDC);
PDC NewDC;
HDC hDC = NULL;
DRVENABLEDATA DED;
-int i; // DELETEME
+ HDC hNewDC;
/* Check for existing DC object */
if ((NewDC = DC_FindOpenDC(Driver)) != NULL)
- {
- hDC = DC_PtrToHandle(NewDC);
- return W32kCreateCompatableDC(hDC);
- }
+ {
+ hDC = DC_PtrToHandle(NewDC);
+ return W32kCreateCompatableDC(hDC);
+ }
-DPRINT("NAME: %S\n", Driver);
+ DPRINT("NAME: %S\n", Driver); // FIXME: Should not crash if NULL
/* Allocate a DC object */
if ((NewDC = DC_AllocDC(Driver)) == NULL)
- {
- return NULL;
- }
+ {
+ return NULL;
+ }
/* Open the miniport driver */
if ((NewDC->DeviceDriver = DRIVER_FindMPDriver(Driver)) == NULL)
- {
- DPRINT("FindMPDriver failed\n");
- goto Failure;
- }
+ {
+ DPRINT("FindMPDriver failed\n");
+ goto Failure;
+ }
/* Get the DDI driver's entry point */
/* FIXME: Retrieve DDI driver name from registry */
if ((GDEnableDriver = DRIVER_FindDDIDriver(L"\\??\\C:\\reactos\\system32\\drivers\\vgaddi.dll")) == NULL)
- {
- DPRINT("FindDDIDriver failed\n");
- goto Failure;
- }
+ {
+ DPRINT("FindDDIDriver failed\n");
+ goto Failure;
+ }
/* Call DDI driver's EnableDriver function */
RtlZeroMemory(&DED, sizeof(DED));
if (!GDEnableDriver(DDI_DRIVER_VERSION, sizeof(DED), &DED))
- {
- DPRINT("DrvEnableDriver failed\n");
- goto Failure;
- }
-DPRINT("Building DDI Functions\n");
+ {
+ DPRINT("DrvEnableDriver failed\n");
+ goto Failure;
+ }
+ DPRINT("Building DDI Functions\n");
/* Construct DDI driver function dispatch table */
if (!DRIVER_BuildDDIFunctions(&DED, &NewDC->DriverFunctions))
- {
- DPRINT("BuildDDIFunctions failed\n");
- goto Failure;
- }
+ {
+ DPRINT("BuildDDIFunctions failed\n");
+ goto Failure;
+ }
/* Allocate a phyical device handle from the driver */
if (Device != NULL)
- {
-DPRINT("Device in u: %u\n", Device);
-// wcsncpy(NewDC->DMW.dmDeviceName, Device, DMMAXDEVICENAME); FIXME: this crashes everything?
- }
+ {
+ DPRINT("Device in u: %u\n", Device);
+// wcsncpy(NewDC->DMW.dmDeviceName, Device, DMMAXDEVICENAME); FIXME: this crashes everything?
+ }
NewDC->DMW.dmSize = sizeof(NewDC->DMW);
NewDC->DMW.dmFields = 0x000fc000;
/* FIXME: get mode selection information from somewhere */
NewDC->DMW.dmLogPixels = 96;
- NewDC->DMW.dmBitsPerPel = 8;
+ NewDC->DMW.dmBitsPerPel = 4;
NewDC->DMW.dmPelsWidth = 640;
NewDC->DMW.dmPelsHeight = 480;
NewDC->DMW.dmDisplayFlags = 0;
NewDC->DMW.dmDisplayFrequency = 0;
- NewDC->w.bitsPerPixel = 8; // FIXME: set this here??
+ NewDC->w.bitsPerPixel = 4; // FIXME: set this here??
-DPRINT("Enabling PDev\n");
+ DPRINT("Enabling PDev\n");
NewDC->PDev = NewDC->DriverFunctions.EnablePDev(&NewDC->DMW,
L"",
L"",
NewDC->DeviceDriver);
if (NewDC->PDev == NULL)
- {
- DPRINT("DrvEnablePDEV failed\n");
- goto Failure;
- }
+ {
+ DPRINT("DrvEnablePDEV failed\n");
+ goto Failure;
+ }
-DPRINT("calling completePDev\n");
+ DPRINT("calling completePDev\n");
/* Complete initialization of the physical device */
NewDC->DriverFunctions.CompletePDev(NewDC->PDev, NewDC);
-DPRINT("calling DRIVER_ReferenceDriver\n");
+ DPRINT("calling DRIVER_ReferenceDriver\n");
DRIVER_ReferenceDriver (Driver);
-DPRINT("calling EnableSurface\n");
+ DPRINT("calling EnableSurface\n");
/* Enable the drawing surface */
NewDC->Surface = NewDC->DriverFunctions.EnableSurface(NewDC->PDev); // hsurf
+ NewDC->w.hPalette = NewDC->DevInfo.hpalDefault;
-DPRINT("Bits per pel: %u\n", NewDC->w.bitsPerPixel);
-
- /* Test EngXxx functions */
-// TestEngXxx(NewDC);
+ DPRINT("Bits per pel: %u\n", NewDC->w.bitsPerPixel);
/* Initialize the DC state */
DC_InitDC(NewDC);
+ hNewDC = DC_PtrToHandle(NewDC);
- return DC_PtrToHandle(NewDC);
+ // If we've created a DC for the DISPLAY, save the reference for later CreateCompatibleDC(NULL... usage
+ if(wcscmp(Driver, "DISPLAY")) // FIXME: this works.. but shouldn't we compare to L"DISPLAY" ? (which doesn't work..)
+ {
+ hDISPLAY_DC = hNewDC;
+ }
+
+ return hNewDC;
Failure:
DC_FreeDC(NewDC);
return FALSE;
}
DPRINT( "Deleting DC\n" );
- if (!DRIVER_UnreferenceDriver (DCToDelete->DriverName))
- {
- DPRINT( "No more references to driver, reseting display\n" );
- DCToDelete->DriverFunctions.DisableSurface(DCToDelete->PDev);
- CHECKPOINT;
- DCToDelete->DriverFunctions.AssertMode( DCToDelete->PDev, FALSE );
- CHECKPOINT;
- DCToDelete->DriverFunctions.DisablePDev(DCToDelete->PDev);
- }
+ if ((!DRIVER_UnreferenceDriver (DCToDelete->DriverName)) &&
+ (!(DCToDelete->w.flags & DC_MEMORY))) // Don't reset the display if its a memory DC
+ {
+ DPRINT( "No more references to driver, reseting display\n" );
+ DCToDelete->DriverFunctions.DisableSurface(DCToDelete->PDev);
+ CHECKPOINT;
+ DCToDelete->DriverFunctions.AssertMode( DCToDelete->PDev, FALSE );
+ CHECKPOINT;
+ DCToDelete->DriverFunctions.DisablePDev(DCToDelete->PDev);
+ }
CHECKPOINT;
/* First delete all saved DCs */
while (DCToDelete->saveLevel)
- {
- PDC savedDC;
- HDC savedHDC;
+ {
+ PDC savedDC;
+ HDC savedHDC;
- savedHDC = GDIOBJ_GetNextObject (DCHandle, GO_DC_MAGIC);
- savedDC = DC_HandleToPtr (savedHDC);
- if (savedDC == NULL)
- {
- break;
- }
- GDIOBJ_SetNextObject (DCHandle, GO_DC_MAGIC, GDIOBJ_GetNextObject (savedHDC, GO_DC_MAGIC));
- DCToDelete->saveLevel--;
- DC_UnlockDC (savedDC);
- W32kDeleteDC (savedHDC);
+ savedHDC = GDIOBJ_GetNextObject (DCHandle, GO_DC_MAGIC);
+ savedDC = DC_HandleToPtr (savedHDC);
+ if (savedDC == NULL)
+ {
+ break;
}
+ GDIOBJ_SetNextObject (DCHandle, GO_DC_MAGIC, GDIOBJ_GetNextObject (savedHDC, GO_DC_MAGIC));
+ DCToDelete->saveLevel--;
+ DC_UnlockDC (savedDC);
+ W32kDeleteDC (savedHDC);
+ }
/* Free GDI resources allocated to this DC */
if (!(DCToDelete->w.flags & DC_SAVED))
+ {
+ /* DC_UnlockDC (DCToDelete);
+ W32kSelectObject (DCHandle, STOCK_BLACK_PEN);
+ W32kSelectObject (DCHandle, STOCK_WHITE_BRUSH);
+ W32kSelectObject (DCHandle, STOCK_SYSTEM_FONT);
+ DC_LockDC (DCHandle); W32kSelectObject does not recognize stock objects yet */
+ if (DCToDelete->w.flags & DC_MEMORY)
{
- /* DC_UnlockDC (DCToDelete);
- W32kSelectObject (DCHandle, STOCK_BLACK_PEN);
- W32kSelectObject (DCHandle, STOCK_WHITE_BRUSH);
- W32kSelectObject (DCHandle, STOCK_SYSTEM_FONT);
- DC_LockDC (DCHandle); W32kSelectObject does not recognize stock objects yet */
- if (DCToDelete->w.flags & DC_MEMORY)
- {
- W32kDeleteObject (DCToDelete->w.hFirstBitmap);
- }
+ W32kDeleteObject (DCToDelete->w.hFirstBitmap);
}
+ }
if (DCToDelete->w.hClipRgn)
- {
- W32kDeleteObject (DCToDelete->w.hClipRgn);
- }
+ {
+ W32kDeleteObject (DCToDelete->w.hClipRgn);
+ }
if (DCToDelete->w.hVisRgn)
- {
- W32kDeleteObject (DCToDelete->w.hVisRgn);
- }
+ {
+ W32kDeleteObject (DCToDelete->w.hVisRgn);
+ }
if (DCToDelete->w.hGCClipRgn)
- {
- W32kDeleteObject (DCToDelete->w.hGCClipRgn);
- }
+ {
+ W32kDeleteObject (DCToDelete->w.hGCClipRgn);
+ }
#if 0 /* FIXME */
PATH_DestroyGdiPath (&DCToDelete->w.path);
#endif
BOOL STDCALL W32kDeleteObject(HGDIOBJ hObject)
{
- PGDIOBJ Obj;
- PGDIOBJHDR ObjHdr;
-
- Obj = GDIOBJ_HandleToPtr( hObject, GO_MAGIC_DONTCARE );
- if( !Obj )
+ PGDIOBJ Obj;
+ PGDIOBJHDR ObjHdr;
+
+ Obj = GDIOBJ_HandleToPtr( hObject, GO_MAGIC_DONTCARE );
+ if( !Obj )
+ return FALSE;
+ ObjHdr = (PGDIOBJHDR)(((PCHAR)Obj) - sizeof (GDIOBJHDR));
+ switch( ObjHdr->wMagic )
+ {
+ case GO_BITMAP_MAGIC: {
+ DPRINT( "Deleting bitmap\n" );
+ ExFreePool( ((PBITMAPOBJ)Obj)->bitmap.bmBits );
+ BITMAPOBJ_FreeBitmap( Obj );
+ break;
+ }
+ default: {
+ DPRINT( "W32kDeleteObject: Deleting object of unknown type %x\n", ObjHdr->wMagic );
return FALSE;
- ObjHdr = (PGDIOBJHDR)(((PCHAR)Obj) - sizeof (GDIOBJHDR));
- switch( ObjHdr->wMagic )
- {
- case GO_BITMAP_MAGIC: {
- DPRINT( "Deleting bitmap\n" );
- ExFreePool( ((PBITMAPOBJ)Obj)->bitmap.bmBits );
- BITMAPOBJ_FreeBitmap( Obj );
- break;
- }
- default: {
- DPRINT( "W32kDeleteObject: Deleting object of unknown type %x\n", ObjHdr->wMagic );
- return FALSE;
- }
- }
- return TRUE;
+ }
+ }
+ return TRUE;
}
INT STDCALL W32kDrawEscape(HDC hDC,
DC * dc;
if (!Point)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
dc = DC_HandleToPtr(hDC);
if (dc == NULL)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
Point->x = Point->y = 0;
dc = DC_HandleToPtr(hDC);
if (dc == NULL)
- {
- return 0;
- }
+ {
+ return 0;
+ }
newdc = DC_AllocDC(NULL);
if (newdc == NULL)
- {
- DC_UnlockDC(hDC);
- return 0;
- }
+ {
+ DC_UnlockDC(hDC);
+ return 0;
+ }
newdc->w.flags = dc->w.flags | DC_SAVED;
#if 0
newdc->w.hGCClipRgn = newdc->w.hVisRgn = 0;
#endif
if (dc->w.hClipRgn)
- {
- newdc->w.hClipRgn = W32kCreateRectRgn( 0, 0, 0, 0 );
- W32kCombineRgn( newdc->w.hClipRgn, dc->w.hClipRgn, 0, RGN_COPY );
- }
+ {
+ newdc->w.hClipRgn = W32kCreateRectRgn( 0, 0, 0, 0 );
+ W32kCombineRgn( newdc->w.hClipRgn, dc->w.hClipRgn, 0, RGN_COPY );
+ }
else
- {
- newdc->w.hClipRgn = 0;
- }
+ {
+ newdc->w.hClipRgn = 0;
+ }
DC_UnlockDC(hDC);
return newdc->hSelf;
dc = DC_HandleToPtr(hDC);
if (dc == NULL)
- {
- return 0;
- }
+ {
+ return 0;
+ }
/* Device capabilities for the printer */
switch (Index)
- {
+ {
case PHYSICALWIDTH:
if(W32kEscape(hDC, GETPHYSPAGESIZE, 0, NULL, (LPVOID)&pt) > 0)
- {
- return pt.x;
- }
+ {
+ return pt.x;
+ }
break;
case PHYSICALHEIGHT:
if(W32kEscape(hDC, GETPHYSPAGESIZE, 0, NULL, (LPVOID)&pt) > 0)
- {
- return pt.y;
- }
+ {
+ return pt.y;
+ }
break;
case PHYSICALOFFSETX:
if(W32kEscape(hDC, GETPRINTINGOFFSET, 0, NULL, (LPVOID)&pt) > 0)
- {
- return pt.x;
- }
+ {
+ return pt.x;
+ }
break;
case PHYSICALOFFSETY:
if(W32kEscape(hDC, GETPRINTINGOFFSET, 0, NULL, (LPVOID)&pt) > 0)
- {
- return pt.y;
- }
+ {
+ return pt.y;
+ }
break;
case SCALINGFACTORX:
if(W32kEscape(hDC, GETSCALINGFACTOR, 0, NULL, (LPVOID)&pt) > 0)
- {
- return pt.x;
- }
+ {
+ return pt.x;
+ }
break;
case SCALINGFACTORY:
if(W32kEscape(hDC, GETSCALINGFACTOR, 0, NULL, (LPVOID)&pt) > 0)
- {
- return pt.y;
- }
+ {
+ return pt.y;
+ }
break;
- }
+ }
- if ((Index < 0) || (Index > sizeof(DEVICECAPS) - sizeof(WORD)))
- {
- DC_UnlockDC(hDC);
- return 0;
- }
+ if ((Index < 0) || (Index > sizeof(DEVICECAPS) - sizeof(WORD)))
+ {
+ DC_UnlockDC(hDC);
+ return 0;
+ }
- DPRINT("(%04x,%d): returning %d\n",
- hDC, Index, *(WORD *)(((char *)dc->w.devCaps) + Index));
+ DPRINT("(%04x,%d): returning %d\n",
+ hDC, Index, *(WORD *)(((char *)dc->w.devCaps) + Index));
ret = *(WORD *)(((char *)dc->w.devCaps) + Index);
DC_UnlockDC(hDC);
DC_GET_VAL( INT, W32kGetMapMode, w.MapMode )
DC_GET_VAL( INT, W32kGetPolyFillMode, w.polyFillMode )
-INT STDCALL W32kGetObject(HGDIOBJ hGDIObj,
- INT BufSize,
- LPVOID Object)
+INT STDCALL W32kGetObjectA(HANDLE handle, INT count, LPVOID buffer)
{
- UNIMPLEMENTED;
+ GDIOBJHDR * ptr;
+ INT result = 0;
+
+ if (!count) return 0;
+ if (!(ptr = GDIOBJ_HandleToPtr(handle, GO_MAGIC_DONTCARE))) return 0;
+
+ switch(ptr->wMagic)
+ {
+/* case GO_PEN_MAGIC:
+ result = PEN_GetObject((PENOBJ *)ptr, count, buffer);
+ break;
+ case GO_BRUSH_MAGIC:
+ result = BRUSH_GetObject((BRUSHOBJ *)ptr, count, buffer);
+ break; */
+ case GO_BITMAP_MAGIC:
+ result = BITMAP_GetObject((BITMAPOBJ *)ptr, count, buffer);
+ break;
+/* case GO_FONT_MAGIC:
+ result = FONT_GetObjectA((FONTOBJ *)ptr, count, buffer);
+
+ // FIXME: Fix the LOGFONT structure for the stock fonts
+
+ if ( (handle >= FIRST_STOCK_HANDLE) && (handle <= LAST_STOCK_HANDLE) )
+ FixStockFontSizeA(handle, count, buffer);
+ break;
+ case GO_PALETTE_MAGIC:
+ result = PALETTE_GetObject((PALETTEOBJ *)ptr, count, buffer);
+ break; */
+
+ case GO_REGION_MAGIC:
+ case GO_DC_MAGIC:
+ case GO_DISABLED_DC_MAGIC:
+ case GO_META_DC_MAGIC:
+ case GO_METAFILE_MAGIC:
+ case GO_METAFILE_DC_MAGIC:
+ case GO_ENHMETAFILE_MAGIC:
+ case GO_ENHMETAFILE_DC_MAGIC:
+ // FIXME("Magic %04x not implemented\n", ptr->wMagic);
+ break;
+
+ default:
+ DbgPrint("Invalid GDI Magic %04x\n", ptr->wMagic);
+ break;
+ }
+ GDIOBJ_UnlockObject(handle);
+ return result;
+}
+
+INT STDCALL W32kGetObjectW(HANDLE handle, INT count, LPVOID buffer)
+{
+ GDIOBJHDR * ptr;
+ INT result = 0;
+
+ if (!count) return 0;
+ if (!(ptr = GDIOBJ_HandleToPtr(handle, GO_MAGIC_DONTCARE))) return 0;
+
+ switch(ptr->wMagic)
+ {
+/* case GO_PEN_MAGIC:
+ result = PEN_GetObject((PENOBJ *)ptr, count, buffer);
+ break;
+ case GO_BRUSH_MAGIC:
+ result = BRUSH_GetObject((BRUSHOBJ *)ptr, count, buffer);
+ break; */
+ case GO_BITMAP_MAGIC:
+ result = BITMAP_GetObject((BITMAPOBJ *)ptr, count, buffer);
+ break;
+/* case GO_FONT_MAGIC:
+ result = FONT_GetObjectW((FONTOBJ *)ptr, count, buffer);
+
+ // Fix the LOGFONT structure for the stock fonts
+
+ if ( (handle >= FIRST_STOCK_HANDLE) && (handle <= LAST_STOCK_HANDLE) )
+ FixStockFontSizeW(handle, count, buffer);
+ break;
+ case GO_PALETTE_MAGIC:
+ result = PALETTE_GetObject((PALETTEOBJ *)ptr, count, buffer);
+ break; */
+ default:
+ // FIXME("Magic %04x not implemented\n", ptr->wMagic);
+ break;
+ }
+ GDIOBJ_UnlockObject(handle);
+ return result;
}
-DWORD STDCALL W32kGetObjectType(HGDIOBJ hGDIObj)
+INT STDCALL W32kGetObject(HANDLE handle, INT count, LPVOID buffer)
{
- UNIMPLEMENTED;
+ return W32kGetObjectW(handle, count, buffer);
}
-DC_GET_VAL( INT, W32kGetRelAbs, w.relAbsMode )
-DC_GET_VAL( INT, W32kGetROP2, w.ROPmode )
-DC_GET_VAL( INT, W32kGetStretchBltMode, w.stretchBltMode )
-
-HGDIOBJ STDCALL W32kGetStockObject(INT Object)
+DWORD STDCALL W32kGetObjectType(HANDLE handle)
{
- UNIMPLEMENTED;
+ GDIOBJHDR * ptr;
+ INT result = 0;
+
+ if (!(ptr = GDIOBJ_HandleToPtr(handle, GO_MAGIC_DONTCARE))) return 0;
+
+ switch(ptr->wMagic)
+ {
+ case GO_PEN_MAGIC:
+ result = OBJ_PEN;
+ break;
+ case GO_BRUSH_MAGIC:
+ result = OBJ_BRUSH;
+ break;
+ case GO_BITMAP_MAGIC:
+ result = OBJ_BITMAP;
+ break;
+ case GO_FONT_MAGIC:
+ result = OBJ_FONT;
+ break;
+ case GO_PALETTE_MAGIC:
+ result = OBJ_PAL;
+ break;
+ case GO_REGION_MAGIC:
+ result = OBJ_REGION;
+ break;
+ case GO_DC_MAGIC:
+ result = OBJ_DC;
+ break;
+ case GO_META_DC_MAGIC:
+ result = OBJ_METADC;
+ break;
+ case GO_METAFILE_MAGIC:
+ result = OBJ_METAFILE;
+ break;
+ case GO_METAFILE_DC_MAGIC:
+ result = OBJ_METADC;
+ break;
+ case GO_ENHMETAFILE_MAGIC:
+ result = OBJ_ENHMETAFILE;
+ break;
+ case GO_ENHMETAFILE_DC_MAGIC:
+ result = OBJ_ENHMETADC;
+ break;
+ default:
+ // FIXME("Magic %04x not implemented\n", ptr->wMagic);
+ break;
+ }
+ GDIOBJ_UnlockObject(handle);
+ return result;
}
+DC_GET_VAL( INT, W32kGetRelAbs, w.relAbsMode )
+DC_GET_VAL( INT, W32kGetROP2, w.ROPmode )
+DC_GET_VAL( INT, W32kGetStretchBltMode, w.stretchBltMode )
DC_GET_VAL( UINT, W32kGetTextAlign, w.textAlign )
DC_GET_VAL( COLORREF, W32kGetTextColor, w.textColor )
DC_GET_VAL_EX( W32kGetViewportExtEx, vportExtX, vportExtY, SIZE )
dc = DC_HandleToPtr(hDC);
if(!dc)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
if (SaveLevel == -1)
- {
- SaveLevel = dc->saveLevel;
- }
+ {
+ SaveLevel = dc->saveLevel;
+ }
if ((SaveLevel < 1) || (SaveLevel > dc->saveLevel))
- {
- DC_UnlockDC(hDC);
-
- return FALSE;
- }
+ {
+ DC_UnlockDC(hDC);
+ return FALSE;
+ }
success = TRUE;
while (dc->saveLevel >= SaveLevel)
- {
- HDC hdcs = GDIOBJ_GetNextObject (hDC, GO_DC_MAGIC);
+ {
+ HDC hdcs = GDIOBJ_GetNextObject (hDC, GO_DC_MAGIC);
- dcs = DC_HandleToPtr (hdcs);
- if (dcs == NULL)
+ dcs = DC_HandleToPtr (hdcs);
+ if (dcs == NULL)
+ {
+ DC_UnlockDC (hDC);
+ return FALSE;
+ }
+ GDIOBJ_SetNextObject (hDC, GO_DC_MAGIC, GDIOBJ_GetNextObject (hdcs, GO_DC_MAGIC));
+ if (--dc->saveLevel < SaveLevel)
+ {
+ W32kSetDCState16 (hDC, hdcs);
+#if 0
+ if (!PATH_AssignGdiPath( &dc->w.path, &dcs->w.path ))
{
- DC_UnlockDC (hDC);
-
- return FALSE;
+ /* FIXME: This might not be quite right, since we're
+ * returning FALSE but still destroying the saved DC state */
+ success = FALSE;
}
- GDIOBJ_SetNextObject (hDC, GO_DC_MAGIC, GDIOBJ_GetNextObject (hdcs, GO_DC_MAGIC));
- if (--dc->saveLevel < SaveLevel)
- {
- W32kSetDCState16 (hDC, hdcs);
-#if 0
- 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;
- }
#endif
- }
- W32kDeleteDC (hdcs);
- }
+ }
+ W32kDeleteDC (hdcs);
+ }
DC_UnlockDC (hDC);
return success;
dc = DC_HandleToPtr (hDC);
if (dc == NULL)
- {
- return 0;
- }
+ {
+ return 0;
+ }
if (!(hdcs = W32kGetDCState16 (hDC)))
- {
- DC_UnlockDC (hDC);
-
- return 0;
- }
+ {
+ DC_UnlockDC (hDC);
+ return 0;
+ }
dcs = DC_HandleToPtr (hdcs);
#if 0
* when copying paths).
*/
if (!PATH_AssignGdiPath (&dcs->w.path, &dc->w.path))
- {
- DC_UnlockDC (hdc);
- DC_UnlockDC (hdcs);
- W32kDeleteDC (hdcs);
- return 0;
- }
+ {
+ DC_UnlockDC (hdc);
+ DC_UnlockDC (hdcs);
+ W32kDeleteDC (hdcs);
+ return 0;
+ }
#endif
GDIOBJ_SetNextObject (hdcs, GO_DC_MAGIC, GDIOBJ_GetNextObject (hDC, GO_DC_MAGIC));
HGDIOBJ STDCALL W32kSelectObject(HDC hDC, HGDIOBJ hGDIObj)
{
- HGDIOBJ objOrg;
- GDIOBJHDR *GdiObjHdr;
- BITMAPOBJ *pb;
- PSURFOBJ surfobj;
- PSURFGDI surfgdi;
- PDC dc;
-
- if(!hDC || !hGDIObj) return NULL;
-
- dc = DC_HandleToPtr(hDC);
- GdiObjHdr = hGDIObj;
-
- // FIXME: Get object handle from GDIObj and use it instead of GDIObj below?
-
- switch(GdiObjHdr->wMagic) {
- case GO_PEN_MAGIC:
- objOrg = (HGDIOBJ)dc->w.hPen;
- dc->w.hPen = hGDIObj;
- break;
- case GO_BRUSH_MAGIC:
- objOrg = (HGDIOBJ)dc->w.hBrush;
- dc->w.hBrush = (BRUSHOBJ *)GdiObjHdr;
- break;
+ HGDIOBJ objOrg;
+ GDIOBJHDR *GdiObjHdr;
+ BITMAPOBJ *pb;
+ PSURFOBJ surfobj;
+ PSURFGDI surfgdi;
+ PDC dc;
+ PPENOBJ pen;
+ PXLATEOBJ XlateObj;
+ PPALGDI PalGDI;
+
+ if(!hDC || !hGDIObj) return NULL;
+
+ dc = DC_HandleToPtr(hDC);
+ GdiObjHdr = hGDIObj;
+
+ // FIXME: Get object handle from GDIObj and use it instead of GDIObj below?
+
+ switch(GdiObjHdr->wMagic) {
+ case GO_PEN_MAGIC:
+ objOrg = (HGDIOBJ)dc->w.hPen;
+ dc->w.hPen = hGDIObj;
+
+ // Convert the color of the pen to the format of the DC
+ PalGDI = AccessInternalObject(dc->w.hPalette);
+ XlateObj = EngCreateXlate(PalGDI->Mode, PAL_RGB, dc->w.hPalette, NULL);
+ pen = GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC);
+ pen->logpen.lopnColor = XLATEOBJ_iXlate(XlateObj, pen->logpen.lopnColor);
+ break;
+ case GO_BRUSH_MAGIC:
+ objOrg = (HGDIOBJ)dc->w.hBrush;
+ dc->w.hBrush = (BRUSHOBJ *)GdiObjHdr;
+ break;
case GO_FONT_MAGIC:
- objOrg = (HGDIOBJ)dc->w.hFont;
- dc->w.hFont = (FONTOBJ *)GdiObjHdr;
- break;
- case GO_BITMAP_MAGIC:
- // must be memory dc to select bitmap
- if (!(dc->w.flags & DC_MEMORY))
- return NULL;
- objOrg = (HGDIOBJ)dc->w.hBitmap;
-
- // setup mem dc for drawing into bitmap
- pb = BITMAPOBJ_HandleToPtr(GdiObjHdr);
- surfobj = ExAllocatePool(PagedPool, sizeof(SURFOBJ));
- surfgdi = ExAllocatePool(PagedPool, sizeof(SURFGDI));
- BitmapToSurf(surfgdi, surfobj, pb);
-
- dc->w.hBitmap = (BITMAPOBJ *)GdiObjHdr;
- dc->Surface = CreateGDIHandle(surfgdi, surfobj);
-
- break;
+ objOrg = (HGDIOBJ)dc->w.hFont;
+ dc->w.hFont = (FONTOBJ *)GdiObjHdr;
+ break;
+ case GO_BITMAP_MAGIC:
+ // must be memory dc to select bitmap
+ if (!(dc->w.flags & DC_MEMORY)) return NULL;
+ objOrg = (HGDIOBJ)dc->w.hBitmap;
+
+ // setup mem dc for drawing into bitmap
+ pb = BITMAPOBJ_HandleToPtr(GdiObjHdr);
+ surfobj = ExAllocatePool(PagedPool, sizeof(SURFOBJ));
+ surfgdi = ExAllocatePool(PagedPool, sizeof(SURFGDI));
+
+ BitmapToSurf(hDC, surfgdi, surfobj, pb); // Put the bitmap in a surface
+ dc->w.hBitmap = CreateGDIHandle(surfgdi, surfobj); // Assign the DC's bitmap
+ dc->Surface = dc->w.hBitmap;
+
+ // if we're working with a DIB, get the palette [fixme: only create if the selected palette is null]
+ if(pb->dib)
+ {
+ if((pb->dib->dsBmih.biBitCount > 8) && (pb->dib->dsBmih.biBitCount < 24))
+ {
+ dc->w.hPalette = EngCreatePalette(PAL_BITFIELDS, pb->dib->dsBmih.biClrUsed, NULL, 0, 0, 0);
+ } else
+ if(pb->dib->dsBmih.biBitCount >= 24)
+ {
+ dc->w.hPalette = EngCreatePalette(PAL_RGB, pb->dib->dsBmih.biClrUsed, NULL, 0, 0, 0);
+ }
+ }
+ break;
#if UPDATEREGIONS
- case GO_REGION_MAGIC:
- /* objOrg = (HGDIOBJ)hDC->region; */
- objOrg = NULL; /* FIXME? hDC->region is destroyed below */
- SelectClipRgn(hDC, (HRGN)GdiObjHdr);
- break;
+ case GO_REGION_MAGIC:
+ /* objOrg = (HGDIOBJ)hDC->region; */
+ objOrg = NULL; /* FIXME? hDC->region is destroyed below */
+ SelectClipRgn(hDC, (HRGN)GdiObjHdr);
+ break;
#endif
- default:
+ default:
return NULL;
- }
+ }
- return objOrg;
+ return objOrg;
}
DC_SET_MODE( W32kSetBkMode, w.backgroundMode, TRANSPARENT, OPAQUE )
PDC dc = DC_HandleToPtr(hDC);
if (!dc)
- {
- return 0x80000000;
- }
+ {
+ return 0x80000000;
+ }
oldColor = dc->w.backgroundColor;
dc->w.backgroundColor = color;
dc = DC_HandleToPtr(hDC);
if (dc == NULL)
- {
- return;
- }
+ {
+ return;
+ }
dcs = DC_HandleToPtr(hDCSave);
if (dcs == NULL)
- {
- DC_UnlockDC(hDC);
-
- return;
- }
+ {
+ DC_UnlockDC(hDC);
+ return;
+ }
if (!dcs->w.flags & DC_SAVED)
- {
- DC_UnlockDC(hDC);
- DC_UnlockDC(hDCSave);
-
- return;
- }
+ {
+ DC_UnlockDC(hDC);
+ DC_UnlockDC(hDCSave);
+ return;
+ }
dc->w.flags = dcs->w.flags & ~DC_SAVED;
dc->vportExtY = dcs->vportExtY;
if (!(dc->w.flags & DC_MEMORY))
- {
- dc->w.bitsPerPixel = dcs->w.bitsPerPixel;
- }
+ {
+ dc->w.bitsPerPixel = dcs->w.bitsPerPixel;
+ }
#if 0
if (dcs->w.hClipRgn)
+ {
+ if (!dc->w.hClipRgn)
{
- if (!dc->w.hClipRgn)
- {
- dc->w.hClipRgn = W32kCreateRectRgn( 0, 0, 0, 0 );
- }
- W32kCombineRgn( dc->w.hClipRgn, dcs->w.hClipRgn, 0, RGN_COPY );
+ dc->w.hClipRgn = W32kCreateRectRgn( 0, 0, 0, 0 );
}
+ W32kCombineRgn( dc->w.hClipRgn, dcs->w.hClipRgn, 0, RGN_COPY );
+ }
else
+ {
+ if (dc->w.hClipRgn)
{
- if (dc->w.hClipRgn)
- {
- W32kDeleteObject( dc->w.hClipRgn );
- }
-
- dc->w.hClipRgn = 0;
+ W32kDeleteObject( dc->w.hClipRgn );
}
+
+ dc->w.hClipRgn = 0;
+ }
CLIPPING_UpdateGCRegion( dc );
#endif
NewDC = (PDC) GDIOBJ_AllocObject(sizeof(DC), GO_DC_MAGIC);
if (NewDC == NULL)
- {
- return NULL;
- }
+ {
+ return NULL;
+ }
if (Driver != NULL)
- {
- NewDC->DriverName = ExAllocatePool(PagedPool,
- (wcslen(Driver) + 1) * sizeof(WCHAR));
- wcscpy(NewDC->DriverName, Driver);
- }
+ {
+ NewDC->DriverName = ExAllocatePool(PagedPool, (wcslen(Driver) + 1) * sizeof(WCHAR));
+ wcscpy(NewDC->DriverName, Driver);
+ }
return NewDC;
}
PDC DC_FindOpenDC(LPCWSTR Driver)
{
- /* FIXME */
- return NULL;
+ /* FIXME: This is just a hack to return the pointer to the DISPLAY DC.. must cater for others too! */
+
+ if(wcscmp(Driver, "DISPLAY"))
+ {
+ return DC_HandleToPtr(hDISPLAY_DC);
+ }
+
+ return NULL;
+
}
void DC_InitDC(PDC DCToInit)
{
ExFreePool(DCToFree->DriverName);
if (!GDIOBJ_FreeObject((PGDIOBJ)DCToFree, GO_DC_MAGIC))
- {
- DPRINT("DC_FreeDC failed\n");
- }
+ {
+ DPRINT("DC_FreeDC failed\n");
+ }
}
void
xformWnd2Vport.eM12 = 0.0;
xformWnd2Vport.eM21 = 0.0;
xformWnd2Vport.eM22 = scaleY;
- xformWnd2Vport.eDx = (FLOAT)dc->vportOrgX -
- scaleX * (FLOAT)dc->wndOrgX;
- xformWnd2Vport.eDy = (FLOAT)dc->vportOrgY -
- scaleY * (FLOAT)dc->wndOrgY;
+ xformWnd2Vport.eDx = (FLOAT)dc->vportOrgX - scaleX * (FLOAT)dc->wndOrgX;
+ xformWnd2Vport.eDy = (FLOAT)dc->vportOrgY - scaleY * (FLOAT)dc->wndOrgY;
/* Combine with the world transformation */
- W32kCombineTransform(&dc->w.xformWorld2Vport,
- &dc->w.xformWorld2Wnd,
- &xformWnd2Vport );
+ W32kCombineTransform(&dc->w.xformWorld2Vport, &dc->w.xformWorld2Wnd, &xformWnd2Vport);
/* Create inverse of world-to-viewport transformation */
- dc->w.vport2WorldValid = DC_InvertXform(&dc->w.xformWorld2Vport,
- &dc->w.xformVport2World);
+ dc->w.vport2WorldValid = DC_InvertXform(&dc->w.xformWorld2Vport, &dc->w.xformVport2World);
}
BOOL
{
FLOAT determinant;
- determinant = xformSrc->eM11*xformSrc->eM22 -
- xformSrc->eM12*xformSrc->eM21;
+ determinant = xformSrc->eM11*xformSrc->eM22 - xformSrc->eM12*xformSrc->eM21;
if (determinant > -1e-12 && determinant < 1e-12)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
xformDest->eM11 = xformSrc->eM22 / determinant;
xformDest->eM12 = -xformSrc->eM12 / determinant;
xformDest->eM21 = -xformSrc->eM21 / determinant;
xformDest->eM22 = xformSrc->eM11 / determinant;
- xformDest->eDx = -xformSrc->eDx * xformDest->eM11 -
- xformSrc->eDy * xformDest->eM21;
- xformDest->eDy = -xformSrc->eDx * xformDest->eM12 -
- xformSrc->eDy * xformDest->eM22;
+ xformDest->eDx = -xformSrc->eDx * xformDest->eM11 - xformSrc->eDy * xformDest->eM21;
+ xformDest->eDy = -xformSrc->eDx * xformDest->eM12 - xformSrc->eDy * xformDest->eM22;
return TRUE;
}
--- /dev/null
+#undef WIN32_LEAN_AND_MEAN
+#include <windows.h>
+#include <stdlib.h>
+#include <win32k/bitmaps.h>
+#include <win32k/debug.h>
+#include <debug.h>
+#include "../eng/objects.h"
+#include <ntos/minmax.h>
+
+UINT STDCALL W32kSetDIBColorTable(HDC hDC,
+ UINT StartIndex,
+ UINT Entries,
+ CONST RGBQUAD *Colors)
+{
+ PDC dc;
+ PALETTEENTRY * palEntry;
+ PPALOBJ palette;
+ RGBQUAD *end;
+
+ if (!(dc = AccessUserObject(hDC))) return 0;
+
+ if (!(palette = AccessUserObject(dc->DevInfo.hpalDefault)))
+ {
+// GDI_ReleaseObj( hdc );
+ return 0;
+ }
+
+ // Transfer color info
+
+ if (dc->w.bitsPerPixel <= 8) {
+ palEntry = palette->logpalette.palPalEntry + StartIndex;
+ if (StartIndex + Entries > (1 << dc->w.bitsPerPixel))
+ Entries = (1 << dc->w.bitsPerPixel) - StartIndex;
+
+ if (StartIndex + Entries > palette->logpalette.palNumEntries)
+ Entries = palette->logpalette.palNumEntries - StartIndex;
+
+ for (end = Colors + Entries; Colors < end; palEntry++, Colors++)
+ {
+ palEntry->peRed = Colors->rgbRed;
+ palEntry->peGreen = Colors->rgbGreen;
+ palEntry->peBlue = Colors->rgbBlue;
+ }
+ } else {
+ Entries = 0;
+ }
+
+// GDI_ReleaseObj(dc->DevInfo.hpalDefault);
+// GDI_ReleaseObj(hdc);
+
+ return Entries;
+}
+
+// Converts a DIB to a device-dependent bitmap
+INT STDCALL W32kSetDIBits(HDC hDC,
+ HBITMAP hBitmap,
+ UINT StartScan,
+ UINT ScanLines,
+ CONST VOID *Bits,
+ CONST BITMAPINFO *bmi,
+ UINT ColorUse)
+{
+ DC *dc;
+ BITMAPOBJ *bitmap;
+ HBITMAP SourceBitmap, DestBitmap;
+ INT result;
+ BOOL copyBitsResult;
+ PSURFOBJ DestSurf, SourceSurf;
+ PSURFGDI DestGDI;
+ SIZEL SourceSize;
+ POINTL ZeroPoint;
+ RECTL DestRect;
+ PXLATEOBJ XlateObj;
+ PPALGDI hDCPalette;
+ RGBQUAD *lpRGB;
+ HPALETTE DDB_Palette, DIB_Palette;
+ USHORT DDB_Palette_Type, DIB_Palette_Type;
+
+
+ // Check parameters
+ if (!(dc = DC_HandleToPtr(hDC))) return 0;
+
+ if (!(bitmap = (BITMAPOBJ *)GDIOBJ_HandleToPtr(hBitmap, GO_BITMAP_MAGIC)))
+ {
+ // GDI_ReleaseObj(hDC);
+ return 0;
+ }
+
+ // Get RGB values
+ if (ColorUse == DIB_PAL_COLORS)
+ lpRGB = DIB_MapPaletteColors(hDC, bmi);
+ else
+ lpRGB = &bmi->bmiColors[0];
+
+ // Create a temporary surface for the destination bitmap
+ DestSurf = ExAllocatePool(PagedPool, sizeof(SURFOBJ));
+ DestGDI = ExAllocatePool(PagedPool, sizeof(SURFGDI));
+ DestBitmap = CreateGDIHandle(DestGDI, DestSurf);
+
+ BitmapToSurf(hDC, DestGDI, DestSurf, bitmap);
+
+ // Create source surface
+ SourceSize.cx = bmi->bmiHeader.biWidth;
+ SourceSize.cy = bmi->bmiHeader.biHeight;
+ SourceBitmap = EngCreateBitmap(SourceSize, DIB_GetDIBWidthBytes(SourceSize.cx, bmi->bmiHeader.biBitCount),
+ BitmapFormat(bmi->bmiHeader.biBitCount, bmi->bmiHeader.biCompression),
+ 0, Bits);
+ SourceSurf = AccessUserObject(SourceBitmap);
+
+ // Destination palette obtained from the hDC
+ hDCPalette = AccessInternalObject(dc->DevInfo.hpalDefault);
+ DDB_Palette_Type = hDCPalette->Mode;
+ DDB_Palette = dc->DevInfo.hpalDefault;
+
+ // Source palette obtained from the BITMAPINFO
+ DIB_Palette = BuildDIBPalette(bmi, &DIB_Palette_Type);
+
+ // Determine XLATEOBJ for color translation
+ XlateObj = EngCreateXlate(DDB_Palette_Type, DIB_Palette_Type, DDB_Palette, DIB_Palette);
+
+ // Determine destination rectangle and source point
+ ZeroPoint.x = 0;
+ ZeroPoint.y = 0;
+ DestRect.top = 0;
+ DestRect.left = 0;
+ DestRect.right = SourceSize.cx;
+ DestRect.bottom = SourceSize.cy;
+
+ copyBitsResult = EngCopyBits(DestSurf, SourceSurf, NULL, XlateObj, &DestRect, &ZeroPoint);
+
+ // Clean up
+ EngDeleteSurface(SourceBitmap);
+ EngDeleteSurface(DestBitmap);
+
+// if (ColorUse == DIB_PAL_COLORS)
+// WinFree((LPSTR)lpRGB);
+
+// GDI_ReleaseObj(hBitmap); unlock?
+// GDI_ReleaseObj(hDC);
+
+ return result;
+}
+
+INT STDCALL W32kSetDIBitsToDevice(HDC hDC,
+ INT XDest,
+ INT YDest,
+ DWORD Width,
+ DWORD Height,
+ INT XSrc,
+ INT YSrc,
+ UINT StartScan,
+ UINT ScanLines,
+ CONST VOID *Bits,
+ CONST BITMAPINFO *bmi,
+ UINT ColorUse)
+{
+
+}
+
+UINT STDCALL W32kGetDIBColorTable(HDC hDC,
+ UINT StartIndex,
+ UINT Entries,
+ RGBQUAD *Colors)
+{
+ UNIMPLEMENTED;
+}
+
+// Converts a device-dependent bitmap to a DIB
+INT STDCALL W32kGetDIBits(HDC hDC,
+ HBITMAP hBitmap,
+ UINT StartScan,
+ UINT ScanLines,
+ LPVOID Bits,
+ LPBITMAPINFO bi,
+ UINT Usage)
+{
+ UNIMPLEMENTED;
+}
+
+INT STDCALL W32kStretchDIBits(HDC hDC,
+ INT XDest,
+ INT YDest,
+ INT DestWidth,
+ INT DestHeight,
+ INT XSrc,
+ INT YSrc,
+ INT SrcWidth,
+ INT SrcHeight,
+ CONST VOID *Bits,
+ CONST BITMAPINFO *BitsInfo,
+ UINT Usage,
+ DWORD ROP)
+{
+ UNIMPLEMENTED;
+}
+
+LONG STDCALL W32kGetBitmapBits(HBITMAP hBitmap,
+ LONG Count,
+ LPVOID Bits)
+{
+ PBITMAPOBJ bmp;
+ LONG height, ret;
+
+ bmp = BITMAPOBJ_HandleToPtr (hBitmap);
+ if (!bmp)
+ {
+ return 0;
+ }
+
+ /* If the bits vector is null, the function should return the read size */
+ if (Bits == NULL)
+ {
+ return bmp->bitmap.bmWidthBytes * bmp->bitmap.bmHeight;
+ }
+
+ if (Count < 0)
+ {
+ DPRINT ("(%ld): Negative number of bytes passed???\n", Count);
+ Count = -Count;
+ }
+
+ /* Only get entire lines */
+ height = Count / bmp->bitmap.bmWidthBytes;
+ if (height > bmp->bitmap.bmHeight)
+ {
+ height = bmp->bitmap.bmHeight;
+ }
+ Count = height * bmp->bitmap.bmWidthBytes;
+ if (Count == 0)
+ {
+ DPRINT("Less then one entire line requested\n");
+ BITMAPOBJ_UnlockBitmap (hBitmap);
+ return 0;
+ }
+
+ DPRINT("(%08x, %ld, %p) %dx%d %d colors fetched height: %ld\n",
+ hBitmap, Count, Bits, bmp->bitmap.bmWidth, bmp->bitmap.bmHeight,
+ 1 << bmp->bitmap.bmBitsPixel, height );
+#if 0
+ /* FIXME: Call DDI CopyBits here if available */
+ if(bmp->DDBitmap)
+ {
+ DPRINT("Calling device specific BitmapBits\n");
+ if(bmp->DDBitmap->funcs->pBitmapBits)
+ {
+ ret = bmp->DDBitmap->funcs->pBitmapBits(hbitmap, bits, count,
+ DDB_GET);
+ }
+ else
+ {
+ ERR_(bitmap)("BitmapBits == NULL??\n");
+ ret = 0;
+ }
+ }
+ else
+#endif
+ {
+ if(!bmp->bitmap.bmBits)
+ {
+ DPRINT ("Bitmap is empty\n");
+ ret = 0;
+ }
+ else
+ {
+ memcpy(Bits, bmp->bitmap.bmBits, Count);
+ ret = Count;
+ }
+ }
+ BITMAPOBJ_UnlockBitmap (hBitmap);
+
+ return ret;
+}
+
+// The CreateDIBitmap function creates a device-dependent bitmap (DDB) from a DIB and, optionally, sets the bitmap bits
+// The DDB that is created will be whatever bit depth your reference DC is
+HBITMAP STDCALL W32kCreateDIBitmap(HDC hdc, const BITMAPINFOHEADER *header,
+ DWORD init, LPCVOID bits, const BITMAPINFO *data,
+ UINT coloruse)
+{
+ HBITMAP handle;
+ BOOL fColor;
+ DWORD width;
+ int height;
+ WORD bpp;
+ WORD compr;
+
+ if (DIB_GetBitmapInfo( header, &width, &height, &bpp, &compr ) == -1) return 0;
+ if (height < 0) height = -height;
+
+ // Check if we should create a monochrome or color bitmap.
+ // We create a monochrome bitmap only if it has exactly 2
+ // colors, which are black followed by white, nothing else.
+ // In all other cases, we create a color bitmap.
+
+ if (bpp != 1) fColor = TRUE;
+ else if ((coloruse != DIB_RGB_COLORS) ||
+ (init != CBM_INIT) || !data) fColor = FALSE;
+ else
+ {
+ if (data->bmiHeader.biSize == sizeof(BITMAPINFOHEADER))
+ {
+ RGBQUAD *rgb = data->bmiColors;
+ DWORD col = RGB( rgb->rgbRed, rgb->rgbGreen, rgb->rgbBlue );
+
+ // Check if the first color of the colormap is black
+ if ((col == RGB(0, 0, 0)))
+ {
+ rgb++;
+ col = RGB( rgb->rgbRed, rgb->rgbGreen, rgb->rgbBlue );
+ // If the second color is white, create a monochrome bitmap
+ fColor = (col != RGB(0xff,0xff,0xff));
+ }
+ // Note : If the first color of the colormap is white
+ // followed by black, we have to create a color bitmap.
+ // If we don't the white will be displayed in black later on!
+ else fColor = TRUE;
+ }
+ else if (data->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
+ {
+ RGBTRIPLE *rgb = ((BITMAPCOREINFO *)data)->bmciColors;
+ DWORD col = RGB( rgb->rgbtRed, rgb->rgbtGreen, rgb->rgbtBlue);
+
+ if ((col == RGB(0,0,0)))
+ {
+ rgb++;
+ col = RGB( rgb->rgbtRed, rgb->rgbtGreen, rgb->rgbtBlue );
+ fColor = (col != RGB(0xff,0xff,0xff));
+ }
+ else fColor = TRUE;
+ }
+ else
+ {
+ DbgPrint("(%ld): wrong size for data\n", data->bmiHeader.biSize );
+ return 0;
+ }
+ }
+
+ // Now create the bitmap
+
+ if (fColor)
+ {
+ handle = W32kCreateCompatibleBitmap(RetrieveDisplayHDC(), width, height);
+ }
+ else handle = W32kCreateBitmap(width, height, 1, 1, NULL);
+
+ if (!handle) return 0;
+
+ if (init == CBM_INIT)
+ {
+ W32kSetDIBits(hdc, handle, 0, height, bits, data, coloruse);
+ }
+
+ return handle;
+}
+
+HBITMAP STDCALL W32kCreateDIBSection(HDC hDC,
+ CONST BITMAPINFO *bmi,
+ UINT Usage,
+ VOID *Bits,
+ HANDLE hSection,
+ DWORD dwOffset)
+{
+ HBITMAP hbitmap = 0;
+ DC *dc;
+ BOOL bDesktopDC = FALSE;
+
+ // If the reference hdc is null, take the desktop dc
+ if (hDC == 0)
+ {
+ hDC = W32kCreateCompatableDC(0);
+ bDesktopDC = TRUE;
+ }
+
+ if ((dc = DC_HandleToPtr(hDC)))
+ {
+ hbitmap = DIB_CreateDIBSection(dc, bmi, Usage, Bits, hSection, dwOffset, 0);
+ DC_UnlockDC (hDC);
+ }
+
+ if (bDesktopDC)
+ W32kDeleteDC(hDC);
+
+ return hbitmap;
+}
+
+HBITMAP DIB_CreateDIBSection(
+ PDC dc, BITMAPINFO *bmi, UINT usage,
+ LPVOID *bits, HANDLE section,
+ DWORD offset, DWORD ovr_pitch)
+{
+ HBITMAP res = 0;
+ BITMAPOBJ *bmp = NULL;
+ DIBSECTION *dib = NULL;
+ int *colorMap = NULL;
+ int nColorMap;
+
+ // Fill BITMAP32 structure with DIB data
+ BITMAPINFOHEADER *bi = &bmi->bmiHeader;
+ INT effHeight, totalSize;
+ BITMAP bm;
+
+ DbgPrint("format (%ld,%ld), planes %d, bpp %d, size %ld, colors %ld (%s)\n",
+ bi->biWidth, bi->biHeight, bi->biPlanes, bi->biBitCount,
+ bi->biSizeImage, bi->biClrUsed, usage == DIB_PAL_COLORS? "PAL" : "RGB");
+
+ effHeight = bi->biHeight >= 0 ? bi->biHeight : -bi->biHeight;
+ bm.bmType = 0;
+ bm.bmWidth = bi->biWidth;
+ bm.bmHeight = effHeight;
+ bm.bmWidthBytes = ovr_pitch ? ovr_pitch : DIB_GetDIBWidthBytes(bm.bmWidth, bi->biBitCount);
+
+ bm.bmPlanes = bi->biPlanes;
+ bm.bmBitsPixel = bi->biBitCount;
+ bm.bmBits = NULL;
+
+ // Get storage location for DIB bits. Only use biSizeImage if it's valid and
+ // we're dealing with a compressed bitmap. Otherwise, use width * height.
+ totalSize = bi->biSizeImage && bi->biCompression != BI_RGB
+ ? bi->biSizeImage : bm.bmWidthBytes * effHeight;
+
+/*
+ if (section)
+ bm.bmBits = MapViewOfFile(section, FILE_MAP_ALL_ACCESS,
+ 0L, offset, totalSize);
+ else if (ovr_pitch && offset)
+ bm.bmBits = (LPVOID) offset;
+ else { */
+ offset = 0;
+/* bm.bmBits = VirtualAlloc(NULL, totalSize,
+ MEM_RESERVE|MEM_COMMIT, PAGE_READWRITE); */
+
+ bm.bmBits = ExAllocatePool(NonPagedPool, totalSize);
+
+/* } */
+
+ if (usage == DIB_PAL_COLORS) memcpy(bmi->bmiColors, (UINT *)DIB_MapPaletteColors(dc, bmi), sizeof(UINT *));
+
+ // Allocate Memory for DIB and fill structure
+ if (bm.bmBits)
+ dib = ExAllocatePool(PagedPool, sizeof(DIBSECTION));
+ RtlZeroMemory(dib, sizeof(DIBSECTION));
+
+ if (dib)
+ {
+ dib->dsBm = bm;
+ dib->dsBmih = *bi;
+ dib->dsBmih.biSizeImage = totalSize;
+
+ /* Set dsBitfields values */
+ if ( usage == DIB_PAL_COLORS || bi->biBitCount <= 8)
+ {
+ dib->dsBitfields[0] = dib->dsBitfields[1] = dib->dsBitfields[2] = 0;
+ }
+ else switch(bi->biBitCount)
+ {
+ case 16:
+ dib->dsBitfields[0] = (bi->biCompression == BI_BITFIELDS) ? *(DWORD *)bmi->bmiColors : 0x7c00;
+ dib->dsBitfields[1] = (bi->biCompression == BI_BITFIELDS) ? *((DWORD *)bmi->bmiColors + 1) : 0x03e0;
+ dib->dsBitfields[2] = (bi->biCompression == BI_BITFIELDS) ? *((DWORD *)bmi->bmiColors + 2) : 0x001f;
+ break;
+
+ case 24:
+ dib->dsBitfields[0] = 0xff;
+ dib->dsBitfields[1] = 0xff00;
+ dib->dsBitfields[2] = 0xff0000;
+ break;
+
+ case 32:
+ dib->dsBitfields[0] = (bi->biCompression == BI_BITFIELDS) ? *(DWORD *)bmi->bmiColors : 0xff;
+ dib->dsBitfields[1] = (bi->biCompression == BI_BITFIELDS) ? *((DWORD *)bmi->bmiColors + 1) : 0xff00;
+ dib->dsBitfields[2] = (bi->biCompression == BI_BITFIELDS) ? *((DWORD *)bmi->bmiColors + 2) : 0xff0000;
+ break;
+ }
+ dib->dshSection = section;
+ dib->dsOffset = offset;
+ }
+
+ // Create Device Dependent Bitmap and add DIB pointer
+ if (dib)
+ {
+ res = W32kCreateDIBitmap(dc->hSelf, bi, 0, NULL, bmi, usage);
+ if (res)
+ {
+ bmp = BITMAPOBJ_HandleToPtr (res);
+ if (bmp)
+ {
+ bmp->dib = (DIBSECTION *) dib;
+ }
+ }
+ }
+
+ // Clean up in case of errors
+ if (!res || !bmp || !dib || !bm.bmBits || (bm.bmBitsPixel <= 8 && !colorMap))
+ {
+ DbgPrint("got an error res=%08x, bmp=%p, dib=%p, bm.bmBits=%p\n", res, bmp, dib, bm.bmBits);
+/* if (bm.bmBits)
+ {
+ if (section)
+ UnmapViewOfFile(bm.bmBits), bm.bmBits = NULL;
+ else if (!offset)
+ VirtualFree(bm.bmBits, 0L, MEM_RELEASE), bm.bmBits = NULL;
+ } */
+
+ if (colorMap) { ExFreePool(colorMap); colorMap = NULL; }
+ if (dib) { ExFreePool(dib); dib = NULL; }
+ if (bmp) { BITMAPOBJ_UnlockBitmap(res); bmp = NULL; }
+ if (res) { GDIOBJ_FreeObject(res, GO_BITMAP_MAGIC); res = 0; }
+ }
+
+ // Install fault handler, if possible
+/* if (bm.bmBits)
+ {
+ if (VIRTUAL_SetFaultHandler(bm.bmBits, DIB_FaultHandler, (LPVOID)res))
+ {
+ if (section || offset)
+ {
+ DIB_DoProtectDIBSection( bmp, PAGE_READWRITE );
+ if (dib) dib->status = DIB_AppMod;
+ }
+ else
+ {
+ DIB_DoProtectDIBSection( bmp, PAGE_READONLY );
+ if (dib) dib->status = DIB_InSync;
+ }
+ }
+ } */
+
+ // Return BITMAP handle and storage location
+ if (bmp) BITMAPOBJ_UnlockBitmap(res);
+ if (bm.bmBits && bits) *bits = bm.bmBits;
+ return res;
+}
+
+/***********************************************************************
+ * DIB_GetDIBWidthBytes
+ *
+ * Return the width of a DIB bitmap in bytes. DIB bitmap data is 32-bit aligned.
+ * http://www.microsoft.com/msdn/sdk/platforms/doc/sdk/win32/struc/src/str01.htm
+ * 11/16/1999 (RJJ) lifted from wine
+ */
+int DIB_GetDIBWidthBytes(int width, int depth)
+{
+ int words;
+
+ switch(depth)
+ {
+ case 1: words = (width + 31) / 32; break;
+ case 4: words = (width + 7) / 8; break;
+ case 8: words = (width + 3) / 4; break;
+ case 15:
+ case 16: words = (width + 1) / 2; break;
+ case 24: words = (width * 3 + 3)/4; break;
+
+ default:
+ DPRINT("(%d): Unsupported depth\n", depth );
+ /* fall through */
+ case 32:
+ words = width;
+ }
+ return 4 * words;
+}
+
+/***********************************************************************
+ * DIB_GetDIBImageBytes
+ *
+ * Return the number of bytes used to hold the image in a DIB bitmap.
+ * 11/16/1999 (RJJ) lifted from wine
+ */
+
+int DIB_GetDIBImageBytes (int width, int height, int depth)
+{
+ return DIB_GetDIBWidthBytes( width, depth ) * (height < 0 ? -height : height);
+}
+
+/***********************************************************************
+ * DIB_BitmapInfoSize
+ *
+ * Return the size of the bitmap info structure including color table.
+ * 11/16/1999 (RJJ) lifted from wine
+ */
+
+int DIB_BitmapInfoSize (const BITMAPINFO * info, WORD coloruse)
+{
+ int colors;
+
+ if (info->bmiHeader.biSize == sizeof(BITMAPCOREHEADER))
+ {
+ BITMAPCOREHEADER *core = (BITMAPCOREHEADER *)info;
+ colors = (core->bcBitCount <= 8) ? 1 << core->bcBitCount : 0;
+ return sizeof(BITMAPCOREHEADER) + colors * ((coloruse == DIB_RGB_COLORS) ? sizeof(RGBTRIPLE) : sizeof(WORD));
+ }
+ else /* assume BITMAPINFOHEADER */
+ {
+ colors = info->bmiHeader.biClrUsed;
+ if (!colors && (info->bmiHeader.biBitCount <= 8)) colors = 1 << info->bmiHeader.biBitCount;
+ return sizeof(BITMAPINFOHEADER) + colors * ((coloruse == DIB_RGB_COLORS) ? sizeof(RGBQUAD) : sizeof(WORD));
+ }
+}
+
+int DIB_GetBitmapInfo( const BITMAPINFOHEADER *header, DWORD *width,
+ int *height, WORD *bpp, WORD *compr )
+{
+ if (header->biSize == sizeof(BITMAPINFOHEADER))
+ {
+ *width = header->biWidth;
+ *height = header->biHeight;
+ *bpp = header->biBitCount;
+ *compr = header->biCompression;
+ return 1;
+ }
+ if (header->biSize == sizeof(BITMAPCOREHEADER))
+ {
+ BITMAPCOREHEADER *core = (BITMAPCOREHEADER *)header;
+ *width = core->bcWidth;
+ *height = core->bcHeight;
+ *bpp = core->bcBitCount;
+ *compr = 0;
+ return 0;
+ }
+ DbgPrint("(%ld): wrong size for header\n", header->biSize );
+ return -1;
+}
+
+// Converts a Device Independent Bitmap (DIB) to a Device Dependant Bitmap (DDB)
+// The specified Device Context (DC) defines what the DIB should be converted to
+PBITMAPOBJ DIBtoDDB(HGLOBAL hPackedDIB, HDC hdc) // FIXME: This should be removed. All references to this function should
+ // change to W32kSetDIBits
+{
+ HBITMAP hBmp = 0;
+ PBITMAPOBJ pBmp = NULL;
+ DIBSECTION *dib;
+ LPBYTE pbits = NULL;
+
+ // Get a pointer to the packed DIB's data
+ // pPackedDIB = (LPBYTE)GlobalLock(hPackedDIB);
+ dib = hPackedDIB;
+
+ pbits = (dib + DIB_BitmapInfoSize(&dib->dsBmih, DIB_RGB_COLORS));
+
+ // Create a DDB from the DIB
+ hBmp = W32kCreateDIBitmap(hdc, &dib->dsBmih, CBM_INIT, (LPVOID)pbits, &dib->dsBmih, DIB_RGB_COLORS);
+
+ // GlobalUnlock(hPackedDIB);
+
+ // Retrieve the internal Pixmap from the DDB
+ pBmp = (BITMAPOBJ *)GDIOBJ_HandleToPtr(hBmp, GO_BITMAP_MAGIC);
+
+ return pBmp;
+}
+
+RGBQUAD *DIB_MapPaletteColors(PDC dc, LPBITMAPINFO lpbmi)
+{
+ RGBQUAD *lpRGB;
+ int nNumColors,i;
+ DWORD *lpIndex;
+ PPALOBJ palObj;
+
+ palObj = AccessUserObject(dc->DevInfo.hpalDefault);
+
+ if (palObj == NULL) {
+// RELEASEDCINFO(hDC);
+ return NULL;
+ }
+
+ nNumColors = 1 << lpbmi->bmiHeader.biBitCount;
+ if (lpbmi->bmiHeader.biClrUsed)
+ nNumColors = min(nNumColors, lpbmi->bmiHeader.biClrUsed);
+
+ lpRGB = (RGBQUAD *)ExAllocatePool(NonPagedPool, sizeof(RGBQUAD) * nNumColors);
+ lpIndex = (DWORD *)&lpbmi->bmiColors[0];
+
+ for (i=0; i<nNumColors; i++) {
+ pRGB[i].rgbRed = palObj->logpalette.palPalEntry[*lpIndex].peRed;
+ lpRGB[i].rgbGreen = palObj->logpalette.palPalEntry[*lpIndex].peGreen;
+ lpRGB[i].rgbBlue = palObj->logpalette.palPalEntry[*lpIndex].peBlue;
+ lpIndex++;
+ }
+// RELEASEDCINFO(hDC);
+// RELEASEPALETTEINFO(hPalette);
+ return lpRGB;
+}
+
+HPALETTE BuildDIBPalette(BITMAPINFO *bmi, PINT paletteType)
+{
+ BYTE bits;
+
+ // Determine Bits Per Pixel
+ bits = bmi->bmiHeader.biBitCount;
+
+ // Determine paletteType from Bits Per Pixel
+ if(bits <= 8)
+ {
+ *paletteType = PAL_INDEXED;
+ } else
+ if(bits < 24)
+ {
+ *paletteType = PAL_BITFIELDS;
+ } else {
+ *paletteType = PAL_RGB; // FIXME: This could be BGR, must still check
+ }
+
+ return EngCreatePalette(*paletteType, bmi->bmiHeader.biClrUsed, bmi->bmiColors, 0, 0, 0);
+}
int RightRect,
int BottomRect)
{
- DC *dc = DC_HandleToPtr(hDC);
- SURFOBJ *SurfObj = AccessUserObject(dc->Surface);
- PBRUSHOBJ BrushObj;
- BOOL ret;
- PRECTL RectBounds = GDIOBJ_HandleToPtr(dc->w.hGCClipRgn, GO_REGION_MAGIC);
-
- if(!dc) return FALSE;
-
- if(PATH_IsPathOpen(dc->w.path)) {
- ret = PATH_Rectangle(hDC, LeftRect, TopRect, RightRect, BottomRect);
- } else {
-
- DbgPrint("W32kRectangle pen: ");
- DbgPrint("--- %08x\n", GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC));
-
- BrushObj = PenToBrushObj(dc, GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC));
-
- ret = EngLineTo(SurfObj,
- NULL, // ClipObj,
- BrushObj,
- LeftRect, TopRect, RightRect, TopRect,
- RectBounds, // Bounding rectangle
- dc->w.ROPmode); // MIX
-
- ret = EngLineTo(SurfObj,
- NULL, // ClipObj,
- BrushObj,
- RightRect, TopRect, RightRect, BottomRect,
- RectBounds, // Bounding rectangle
- dc->w.ROPmode); // MIX
-
- ret = EngLineTo(SurfObj,
- NULL, // ClipObj,
- BrushObj,
- LeftRect, BottomRect, RightRect, BottomRect,
- RectBounds, // Bounding rectangle
- dc->w.ROPmode); // MIX
-
- ret = EngLineTo(SurfObj,
- NULL, // ClipObj,
- BrushObj,
- LeftRect, TopRect, LeftRect, BottomRect,
- RectBounds, // Bounding rectangle
- dc->w.ROPmode); // MIX */
-
- ExFreePool(BrushObj);
- }
+ DC *dc = DC_HandleToPtr(hDC);
+ SURFOBJ *SurfObj = AccessUserObject(dc->Surface);
+ PBRUSHOBJ BrushObj;
+ BOOL ret;
+ PRECTL RectBounds = GDIOBJ_HandleToPtr(dc->w.hGCClipRgn, GO_REGION_MAGIC);
+
+ if(!dc) return FALSE;
+
+ if(PATH_IsPathOpen(dc->w.path)) {
+ ret = PATH_Rectangle(hDC, LeftRect, TopRect, RightRect, BottomRect);
+ } else {
+
+ DbgPrint("W32kRectangle pen: ");
+ DbgPrint("--- %08x\n", GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC));
+
+ BrushObj = PenToBrushObj(dc, GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC));
+
+ ret = EngLineTo(SurfObj,
+ NULL, // ClipObj,
+ BrushObj,
+ LeftRect, TopRect, RightRect, TopRect,
+ RectBounds, // Bounding rectangle
+ dc->w.ROPmode); // MIX
+
+ ret = EngLineTo(SurfObj,
+ NULL, // ClipObj,
+ BrushObj,
+ RightRect, TopRect, RightRect, BottomRect,
+ RectBounds, // Bounding rectangle
+ dc->w.ROPmode); // MIX
+
+ ret = EngLineTo(SurfObj,
+ NULL, // ClipObj,
+ BrushObj,
+ LeftRect, BottomRect, RightRect, BottomRect,
+ RectBounds, // Bounding rectangle
+ dc->w.ROPmode); // MIX
+
+ ret = EngLineTo(SurfObj,
+ NULL, // ClipObj,
+ BrushObj,
+ LeftRect, TopRect, LeftRect, BottomRect,
+ RectBounds, // Bounding rectangle
+ dc->w.ROPmode); // MIX */
+
+ ExFreePool(BrushObj);
+ }
// FIXME: Move current position in DC?
{
UNIMPLEMENTED;
}
-
-
/*
* GDIOBJ.C - GDI object manipulation routines
*
- * $Id: gdiobj.c,v 1.6 2000/06/16 07:22:39 jfilby Exp $
+ * $Id: gdiobj.c,v 1.7 2001/03/31 15:35:08 jfilby Exp $
*
*/
#include <windows.h>
#include <ddk/ntddk.h>
#include <win32k/gdiobj.h>
+#include <win32k/brush.h>
+#include <win32k/pen.h>
+#include <win32k/text.h>
+
+// GDI stock objects
+
+static LOGBRUSH WhiteBrush =
+{ BS_SOLID, RGB(255,255,255), 0 };
+
+static LOGBRUSH LtGrayBrush =
+/* FIXME : this should perhaps be BS_HATCHED, at least for 1 bitperpixel */
+{ BS_SOLID, RGB(192,192,192), 0 };
+
+static LOGBRUSH GrayBrush =
+/* FIXME : this should perhaps be BS_HATCHED, at least for 1 bitperpixel */
+{ BS_SOLID, RGB(128,128,128), 0 };
+
+static LOGBRUSH DkGrayBrush =
+/* This is BS_HATCHED, for 1 bitperpixel. This makes the spray work in pbrush */
+/* NB_HATCH_STYLES is an index into HatchBrushes */
+{ BS_HATCHED, RGB(0,0,0), NB_HATCH_STYLES };
+
+static LOGBRUSH BlackBrush =
+{ BS_SOLID, RGB(0,0,0), 0 };
+
+static LOGBRUSH NullBrush =
+{ BS_NULL, 0, 0 };
+
+static LOGPEN WhitePen =
+{ PS_SOLID, { 0, 0 }, RGB(255,255,255) };
+
+static LOGPEN BlackPen =
+{ PS_SOLID, { 0, 0 }, RGB(0,0,0) };
+
+static LOGPEN NullPen =
+{ PS_NULL, { 0, 0 }, 0 };
+
+static LOGFONT OEMFixedFont =
+{ 0, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, OEM_CHARSET,
+ 0, 0, DEFAULT_QUALITY, FIXED_PITCH | FF_MODERN, "" };
+
+/* Filler to make the location counter dword aligned again. This is necessary
+ since (a) LOGFONT is packed, (b) gcc places initialised variables in the code
+ segment, and (c) Solaris assembler is stupid. */
+static UINT align_OEMFixedFont = 1;
+
+static LOGFONT AnsiFixedFont =
+{ 0, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
+ 0, 0, DEFAULT_QUALITY, FIXED_PITCH | FF_MODERN, "" };
+
+static UINT align_AnsiFixedFont = 1;
+
+static LOGFONT AnsiVarFont =
+{ 0, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
+ 0, 0, DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, "MS Sans Serif" };
+
+static UINT align_AnsiVarFont = 1;
+
+static LOGFONT SystemFont =
+{ 0, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
+ 0, 0, DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, "System" };
+
+static UINT align_SystemFont = 1;
+
+static LOGFONT DeviceDefaultFont =
+{ 0, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
+ 0, 0, DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, "" };
+
+static UINT align_DeviceDefaultFont = 1;
+
+static LOGFONT SystemFixedFont =
+{ 0, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
+ 0, 0, DEFAULT_QUALITY, FIXED_PITCH | FF_MODERN, "" };
+
+static UINT align_SystemFixedFont = 1;
+
+/* FIXME: Is this correct? */
+static LOGFONT DefaultGuiFont =
+{ 0, 0, 0, 0, FW_NORMAL, FALSE, FALSE, FALSE, ANSI_CHARSET,
+ 0, 0, DEFAULT_QUALITY, VARIABLE_PITCH | FF_SWISS, "MS Sans Serif" };
+
+static UINT align_DefaultGuiFont = 1;
+
+static HGDIOBJ *StockObjects[NB_STOCK_OBJECTS]; // we dont assign these statically as WINE does because we might redesign
+ // the way handles work, so it's more dynamic now
+
+HBITMAP hPseudoStockBitmap; /* 1x1 bitmap for memory DCs */
PGDIOBJ GDIOBJ_AllocObject(WORD Size, WORD Magic)
{
PGDIOBJHDR NewObj;
-
+
NewObj = ExAllocatePool(PagedPool, Size + sizeof (GDIOBJHDR)); // FIXME: Allocate with tag of MAGIC?
+
if (NewObj == NULL)
{
return NULL;
}
RtlZeroMemory(NewObj, Size + sizeof (GDIOBJHDR));
+
NewObj->wMagic = Magic;
#if 0
KeInitializeSpinlock(&NewObj->Lock);
#endif
-
+
return (PGDIOBJ)(((PCHAR) NewObj) + sizeof (GDIOBJHDR));
}
ObjHdr = (PGDIOBJHDR)(((PCHAR)Obj) - sizeof (GDIOBJHDR));
if (ObjHdr->wMagic != Magic)
- {
- return FALSE;
- }
+ {
+ return FALSE;
+ }
ExFreePool (ObjHdr);
return TRUE;
}
if (Obj == NULL) return NULL;
objHeader = (PGDIOBJHDR) (((PCHAR)Obj) - sizeof (GDIOBJHDR));
if (objHeader->wMagic != Magic)
- {
- return 0;
- }
+ {
+ return 0;
+ }
return (HGDIOBJ) objHeader;
}
/* FIXME: Lock object for duration */
if ((objHeader->wMagic != Magic) && (Magic != GO_MAGIC_DONTCARE))
- {
- return 0;
- }
+ {
+ return 0;
+ }
return (PGDIOBJ) (((PCHAR)Obj) + sizeof (GDIOBJHDR));
}
BOOL GDIOBJ_LockObject (HGDIOBJ Obj)
{
/* FIXME: write this */
- return TRUE;
+ // return TRUE;
}
BOOL GDIOBJ_UnlockObject (HGDIOBJ Obj)
objHeader = (PGDIOBJHDR) ((PCHAR) Obj - sizeof (GDIOBJHDR));
if (objHeader->wMagic != Magic)
- {
- return 0;
- }
+ {
+ return 0;
+ }
return objHeader->hNext;
}
/* FIXME: should we lock/unlock the object here? */
objHeader = (PGDIOBJHDR) ((PCHAR) Obj - sizeof (GDIOBJHDR));
if (objHeader->wMagic != Magic)
- {
- return 0;
- }
+ {
+ return 0;
+ }
oldNext = objHeader->hNext;
objHeader->hNext = NextObj;
return oldNext;
}
+VOID CreateStockObjects(void)
+{
+ // Create GDI Stock Objects from the logical structures we've defined
+ StockObjects[WHITE_BRUSH] = W32kCreateBrushIndirect(&WhiteBrush);
+ StockObjects[LTGRAY_BRUSH] = W32kCreateBrushIndirect(&LtGrayBrush);
+ StockObjects[GRAY_BRUSH] = W32kCreateBrushIndirect(&GrayBrush);
+ StockObjects[DKGRAY_BRUSH] = W32kCreateBrushIndirect(&DkGrayBrush);
+ StockObjects[BLACK_BRUSH] = W32kCreateBrushIndirect(&BlackBrush);
+ StockObjects[NULL_BRUSH] = W32kCreateBrushIndirect(&NullBrush);
+
+ StockObjects[WHITE_PEN] = W32kCreatePenIndirect(&WhitePen);
+ StockObjects[BLACK_PEN] = W32kCreatePenIndirect(&BlackPen);
+ StockObjects[NULL_PEN] = W32kCreatePenIndirect(&NullPen);
+
+ StockObjects[OEM_FIXED_FONT] = W32kCreateFontIndirect(&OEMFixedFont);
+ StockObjects[ANSI_FIXED_FONT] = W32kCreateFontIndirect(&AnsiFixedFont);
+ StockObjects[SYSTEM_FONT] = W32kCreateFontIndirect(&SystemFont);
+ StockObjects[DEVICE_DEFAULT_FONT] = W32kCreateFontIndirect(&DeviceDefaultFont);
+ StockObjects[SYSTEM_FIXED_FONT] = W32kCreateFontIndirect(&SystemFixedFont);
+ StockObjects[DEFAULT_GUI_FONT] = W32kCreateFontIndirect(&DefaultGuiFont);
+
+ StockObjects[DEFAULT_PALETTE] = PALETTE_Init();
+}
+
+HGDIOBJ STDCALL W32kGetStockObject(INT Object)
+{
+ HGDIOBJ ret;
+
+/* if ((Object < 0) || (Object >= NB_STOCK_OBJECTS)) return 0;
+ if (!StockObjects[Object]) return 0;
+ ret = FIRST_STOCK_HANDLE + Object;
+ return ret; */
+ return StockObjects[Object]; // FIXME........
+}
int XEndArc,
int YEndArc)
{
- DC *dc = DC_HandleToPtr(hDC);
- if(!dc) return FALSE;
+ DC *dc = DC_HandleToPtr(hDC);
+ if(!dc) return FALSE;
- if(PATH_IsPathOpen(dc->w.path))
- return PATH_Arc(hDC, LeftRect, TopRect, RightRect, BottomRect,
- XStartArc, YStartArc, XEndArc, YEndArc);
+ if(PATH_IsPathOpen(dc->w.path))
+ return PATH_Arc(hDC, LeftRect, TopRect, RightRect, BottomRect,
+ XStartArc, YStartArc, XEndArc, YEndArc);
// EngArc(dc, LeftRect, TopRect, RightRect, BottomRect, UNIMPLEMENTED
// XStartArc, YStartArc, XEndArc, YEndArc);
int XRadial2,
int YRadial2)
{
- BOOL result;
- DC *dc = DC_HandleToPtr(hDC);
- if(!dc) return FALSE;
+ BOOL result;
+ DC *dc = DC_HandleToPtr(hDC);
+ if(!dc) return FALSE;
- // Line from current position to starting point of arc
- W32kLineTo(hDC, XRadial1, YRadial1);
+ // Line from current position to starting point of arc
+ W32kLineTo(hDC, XRadial1, YRadial1);
- // Then the arc is drawn.
- result = W32kArc(hDC, LeftRect, TopRect, RightRect, BottomRect,
- XRadial1, YRadial1, XRadial2, YRadial2);
+ // Then the arc is drawn.
+ result = W32kArc(hDC, LeftRect, TopRect, RightRect, BottomRect,
+ XRadial1, YRadial1, XRadial2, YRadial2);
- // If no error occured, the current position is moved to the ending point of the arc.
- if(result)
- {
- W32kMoveToEx(hDC, XRadial2, YRadial2, NULL);
- }
+ // If no error occured, the current position is moved to the ending point of the arc.
+ if(result)
+ {
+ W32kMoveToEx(hDC, XRadial2, YRadial2, NULL);
+ }
- return result;
+ return result;
}
INT
STDCALL
W32kGetArcDirection(HDC hDC)
{
- PDC dc;
- int ret;
+ PDC dc;
+ int ret;
- dc = DC_HandleToPtr (hDC);
- if (!dc)
- {
- return 0;
- }
-
- ret = dc->w.ArcDirection;
- DC_UnlockDC (hDC);
+ dc = DC_HandleToPtr (hDC);
+ if (!dc)
+ {
+ return 0;
+ }
+
+ ret = dc->w.ArcDirection;
+ DC_UnlockDC (hDC);
- return ret;
+ return ret;
}
BOOL
int XEnd,
int YEnd)
{
- DC *dc = DC_HandleToPtr(hDC);
- SURFOBJ *SurfObj = AccessUserObject(dc->Surface);
- BOOL ret;
-
- if(!dc) return FALSE;
-
- if(PATH_IsPathOpen(dc->w.path)) {
- ret = PATH_LineTo(hDC, XEnd, YEnd);
- } else {
-
- DbgPrint("W32kLineTo on DC:%08x (h:%08x) with pen handle %08x\n", dc, hDC, dc->w.hPen);
- DbgPrint("--- %08x\n", GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC));
-
- ret = EngLineTo(SurfObj,
- NULL, // ClipObj
- PenToBrushObj(dc, GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC)),
- dc->w.CursPosX, dc->w.CursPosY, XEnd, YEnd,
- GDIOBJ_HandleToPtr(dc->w.hGCClipRgn, GO_REGION_MAGIC), // Bounding rectangle
- dc->w.ROPmode); // MIX
- }
- if(ret) {
- dc->w.CursPosX = XEnd;
- dc->w.CursPosY = YEnd;
- }
-
- return ret;
+ DC *dc = DC_HandleToPtr(hDC);
+ SURFOBJ *SurfObj = AccessUserObject(dc->Surface);
+ BOOL ret;
+
+ if(!dc) return FALSE;
+
+ if(PATH_IsPathOpen(dc->w.path)) {
+ ret = PATH_LineTo(hDC, XEnd, YEnd);
+ } else {
+ ret = EngLineTo(SurfObj,
+ NULL, // ClipObj
+ PenToBrushObj(dc, GDIOBJ_HandleToPtr(dc->w.hPen, GO_PEN_MAGIC)),
+ dc->w.CursPosX, dc->w.CursPosY, XEnd, YEnd,
+ GDIOBJ_HandleToPtr(dc->w.hGCClipRgn, GO_REGION_MAGIC), // Bounding rectangle
+ dc->w.ROPmode); // MIX
+ }
+ if(ret) {
+ dc->w.CursPosX = XEnd;
+ dc->w.CursPosY = YEnd;
+ }
+
+ return ret;
}
BOOL
int Y,
LPPOINT Point)
{
- DC *dc = DC_HandleToPtr( hDC );
+ DC *dc = DC_HandleToPtr( hDC );
- if(!dc) return FALSE;
+ if(!dc) return FALSE;
- if(Point) {
- Point->x = dc->w.CursPosX;
- Point->y = dc->w.CursPosY;
- }
- dc->w.CursPosX = X;
- dc->w.CursPosY = Y;
+ if(Point) {
+ Point->x = dc->w.CursPosX;
+ Point->y = dc->w.CursPosY;
+ }
+ dc->w.CursPosX = X;
+ dc->w.CursPosY = Y;
- if(PATH_IsPathOpen(dc->w.path))
- return PATH_MoveTo(hDC);
+ if(PATH_IsPathOpen(dc->w.path))
+ return PATH_MoveTo(hDC);
- return FALSE;
+ return FALSE;
}
BOOL
CONST LPPOINT pt,
DWORD Count)
{
- DC *dc = DC_HandleToPtr(hDC);
- if(!dc) return FALSE;
-
- if(PATH_IsPathOpen(dc->w.path))
- return PATH_PolyBezier(hDC, pt, Count);
-
- /* We'll convert it into line segments and draw them using Polyline */
- {
- POINT *Pts;
- INT nOut;
- BOOL ret;
-
- Pts = GDI_Bezier(pt, Count, &nOut);
- if(!Pts) return FALSE;
- DbgPrint("Pts = %p, no = %d\n", Pts, nOut);
- ret = W32kPolyline(dc->hSelf, Pts, nOut);
- ExFreePool(Pts);
- return ret;
- }
+ DC *dc = DC_HandleToPtr(hDC);
+ if(!dc) return FALSE;
+
+ if(PATH_IsPathOpen(dc->w.path))
+ return PATH_PolyBezier(hDC, pt, Count);
+
+ /* We'll convert it into line segments and draw them using Polyline */
+ {
+ POINT *Pts;
+ INT nOut;
+ BOOL ret;
+
+ Pts = GDI_Bezier(pt, Count, &nOut);
+ if(!Pts) return FALSE;
+ DbgPrint("Pts = %p, no = %d\n", Pts, nOut);
+ ret = W32kPolyline(dc->hSelf, Pts, nOut);
+ ExFreePool(Pts);
+ return ret;
+ }
}
BOOL
CONST LPPOINT pt,
DWORD Count)
{
- DC *dc = DC_HandleToPtr(hDC);
- BOOL ret;
-
- if(!dc) return FALSE;
-
- if(PATH_IsPathOpen(dc->w.path))
- ret = PATH_PolyBezierTo(hDC, pt, Count);
- else { /* We'll do it using PolyBezier */
- POINT *npt;
- npt = ExAllocatePool(NonPagedPool, sizeof(POINT) * (Count + 1));
- if(!npt) return FALSE;
- npt[0].x = dc->w.CursPosX;
- npt[0].y = dc->w.CursPosY;
- memcpy(npt + 1, pt, sizeof(POINT) * Count);
- ret = W32kPolyBezier(dc->hSelf, npt, Count+1);
- ExFreePool(npt);
- }
- if(ret) {
- dc->w.CursPosX = pt[Count-1].x;
- dc->w.CursPosY = pt[Count-1].y;
- }
- return ret;
+ DC *dc = DC_HandleToPtr(hDC);
+ BOOL ret;
+
+ if(!dc) return FALSE;
+
+ if(PATH_IsPathOpen(dc->w.path))
+ ret = PATH_PolyBezierTo(hDC, pt, Count);
+ else { /* We'll do it using PolyBezier */
+ POINT *npt;
+ npt = ExAllocatePool(NonPagedPool, sizeof(POINT) * (Count + 1));
+ if(!npt) return FALSE;
+ npt[0].x = dc->w.CursPosX;
+ npt[0].y = dc->w.CursPosY;
+ memcpy(npt + 1, pt, sizeof(POINT) * Count);
+ ret = W32kPolyBezier(dc->hSelf, npt, Count+1);
+ ExFreePool(npt);
+ }
+ if(ret) {
+ dc->w.CursPosX = pt[Count-1].x;
+ dc->w.CursPosY = pt[Count-1].y;
+ }
+ return ret;
}
BOOL
CONST LPPOINT pt,
DWORD Count)
{
- DC *dc = DC_HandleToPtr(hDC);
- BOOL ret;
-
- if(!dc) return FALSE;
-
- if(PATH_IsPathOpen(dc->w.path))
- {
- ret = PATH_PolylineTo(hDC, pt, Count);
- }
- else { /* do it using Polyline */
- POINT *pts = ExAllocatePool(NonPagedPool, sizeof(POINT) * (Count + 1));
- if(!pts) return FALSE;
-
- pts[0].x = dc->w.CursPosX;
- pts[0].y = dc->w.CursPosY;
- memcpy( pts + 1, pt, sizeof(POINT) * Count);
- ret = W32kPolyline(hDC, pts, Count + 1);
- ExFreePool(pts);
- }
- if(ret) {
- dc->w.CursPosX = pt[Count-1].x;
- dc->w.CursPosY = pt[Count-1].y;
- }
- return ret;
+ DC *dc = DC_HandleToPtr(hDC);
+ BOOL ret;
+
+ if(!dc) return FALSE;
+
+ if(PATH_IsPathOpen(dc->w.path))
+ {
+ ret = PATH_PolylineTo(hDC, pt, Count);
+ }
+ else { /* do it using Polyline */
+ POINT *pts = ExAllocatePool(NonPagedPool, sizeof(POINT) * (Count + 1));
+ if(!pts) return FALSE;
+
+ pts[0].x = dc->w.CursPosX;
+ pts[0].y = dc->w.CursPosY;
+ memcpy( pts + 1, pt, sizeof(POINT) * Count);
+ ret = W32kPolyline(hDC, pts, Count + 1);
+ ExFreePool(pts);
+ }
+ if(ret) {
+ dc->w.CursPosX = pt[Count-1].x;
+ dc->w.CursPosY = pt[Count-1].y;
+ }
+ return ret;
}
BOOL
W32kSetArcDirection(HDC hDC,
int ArcDirection)
{
- PDC dc;
- INT nOldDirection;
-
- dc = DC_HandleToPtr (hDC);
- if (!dc)
- {
- return 0;
- }
- if (ArcDirection != AD_COUNTERCLOCKWISE && ArcDirection != AD_CLOCKWISE)
- {
-// SetLastError(ERROR_INVALID_PARAMETER);
- return 0;
- }
-
- nOldDirection = dc->w.ArcDirection;
- dc->w.ArcDirection = ArcDirection;
-
- return nOldDirection;
+ PDC dc;
+ INT nOldDirection;
+
+ dc = DC_HandleToPtr (hDC);
+ if (!dc)
+ {
+ return 0;
+ }
+ if (ArcDirection != AD_COUNTERCLOCKWISE && ArcDirection != AD_CLOCKWISE)
+ {
+// SetLastError(ERROR_INVALID_PARAMETER);
+ return 0;
+ }
+
+ nOldDirection = dc->w.ArcDirection;
+ dc->w.ArcDirection = ArcDirection;
+
+ return nOldDirection;
}
PBRUSHOBJ PenToBrushObj(PDC dc, PENOBJ *pen)
{
- BRUSHOBJ *BrushObj;
- XLATEOBJ *RGBtoVGA16;
+ BRUSHOBJ *BrushObj;
+ XLATEOBJ *RGBtoVGA16;
-// FIXME: move color translation routines to W32kSelectObject
+ BrushObj = ExAllocatePool(NonPagedPool, sizeof(BRUSHOBJ));
+ BrushObj->iSolidColor = pen->logpen.lopnColor;
-DbgPrint("PenToBrushObj:%08x ", pen);
- BrushObj = ExAllocatePool(NonPagedPool, sizeof(BRUSHOBJ));
-
- RGBtoVGA16 = EngCreateXlate(PAL_INDEXED, PAL_RGB,
- dc->DevInfo.hpalDefault, NULL);
- BrushObj->iSolidColor = XLATEOBJ_iXlate(RGBtoVGA16, pen->logpen.lopnColor);
-
-DbgPrint("BrushObj->iSolidColor:%u\n", BrushObj->iSolidColor);
- return BrushObj;
-
-// CreateGDIHandle(BrushGDI, BrushObj);
+ return BrushObj;
}
-VOID BitmapToSurf(PSURFGDI SurfGDI, PSURFOBJ SurfObj, PBITMAPOBJ Bitmap)
+VOID BitmapToSurf(HDC hdc, PSURFGDI SurfGDI, PSURFOBJ SurfObj, PBITMAPOBJ Bitmap)
{
- SurfObj->dhsurf = NULL;
- SurfObj->hsurf = NULL;
- SurfObj->dhpdev = NULL;
- SurfObj->hdev = NULL;
- SurfObj->sizlBitmap = Bitmap->size;
- SurfObj->cjBits = Bitmap->bitmap.bmHeight * Bitmap->bitmap.bmWidthBytes;
- SurfObj->pvBits = Bitmap->bitmap.bmBits;
- SurfObj->pvScan0 = NULL; // start of bitmap
- SurfObj->lDelta = Bitmap->bitmap.bmWidthBytes;
+ if(Bitmap->dib)
+ {
+ SurfGDI->BitsPerPixel = Bitmap->dib->dsBm.bmBitsPixel;
+ SurfObj->lDelta = Bitmap->dib->dsBm.bmWidthBytes;
+ SurfObj->pvBits = Bitmap->dib->dsBm.bmBits;
+ SurfObj->cjBits = Bitmap->dib->dsBm.bmHeight * Bitmap->dib->dsBm.bmWidthBytes;
+ } else {
+ SurfGDI->BitsPerPixel = Bitmap->bitmap.bmBitsPixel;
+ SurfObj->lDelta = Bitmap->bitmap.bmWidthBytes;
+ SurfObj->pvBits = Bitmap->bitmap.bmBits;
+ SurfObj->cjBits = Bitmap->bitmap.bmHeight * Bitmap->bitmap.bmWidthBytes;
+ }
+
+ SurfObj->dhsurf = NULL;
+ SurfObj->hsurf = NULL;
+ SurfObj->dhpdev = NULL;
+ SurfObj->hdev = NULL;
+ SurfObj->pvScan0 = SurfObj->pvBits; // start of bitmap
+ SurfObj->sizlBitmap = Bitmap->size; // FIXME: alloc memory for our own struct?
SurfObj->iUniq = 0; // not sure..
- SurfObj->iBitmapFormat = BMF_4BPP; /* FIXME */
+ SurfObj->iBitmapFormat = BitmapFormat(SurfGDI->BitsPerPixel, BI_RGB);
SurfObj->iType = STYPE_BITMAP;
SurfObj->fjBitmap = BMF_TOPDOWN;
-
- SurfGDI->BytesPerPixel = bytesPerPixel(SurfObj->iType);
-
-DbgPrint("Bitmap2Surf: cjBits: %u lDelta: %u width: %u height: %u\n",
- SurfObj->cjBits, SurfObj->lDelta, Bitmap->bitmap.bmWidth, Bitmap->bitmap.bmHeight);
}
--- /dev/null
+#undef WIN32_LEAN_AND_MEAN
+#include <windows.h>
+#include <win32k/debug.h>
+#include <win32k/bitmaps.h>
+#include <win32k/color.h>
+#include <debug.h>
+
+static int PALETTE_firstFree = 0;
+static unsigned char PALETTE_freeList[256];
+
+int PALETTE_PaletteFlags = 0;
+PALETTEENTRY *COLOR_sysPal = NULL;
+int COLOR_gapStart;
+int COLOR_gapEnd;
+int COLOR_gapFilled;
+int COLOR_max;
+
+PALETTEENTRY *ReturnSystemPalette(void)
+{
+ return COLOR_sysPal;
+}
+
+// Create the system palette
+HPALETTE PALETTE_Init(void)
+{
+ int i;
+ HPALETTE hpalette;
+ PLOGPALETTE palPtr;
+ PPALOBJ palObj;
+ const PALETTEENTRY* __sysPalTemplate = COLOR_GetSystemPaletteTemplate();
+
+ // create default palette (20 system colors)
+ palPtr = ExAllocatePool(NonPagedPool, sizeof(LOGPALETTE) + (NB_RESERVED_COLORS-1) * sizeof(PALETTEENTRY));
+ if (!palPtr) return FALSE;
+
+ palPtr->palVersion = 0x300;
+ palPtr->palNumEntries = NB_RESERVED_COLORS;
+ for(i=0; i<NB_RESERVED_COLORS; i++)
+ {
+ palPtr->palPalEntry[i].peRed = __sysPalTemplate[i].peRed;
+ palPtr->palPalEntry[i].peGreen = __sysPalTemplate[i].peGreen;
+ palPtr->palPalEntry[i].peBlue = __sysPalTemplate[i].peBlue;
+ palPtr->palPalEntry[i].peFlags = 0;
+ }
+ hpalette = W32kCreatePalette(palPtr);
+ ExFreePool(palPtr);
+
+ palObj = AccessUserObject(hpalette);
+ if (palObj)
+ {
+ if (!(palObj->mapping = ExAllocatePool(NonPagedPool, sizeof(int) * 20)))
+ {
+ DbgPrint("Win32k: Can not create palette mapping -- out of memory!");
+ return FALSE;
+ }
+// GDI_ReleaseObj( hpalette );
+ }
+
+ return hpalette;
+}
+
+static void PALETTE_FormatSystemPalette(void)
+{
+ // Build free list so we'd have an easy way to find
+ // out if there are any available colorcells.
+
+ int i, j = PALETTE_firstFree = NB_RESERVED_COLORS/2;
+
+ COLOR_sysPal[j].peFlags = 0;
+ for(i = NB_RESERVED_COLORS/2 + 1 ; i < 256 - NB_RESERVED_COLORS/2 ; i++)
+ {
+ if( i < COLOR_gapStart || i > COLOR_gapEnd )
+ {
+ COLOR_sysPal[i].peFlags = 0; // unused tag
+ PALETTE_freeList[j] = i; // next
+ j = i;
+ }
+ }
+ PALETTE_freeList[j] = 0;
+}
+
+void PALETTE_ValidateFlags(PALETTEENTRY* lpPalE, int size)
+{
+ int i = 0;
+ for( ; i<size ; i++ )
+ lpPalE[i].peFlags = PC_SYS_USED | (lpPalE[i].peFlags & 0x07);
+}
+
+// Set the color-mapping table for selected palette.
+// Return number of entries which mapping has changed.
+int PALETTE_SetMapping(PPALOBJ palPtr, UINT uStart, UINT uNum, BOOL mapOnly)
+{
+ char flag;
+ int prevMapping = (palPtr->mapping) ? 1 : 0;
+ int index, iRemapped = 0;
+ int *mapping;
+
+ // reset dynamic system palette entries
+
+ if( !mapOnly && PALETTE_firstFree != -1) PALETTE_FormatSystemPalette();
+
+ // initialize palette mapping table
+
+ //mapping = HeapReAlloc( GetProcessHeap(), 0, palPtr->mapping,
+ // sizeof(int)*palPtr->logpalette.palNumEntries);
+ ExFreePool(palPtr->mapping);
+ mapping = ExAllocatePool(NonPagedPool, sizeof(int)*palPtr->logpalette.palNumEntries);
+
+ palPtr->mapping = mapping;
+
+ for(uNum += uStart; uStart < uNum; uStart++)
+ {
+ index = -1;
+ flag = PC_SYS_USED;
+
+ switch( palPtr->logpalette.palPalEntry[uStart].peFlags & 0x07 )
+ {
+ case PC_EXPLICIT: // palette entries are indices into system palette
+ // The PC_EXPLICIT flag is used to copy an entry from the system palette into the logical palette
+ index = *(WORD*)(palPtr->logpalette.palPalEntry + uStart);
+ if(index > 255 || (index >= COLOR_gapStart && index <= COLOR_gapEnd))
+ {
+ DbgPrint("Win32k: PC_EXPLICIT: idx %d out of system palette, assuming black.\n", index);
+ index = 0;
+ }
+ break;
+
+ case PC_RESERVED: // forbid future mappings to this entry
+ // For palette animation, the entries in the logical palette need the PC_RESERVED flag
+ flag |= PC_SYS_RESERVED;
+
+ // fall through
+ default: // try to collapse identical colors
+ index = COLOR_PaletteLookupExactIndex(COLOR_sysPal, 256,
+ *(COLORREF*)(palPtr->logpalette.palPalEntry + uStart));
+ // fall through
+
+ case PC_NOCOLLAPSE:
+ // If an entry in the logical palette is marked with the PC_NOCOLLAPSE flag, the palette
+ // manager allocates a free entry in the system palette if one is available and only uses the
+ // closest colour match if there are no (more) free entries in the system palette
+
+ DbgPrint("Win32k: WARNING: PC_NOCOLLAPSE is not yet working properly\n");
+
+ if( index < 0 )
+ {
+ if(PALETTE_firstFree > 0 /* && !(PALETTE_PaletteFlags & PALETTE_FIXED) FIXME */ )
+ {
+ DgPrint("Win32k: Unimplemented Palette Operation: PC_NOCOLLAPSE [objects/palette.c]\n");
+/* XColor color;
+ index = PALETTE_firstFree; // ought to be available
+ PALETTE_firstFree = PALETTE_freeList[index];
+
+ color.pixel = (PALETTE_PaletteToXPixel) ? PALETTE_PaletteToXPixel[index] : index;
+ color.red = palPtr->logpalette.palPalEntry[uStart].peRed << 8;
+ color.green = palPtr->logpalette.palPalEntry[uStart].peGreen << 8;
+ color.blue = palPtr->logpalette.palPalEntry[uStart].peBlue << 8;
+ color.flags = DoRed | DoGreen | DoBlue;
+ TSXStoreColor(display, PALETTE_PaletteXColormap, &color);
+
+ COLOR_sysPal[index] = palPtr->logpalette.palPalEntry[uStart];
+ COLOR_sysPal[index].peFlags = flag;
+ PALETTE_freeList[index] = 0;
+
+ if(PALETTE_PaletteToXPixel) index = PALETTE_PaletteToXPixel[index]; */
+ break;
+ }
+/* else if (PALETTE_PaletteFlags & PALETTE_VIRTUAL)
+ {
+ index = PALETTE_ToPhysical(NULL, 0x00ffffff &
+ *(COLORREF*)(palPtr->logpalette.palPalEntry + uStart));
+ break;
+ } FIXME */
+
+ // we have to map to existing entry in the system palette
+
+ index = COLOR_PaletteLookupPixel(COLOR_sysPal, 256, NULL,
+ *(COLORREF*)(palPtr->logpalette.palPalEntry + uStart), TRUE);
+ }
+ palPtr->logpalette.palPalEntry[uStart].peFlags |= PC_SYS_USED;
+
+/* if(PALETTE_PaletteToXPixel) index = PALETTE_PaletteToXPixel[index]; FIXME */
+ break;
+ }
+
+ if( !prevMapping || palPtr->mapping[uStart] != index ) iRemapped++;
+ palPtr->mapping[uStart] = index;
+
+ }
+ return iRemapped;
+}
*/
void PATH_InitGdiPath(GdiPath *pPath)
{
- assert(pPath!=NULL);
+ assert(pPath!=NULL);
- pPath->state=PATH_Null;
- pPath->pPoints=NULL;
- pPath->pFlags=NULL;
- pPath->numEntriesUsed=0;
- pPath->numEntriesAllocated=0;
+ pPath->state=PATH_Null;
+ pPath->pPoints=NULL;
+ pPath->pFlags=NULL;
+ pPath->numEntriesUsed=0;
+ pPath->numEntriesAllocated=0;
}
/* PATH_DestroyGdiPath
*/
void PATH_DestroyGdiPath(GdiPath *pPath)
{
- assert(pPath!=NULL);
+ assert(pPath!=NULL);
- ExFreePool(pPath->pPoints);
- ExFreePool(pPath->pFlags);
+ ExFreePool(pPath->pPoints);
+ ExFreePool(pPath->pFlags);
}
/* PATH_AssignGdiPath
*/
BOOL PATH_AssignGdiPath(GdiPath *pPathDest, const GdiPath *pPathSrc)
{
- assert(pPathDest!=NULL && pPathSrc!=NULL);
+ assert(pPathDest!=NULL && pPathSrc!=NULL);
- /* Make sure destination arrays are big enough */
- if(!PATH_ReserveEntries(pPathDest, pPathSrc->numEntriesUsed))
- return FALSE;
+ /* Make sure destination arrays are big enough */
+ if(!PATH_ReserveEntries(pPathDest, pPathSrc->numEntriesUsed))
+ return FALSE;
- /* Perform the copy operation */
- memcpy(pPathDest->pPoints, pPathSrc->pPoints,
- sizeof(POINT)*pPathSrc->numEntriesUsed);
- memcpy(pPathDest->pFlags, pPathSrc->pFlags,
- sizeof(BYTE)*pPathSrc->numEntriesUsed);
+ /* Perform the copy operation */
+ memcpy(pPathDest->pPoints, pPathSrc->pPoints,
+ sizeof(POINT)*pPathSrc->numEntriesUsed);
+ memcpy(pPathDest->pFlags, pPathSrc->pFlags,
+ sizeof(BYTE)*pPathSrc->numEntriesUsed);
- pPathDest->state=pPathSrc->state;
- pPathDest->numEntriesUsed=pPathSrc->numEntriesUsed;
- pPathDest->newStroke=pPathSrc->newStroke;
+ pPathDest->state=pPathSrc->state;
+ pPathDest->numEntriesUsed=pPathSrc->numEntriesUsed;
+ pPathDest->newStroke=pPathSrc->newStroke;
- return TRUE;
+ return TRUE;
}
/* PATH_MoveTo
*/
BOOL PATH_MoveTo(HDC hdc)
{
- GdiPath *pPath;
+ GdiPath *pPath;
- /* Get pointer to path */
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ /* Get pointer to path */
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- /* FIXME: Do we have to call SetLastError? */
- return FALSE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ /* FIXME: Do we have to call SetLastError? */
+ return FALSE;
- /* Start a new stroke */
- pPath->newStroke=TRUE;
+ /* Start a new stroke */
+ pPath->newStroke=TRUE;
- return TRUE;
+ return TRUE;
}
/* PATH_LineTo
*/
BOOL PATH_LineTo(HDC hdc, INT x, INT y)
{
- GdiPath *pPath;
- POINT point, pointCurPos;
+ GdiPath *pPath;
+ POINT point, pointCurPos;
- /* Get pointer to path */
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ /* Get pointer to path */
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
+
+ /* Convert point to device coordinates */
+ point.x=x;
+ point.y=y;
+ if(!W32kLPtoDP(hdc, &point, 1))
+ return FALSE;
+
+ /* Add a PT_MOVETO if necessary */
+ if(pPath->newStroke)
+ {
+ pPath->newStroke=FALSE;
+ if(!W32kGetCurrentPositionEx(hdc, &pointCurPos) ||
+ !W32kLPtoDP(hdc, &pointCurPos, 1))
return FALSE;
-
- /* Convert point to device coordinates */
- point.x=x;
- point.y=y;
- if(!W32kLPtoDP(hdc, &point, 1))
+ if(!PATH_AddEntry(pPath, &pointCurPos, PT_MOVETO))
return FALSE;
+ }
- /* Add a PT_MOVETO if necessary */
- if(pPath->newStroke)
- {
- pPath->newStroke=FALSE;
- if(!W32kGetCurrentPositionEx(hdc, &pointCurPos) ||
- !W32kLPtoDP(hdc, &pointCurPos, 1))
- return FALSE;
- if(!PATH_AddEntry(pPath, &pointCurPos, PT_MOVETO))
- return FALSE;
- }
-
- /* Add a PT_LINETO entry */
- return PATH_AddEntry(pPath, &point, PT_LINETO);
+ /* Add a PT_LINETO entry */
+ return PATH_AddEntry(pPath, &point, PT_LINETO);
}
/* PATH_Rectangle
*/
BOOL PATH_Rectangle(HDC hdc, INT x1, INT y1, INT x2, INT y2)
{
- GdiPath *pPath;
- POINT corners[2], pointTemp;
- INT temp;
+ GdiPath *pPath;
+ POINT corners[2], pointTemp;
+ INT temp;
- /* Get pointer to path */
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ /* Get pointer to path */
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
-
- /* Convert points to device coordinates */
- corners[0].x=x1;
- corners[0].y=y1;
- corners[1].x=x2;
- corners[1].y=y2;
- if(!W32kLPtoDP(hdc, corners, 2))
- return FALSE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
+
+ /* Convert points to device coordinates */
+ corners[0].x=x1;
+ corners[0].y=y1;
+ corners[1].x=x2;
+ corners[1].y=y2;
+ if(!W32kLPtoDP(hdc, corners, 2))
+ return FALSE;
- /* Make sure first corner is top left and second corner is bottom right */
- if(corners[0].x>corners[1].x)
- {
- temp=corners[0].x;
- corners[0].x=corners[1].x;
- corners[1].x=temp;
- }
- if(corners[0].y>corners[1].y)
- {
- temp=corners[0].y;
- corners[0].y=corners[1].y;
- corners[1].y=temp;
- }
+ /* Make sure first corner is top left and second corner is bottom right */
+ if(corners[0].x>corners[1].x)
+ {
+ temp=corners[0].x;
+ corners[0].x=corners[1].x;
+ corners[1].x=temp;
+ }
+ if(corners[0].y>corners[1].y)
+ {
+ temp=corners[0].y;
+ corners[0].y=corners[1].y;
+ corners[1].y=temp;
+ }
- /* In GM_COMPATIBLE, don't include bottom and right edges */
- if(W32kGetGraphicsMode(hdc)==GM_COMPATIBLE)
- {
- corners[1].x--;
- corners[1].y--;
- }
-
- /* Close any previous figure */
- if(!W32kCloseFigure(hdc))
- {
- /* The W32kCloseFigure call shouldn't have failed */
- assert(FALSE);
- return FALSE;
- }
-
- /* Add four points to the path */
- pointTemp.x=corners[1].x;
- pointTemp.y=corners[0].y;
- if(!PATH_AddEntry(pPath, &pointTemp, PT_MOVETO))
- return FALSE;
- if(!PATH_AddEntry(pPath, corners, PT_LINETO))
- return FALSE;
- pointTemp.x=corners[0].x;
- pointTemp.y=corners[1].y;
- if(!PATH_AddEntry(pPath, &pointTemp, PT_LINETO))
- return FALSE;
- if(!PATH_AddEntry(pPath, corners+1, PT_LINETO))
- return FALSE;
-
- /* Close the rectangle figure */
- if(!W32kCloseFigure(hdc))
- {
- /* The W32kCloseFigure call shouldn't have failed */
- assert(FALSE);
- return FALSE;
- }
-
- return TRUE;
+ /* In GM_COMPATIBLE, don't include bottom and right edges */
+ if(W32kGetGraphicsMode(hdc)==GM_COMPATIBLE)
+ {
+ corners[1].x--;
+ corners[1].y--;
+ }
+
+ /* Close any previous figure */
+ if(!W32kCloseFigure(hdc))
+ {
+ /* The W32kCloseFigure call shouldn't have failed */
+ assert(FALSE);
+ return FALSE;
+ }
+
+ /* Add four points to the path */
+ pointTemp.x=corners[1].x;
+ pointTemp.y=corners[0].y;
+ if(!PATH_AddEntry(pPath, &pointTemp, PT_MOVETO))
+ return FALSE;
+ if(!PATH_AddEntry(pPath, corners, PT_LINETO))
+ return FALSE;
+ pointTemp.x=corners[0].x;
+ pointTemp.y=corners[1].y;
+ if(!PATH_AddEntry(pPath, &pointTemp, PT_LINETO))
+ return FALSE;
+ if(!PATH_AddEntry(pPath, corners+1, PT_LINETO))
+ return FALSE;
+
+ /* Close the rectangle figure */
+ if(!W32kCloseFigure(hdc))
+ {
+ /* The W32kCloseFigure call shouldn't have failed */
+ assert(FALSE);
+ return FALSE;
+ }
+
+ return TRUE;
}
/* PATH_Ellipse
*/
BOOL PATH_Ellipse(HDC hdc, INT x1, INT y1, INT x2, INT y2)
{
- /* TODO: This should probably be revised to call PATH_AngleArc */
- /* (once it exists) */
- return PATH_Arc(hdc, x1, y1, x2, y2, x1, (y1+y2)/2, x1, (y1+y2)/2);
+ /* TODO: This should probably be revised to call PATH_AngleArc */
+ /* (once it exists) */
+ return PATH_Arc(hdc, x1, y1, x2, y2, x1, (y1+y2)/2, x1, (y1+y2)/2);
}
/* PATH_Arc
BOOL PATH_Arc(HDC hdc, INT x1, INT y1, INT x2, INT y2,
INT xStart, INT yStart, INT xEnd, INT yEnd)
{
- GdiPath *pPath;
- DC *pDC;
- double angleStart, angleEnd, angleStartQuadrant, angleEndQuadrant=0.0;
- /* Initialize angleEndQuadrant to silence gcc's warning */
- double x, y;
- FLOAT_POINT corners[2], pointStart, pointEnd;
- BOOL start, end;
- INT temp;
-
- /* FIXME: This function should check for all possible error returns */
- /* FIXME: Do we have to respect newStroke? */
+ GdiPath *pPath;
+ DC *pDC;
+ double angleStart, angleEnd, angleStartQuadrant, angleEndQuadrant=0.0;
+ /* Initialize angleEndQuadrant to silence gcc's warning */
+ double x, y;
+ FLOAT_POINT corners[2], pointStart, pointEnd;
+ BOOL start, end;
+ INT temp;
+
+ /* FIXME: This function should check for all possible error returns */
+ /* FIXME: Do we have to respect newStroke? */
- /* Get pointer to DC */
- pDC=DC_HandleToPtr(hdc);
- if(pDC==NULL)
- return FALSE;
-
- /* Get pointer to path */
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ /* Get pointer to DC */
+ pDC=DC_HandleToPtr(hdc);
+ if(pDC==NULL)
+ return FALSE;
+
+ /* Get pointer to path */
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
- /* FIXME: Do we have to close the current figure? */
+ /* FIXME: Do we have to close the current figure? */
- /* Check for zero height / width */
- /* FIXME: Only in GM_COMPATIBLE? */
- if(x1==x2 || y1==y2)
- return TRUE;
+ /* Check for zero height / width */
+ /* FIXME: Only in GM_COMPATIBLE? */
+ if(x1==x2 || y1==y2)
+ return TRUE;
- /* Convert points to device coordinates */
- corners[0].x=(FLOAT)x1;
- corners[0].y=(FLOAT)y1;
- corners[1].x=(FLOAT)x2;
- corners[1].y=(FLOAT)y2;
- pointStart.x=(FLOAT)xStart;
- pointStart.y=(FLOAT)yStart;
- pointEnd.x=(FLOAT)xEnd;
- pointEnd.y=(FLOAT)yEnd;
- INTERNAL_LPTODP_FLOAT(pDC, corners);
- INTERNAL_LPTODP_FLOAT(pDC, corners+1);
- INTERNAL_LPTODP_FLOAT(pDC, &pointStart);
- INTERNAL_LPTODP_FLOAT(pDC, &pointEnd);
-
- /* Make sure first corner is top left and second corner is bottom right */
- if(corners[0].x>corners[1].x)
- {
- temp=corners[0].x;
- corners[0].x=corners[1].x;
- corners[1].x=temp;
- }
- if(corners[0].y>corners[1].y)
- {
- temp=corners[0].y;
- corners[0].y=corners[1].y;
- corners[1].y=temp;
- }
-
- /* Compute start and end angle */
- PATH_NormalizePoint(corners, &pointStart, &x, &y);
- angleStart=atan2(y, x);
- PATH_NormalizePoint(corners, &pointEnd, &x, &y);
- angleEnd=atan2(y, x);
-
- /* Make sure the end angle is "on the right side" of the start angle */
- if(W32kGetArcDirection(hdc)==AD_CLOCKWISE)
- {
- if(angleEnd<=angleStart)
- {
- angleEnd+=2*M_PI;
- assert(angleEnd>=angleStart);
- }
- }
- else
- {
- if(angleEnd>=angleStart)
- {
- angleEnd-=2*M_PI;
- assert(angleEnd<=angleStart);
- }
- }
-
- /* In GM_COMPATIBLE, don't include bottom and right edges */
- if(W32kGetGraphicsMode(hdc)==GM_COMPATIBLE)
- {
- corners[1].x--;
- corners[1].y--;
- }
+ /* Convert points to device coordinates */
+ corners[0].x=(FLOAT)x1;
+ corners[0].y=(FLOAT)y1;
+ corners[1].x=(FLOAT)x2;
+ corners[1].y=(FLOAT)y2;
+ pointStart.x=(FLOAT)xStart;
+ pointStart.y=(FLOAT)yStart;
+ pointEnd.x=(FLOAT)xEnd;
+ pointEnd.y=(FLOAT)yEnd;
+ INTERNAL_LPTODP_FLOAT(pDC, corners);
+ INTERNAL_LPTODP_FLOAT(pDC, corners+1);
+ INTERNAL_LPTODP_FLOAT(pDC, &pointStart);
+ INTERNAL_LPTODP_FLOAT(pDC, &pointEnd);
+
+ /* Make sure first corner is top left and second corner is bottom right */
+ if(corners[0].x>corners[1].x)
+ {
+ temp=corners[0].x;
+ corners[0].x=corners[1].x;
+ corners[1].x=temp;
+ }
+ if(corners[0].y>corners[1].y)
+ {
+ temp=corners[0].y;
+ corners[0].y=corners[1].y;
+ corners[1].y=temp;
+ }
+
+ /* Compute start and end angle */
+ PATH_NormalizePoint(corners, &pointStart, &x, &y);
+ angleStart=atan2(y, x);
+ PATH_NormalizePoint(corners, &pointEnd, &x, &y);
+ angleEnd=atan2(y, x);
+
+ /* Make sure the end angle is "on the right side" of the start angle */
+ if(W32kGetArcDirection(hdc)==AD_CLOCKWISE)
+ {
+ if(angleEnd<=angleStart)
+ {
+ angleEnd+=2*M_PI;
+ assert(angleEnd>=angleStart);
+ }
+ }
+ else
+ {
+ if(angleEnd>=angleStart)
+ {
+ angleEnd-=2*M_PI;
+ assert(angleEnd<=angleStart);
+ }
+ }
+
+ /* In GM_COMPATIBLE, don't include bottom and right edges */
+ if(W32kGetGraphicsMode(hdc)==GM_COMPATIBLE)
+ {
+ corners[1].x--;
+ corners[1].y--;
+ }
- /* Add the arc to the path with one Bezier spline per quadrant that the
- * arc spans */
- start=TRUE;
- end=FALSE;
- do
- {
- /* Determine the start and end angles for this quadrant */
- if(start)
- {
- angleStartQuadrant=angleStart;
- if(W32kGetArcDirection(hdc)==AD_CLOCKWISE)
- angleEndQuadrant=(floor(angleStart/M_PI_2)+1.0)*M_PI_2;
- else
- angleEndQuadrant=(ceil(angleStart/M_PI_2)-1.0)*M_PI_2;
- }
+ /* Add the arc to the path with one Bezier spline per quadrant that the
+ * arc spans */
+ start=TRUE;
+ end=FALSE;
+ do
+ {
+ /* Determine the start and end angles for this quadrant */
+ if(start)
+ {
+ angleStartQuadrant=angleStart;
+ if(W32kGetArcDirection(hdc)==AD_CLOCKWISE)
+ angleEndQuadrant=(floor(angleStart/M_PI_2)+1.0)*M_PI_2;
else
- {
- angleStartQuadrant=angleEndQuadrant;
- if(W32kGetArcDirection(hdc)==AD_CLOCKWISE)
- angleEndQuadrant+=M_PI_2;
- else
- angleEndQuadrant-=M_PI_2;
- }
-
- /* Have we reached the last part of the arc? */
- if((W32kGetArcDirection(hdc)==AD_CLOCKWISE &&
- angleEnd<angleEndQuadrant) ||
- (W32kGetArcDirection(hdc)==AD_COUNTERCLOCKWISE &&
- angleEnd>angleEndQuadrant))
- {
- /* Adjust the end angle for this quadrant */
- angleEndQuadrant=angleEnd;
- end=TRUE;
- }
-
- /* Add the Bezier spline to the path */
- PATH_DoArcPart(pPath, corners, angleStartQuadrant, angleEndQuadrant,
- start);
- start=FALSE;
- } while(!end);
-
- return TRUE;
+ angleEndQuadrant=(ceil(angleStart/M_PI_2)-1.0)*M_PI_2;
+ }
+ else
+ {
+ angleStartQuadrant=angleEndQuadrant;
+ if(W32kGetArcDirection(hdc)==AD_CLOCKWISE)
+ angleEndQuadrant+=M_PI_2;
+ else
+ angleEndQuadrant-=M_PI_2;
+ }
+
+ /* Have we reached the last part of the arc? */
+ if((W32kGetArcDirection(hdc)==AD_CLOCKWISE &&
+ angleEnd<angleEndQuadrant) ||
+ (W32kGetArcDirection(hdc)==AD_COUNTERCLOCKWISE &&
+ angleEnd>angleEndQuadrant))
+ {
+ /* Adjust the end angle for this quadrant */
+ angleEndQuadrant=angleEnd;
+ end=TRUE;
+ }
+
+ /* Add the Bezier spline to the path */
+ PATH_DoArcPart(pPath, corners, angleStartQuadrant, angleEndQuadrant, start);
+ start=FALSE;
+ } while(!end);
+
+ return TRUE;
}
BOOL PATH_PolyBezierTo(HDC hdc, const POINT *pts, DWORD cbPoints)
{
- GdiPath *pPath;
- POINT pt;
- INT i;
+ GdiPath *pPath;
+ POINT pt;
+ INT i;
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
-
- /* Add a PT_MOVETO if necessary */
- if(pPath->newStroke)
- {
- pPath->newStroke=FALSE;
- if(!W32kGetCurrentPositionEx(hdc, &pt) ||
- !W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- if(!PATH_AddEntry(pPath, &pt, PT_MOVETO))
- return FALSE;
- }
-
- for(i = 0; i < cbPoints; i++) {
- pt = pts[i];
- if(!W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- PATH_AddEntry(pPath, &pt, PT_BEZIERTO);
- }
- return TRUE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
+
+ /* Add a PT_MOVETO if necessary */
+ if(pPath->newStroke)
+ {
+ pPath->newStroke=FALSE;
+ if(!W32kGetCurrentPositionEx(hdc, &pt) ||
+ !W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ if(!PATH_AddEntry(pPath, &pt, PT_MOVETO))
+ return FALSE;
+ }
+
+ for(i = 0; i < cbPoints; i++) {
+ pt = pts[i];
+ if(!W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ PATH_AddEntry(pPath, &pt, PT_BEZIERTO);
+ }
+ return TRUE;
}
BOOL PATH_PolyBezier(HDC hdc, const POINT *pts, DWORD cbPoints)
{
- GdiPath *pPath;
- POINT pt;
- INT i;
+ GdiPath *pPath;
+ POINT pt;
+ INT i;
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
/* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
+ if(pPath->state!=PATH_Open)
+ return FALSE;
- for(i = 0; i < cbPoints; i++) {
- pt = pts[i];
- if(!W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- PATH_AddEntry(pPath, &pt, (i == 0) ? PT_MOVETO : PT_BEZIERTO);
- }
- return TRUE;
+ for(i = 0; i < cbPoints; i++) {
+ pt = pts[i];
+ if(!W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ PATH_AddEntry(pPath, &pt, (i == 0) ? PT_MOVETO : PT_BEZIERTO);
+ }
+ return TRUE;
}
BOOL PATH_Polyline(HDC hdc, const POINT *pts, DWORD cbPoints)
{
- GdiPath *pPath;
- POINT pt;
- INT i;
+ GdiPath *pPath;
+ POINT pt;
+ INT i;
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
- for(i = 0; i < cbPoints; i++) {
- pt = pts[i];
- if(!W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- PATH_AddEntry(pPath, &pt, (i == 0) ? PT_MOVETO : PT_LINETO);
- }
- return TRUE;
+ for(i = 0; i < cbPoints; i++) {
+ pt = pts[i];
+ if(!W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ PATH_AddEntry(pPath, &pt, (i == 0) ? PT_MOVETO : PT_LINETO);
+ }
+ return TRUE;
}
BOOL PATH_PolylineTo(HDC hdc, const POINT *pts, DWORD cbPoints)
{
- GdiPath *pPath;
- POINT pt;
- INT i;
+ GdiPath *pPath;
+ POINT pt;
+ INT i;
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
- /* Add a PT_MOVETO if necessary */
- if(pPath->newStroke)
- {
- pPath->newStroke=FALSE;
- if(!W32kGetCurrentPositionEx(hdc, &pt) ||
- !W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- if(!PATH_AddEntry(pPath, &pt, PT_MOVETO))
- return FALSE;
- }
+ /* Add a PT_MOVETO if necessary */
+ if(pPath->newStroke)
+ {
+ pPath->newStroke=FALSE;
+ if(!W32kGetCurrentPositionEx(hdc, &pt) ||
+ !W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ if(!PATH_AddEntry(pPath, &pt, PT_MOVETO))
+ return FALSE;
+ }
- for(i = 0; i < cbPoints; i++) {
- pt = pts[i];
- if(!W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- PATH_AddEntry(pPath, &pt, PT_LINETO);
- }
+ for(i = 0; i < cbPoints; i++) {
+ pt = pts[i];
+ if(!W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ PATH_AddEntry(pPath, &pt, PT_LINETO);
+ }
- return TRUE;
+ return TRUE;
}
BOOL PATH_Polygon(HDC hdc, const POINT *pts, DWORD cbPoints)
{
- GdiPath *pPath;
- POINT pt;
- INT i;
+ GdiPath *pPath;
+ POINT pt;
+ INT i;
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
- for(i = 0; i < cbPoints; i++) {
- pt = pts[i];
- if(!W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- PATH_AddEntry(pPath, &pt, (i == 0) ? PT_MOVETO :
- ((i == cbPoints-1) ? PT_LINETO | PT_CLOSEFIGURE :
- PT_LINETO));
- }
- return TRUE;
+ for(i = 0; i < cbPoints; i++) {
+ pt = pts[i];
+ if(!W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ PATH_AddEntry(pPath, &pt, (i == 0) ? PT_MOVETO :
+ ((i == cbPoints-1) ? PT_LINETO | PT_CLOSEFIGURE :
+ PT_LINETO));
+ }
+ return TRUE;
}
BOOL PATH_PolyPolygon( HDC hdc, const POINT* pts, const INT* counts,
UINT polygons )
{
- GdiPath *pPath;
- POINT pt, startpt;
- INT poly, point, i;
+ GdiPath *pPath;
+ POINT pt, startpt;
+ INT poly, point, i;
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
-
- for(i = 0, poly = 0; poly < polygons; poly++) {
- for(point = 0; point < counts[poly]; point++, i++) {
- pt = pts[i];
- if(!W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- if(point == 0) startpt = pt;
- PATH_AddEntry(pPath, &pt, (point == 0) ? PT_MOVETO : PT_LINETO);
- }
- /* win98 adds an extra line to close the figure for some reason */
- PATH_AddEntry(pPath, &startpt, PT_LINETO | PT_CLOSEFIGURE);
- }
- return TRUE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
+
+ for(i = 0, poly = 0; poly < polygons; poly++) {
+ for(point = 0; point < counts[poly]; point++, i++) {
+ pt = pts[i];
+ if(!W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ if(point == 0) startpt = pt;
+ PATH_AddEntry(pPath, &pt, (point == 0) ? PT_MOVETO : PT_LINETO);
+ }
+ /* win98 adds an extra line to close the figure for some reason */
+ PATH_AddEntry(pPath, &startpt, PT_LINETO | PT_CLOSEFIGURE);
+ }
+ return TRUE;
}
BOOL PATH_PolyPolyline( HDC hdc, const POINT* pts, const DWORD* counts,
DWORD polylines )
{
- GdiPath *pPath;
- POINT pt;
- INT poly, point, i;
+ GdiPath *pPath;
+ POINT pt;
+ INT poly, point, i;
- if(!PATH_GetPathFromHDC(hdc, &pPath))
- return FALSE;
+ if(!PATH_GetPathFromHDC(hdc, &pPath))
+ return FALSE;
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
-
- for(i = 0, poly = 0; poly < polylines; poly++) {
- for(point = 0; point < counts[poly]; point++, i++) {
- pt = pts[i];
- if(!W32kLPtoDP(hdc, &pt, 1))
- return FALSE;
- PATH_AddEntry(pPath, &pt, (point == 0) ? PT_MOVETO : PT_LINETO);
- }
- }
- return TRUE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
+
+ for(i = 0, poly = 0; poly < polylines; poly++) {
+ for(point = 0; point < counts[poly]; point++, i++) {
+ pt = pts[i];
+ if(!W32kLPtoDP(hdc, &pt, 1))
+ return FALSE;
+ PATH_AddEntry(pPath, &pt, (point == 0) ? PT_MOVETO : PT_LINETO);
+ }
+ }
+ return TRUE;
}
/***********************************************************************
*/
static BOOL PATH_AddFlatBezier(GdiPath *pPath, POINT *pt, BOOL closed)
{
- POINT *pts;
- INT no, i;
+ POINT *pts;
+ INT no, i;
- pts = GDI_Bezier( pt, 4, &no );
- if(!pts) return FALSE;
+ pts = GDI_Bezier( pt, 4, &no );
+ if(!pts) return FALSE;
- for(i = 1; i < no; i++)
- PATH_AddEntry(pPath, &pts[i],
- (i == no-1 && closed) ? PT_LINETO | PT_CLOSEFIGURE : PT_LINETO);
- ExFreePool(pts);
- return TRUE;
+ for(i = 1; i < no; i++)
+ PATH_AddEntry(pPath, &pts[i], (i == no-1 && closed) ? PT_LINETO | PT_CLOSEFIGURE : PT_LINETO);
+
+ ExFreePool(pts);
+ return TRUE;
}
/* PATH_FlattenPath
*/
static BOOL PATH_FlattenPath(GdiPath *pPath)
{
- GdiPath newPath;
- INT srcpt;
-
- memset(&newPath, 0, sizeof(newPath));
- newPath.state = PATH_Open;
- for(srcpt = 0; srcpt < pPath->numEntriesUsed; srcpt++) {
- switch(pPath->pFlags[srcpt] & ~PT_CLOSEFIGURE) {
- case PT_MOVETO:
- case PT_LINETO:
- PATH_AddEntry(&newPath, &pPath->pPoints[srcpt],
- pPath->pFlags[srcpt]);
- break;
- case PT_BEZIERTO:
- PATH_AddFlatBezier(&newPath, &pPath->pPoints[srcpt-1],
- pPath->pFlags[srcpt+2] & PT_CLOSEFIGURE);
- srcpt += 2;
- break;
- }
+ GdiPath newPath;
+ INT srcpt;
+
+ memset(&newPath, 0, sizeof(newPath));
+ newPath.state = PATH_Open;
+ for(srcpt = 0; srcpt < pPath->numEntriesUsed; srcpt++) {
+ switch(pPath->pFlags[srcpt] & ~PT_CLOSEFIGURE) {
+ case PT_MOVETO:
+ case PT_LINETO:
+ PATH_AddEntry(&newPath, &pPath->pPoints[srcpt], pPath->pFlags[srcpt]);
+ break;
+ case PT_BEZIERTO:
+ PATH_AddFlatBezier(&newPath, &pPath->pPoints[srcpt-1], pPath->pFlags[srcpt+2] & PT_CLOSEFIGURE);
+ srcpt += 2;
+ break;
}
- newPath.state = PATH_Closed;
- PATH_AssignGdiPath(pPath, &newPath);
- PATH_EmptyPath(&newPath);
- return TRUE;
+ }
+ newPath.state = PATH_Closed;
+ PATH_AssignGdiPath(pPath, &newPath);
+ PATH_EmptyPath(&newPath);
+ return TRUE;
}
/* PATH_PathToRegion
static BOOL PATH_PathToRegion(const GdiPath *pPath, INT nPolyFillMode,
HRGN *pHrgn)
{
- int numStrokes, iStroke, i;
- INT *pNumPointsInStroke;
- HRGN hrgn;
+ int numStrokes, iStroke, i;
+ INT *pNumPointsInStroke;
+ HRGN hrgn;
- assert(pPath!=NULL);
- assert(pHrgn!=NULL);
+ assert(pPath!=NULL);
+ assert(pHrgn!=NULL);
- PATH_FlattenPath(pPath);
+ PATH_FlattenPath(pPath);
- /* FIXME: What happens when number of points is zero? */
+ /* FIXME: What happens when number of points is zero? */
- /* First pass: Find out how many strokes there are in the path */
- /* FIXME: We could eliminate this with some bookkeeping in GdiPath */
- numStrokes=0;
- for(i=0; i<pPath->numEntriesUsed; i++)
- if((pPath->pFlags[i] & ~PT_CLOSEFIGURE) == PT_MOVETO)
- numStrokes++;
-
- /* Allocate memory for number-of-points-in-stroke array */
- pNumPointsInStroke=(int *)ExAllocatePool(NonPagedPool, sizeof(int) * numStrokes);
- if(!pNumPointsInStroke)
- {
-// SetLastError(ERROR_NOT_ENOUGH_MEMORY);
- return FALSE;
- }
+ /* First pass: Find out how many strokes there are in the path */
+ /* FIXME: We could eliminate this with some bookkeeping in GdiPath */
+ numStrokes=0;
+ for(i=0; i<pPath->numEntriesUsed; i++)
+ if((pPath->pFlags[i] & ~PT_CLOSEFIGURE) == PT_MOVETO)
+ numStrokes++;
+
+ /* Allocate memory for number-of-points-in-stroke array */
+ pNumPointsInStroke=(int *)ExAllocatePool(NonPagedPool, sizeof(int) * numStrokes);
+ if(!pNumPointsInStroke)
+ {
+// SetLastError(ERROR_NOT_ENOUGH_MEMORY);
+ return FALSE;
+ }
- /* Second pass: remember number of points in each polygon */
- iStroke=-1; /* Will get incremented to 0 at beginning of first stroke */
- for(i=0; i<pPath->numEntriesUsed; i++)
- {
- /* Is this the beginning of a new stroke? */
- if((pPath->pFlags[i] & ~PT_CLOSEFIGURE) == PT_MOVETO)
- {
- iStroke++;
- pNumPointsInStroke[iStroke]=0;
- }
-
- pNumPointsInStroke[iStroke]++;
- }
-
- /* Create a region from the strokes */
-/* hrgn=CreatePolyPolygonRgn(pPath->pPoints, pNumPointsInStroke,
- numStrokes, nPolyFillMode); FIXME: reinclude when region code implemented */
- if(hrgn==(HRGN)0)
- {
-// SetLastError(ERROR_NOT_ENOUGH_MEMORY);
- return FALSE;
- }
+ /* Second pass: remember number of points in each polygon */
+ iStroke=-1; /* Will get incremented to 0 at beginning of first stroke */
+ for(i=0; i<pPath->numEntriesUsed; i++)
+ {
+ /* Is this the beginning of a new stroke? */
+ if((pPath->pFlags[i] & ~PT_CLOSEFIGURE) == PT_MOVETO)
+ {
+ iStroke++;
+ pNumPointsInStroke[iStroke]=0;
+ }
- /* Free memory for number-of-points-in-stroke array */
- ExFreePool(pNumPointsInStroke);
+ pNumPointsInStroke[iStroke]++;
+ }
- /* Success! */
- *pHrgn=hrgn;
- return TRUE;
+ /* Create a region from the strokes */
+/* hrgn=CreatePolyPolygonRgn(pPath->pPoints, pNumPointsInStroke,
+ numStrokes, nPolyFillMode); FIXME: reinclude when region code implemented */
+ if(hrgn==(HRGN)0)
+ {
+// SetLastError(ERROR_NOT_ENOUGH_MEMORY);
+ return FALSE;
+ }
+
+ /* Free memory for number-of-points-in-stroke array */
+ ExFreePool(pNumPointsInStroke);
+
+ /* Success! */
+ *pHrgn=hrgn;
+ return TRUE;
}
/* PATH_EmptyPath
*/
static void PATH_EmptyPath(GdiPath *pPath)
{
- assert(pPath!=NULL);
+ assert(pPath!=NULL);
- pPath->state=PATH_Null;
- pPath->numEntriesUsed=0;
+ pPath->state=PATH_Null;
+ pPath->numEntriesUsed=0;
}
/* PATH_AddEntry
*/
BOOL PATH_AddEntry(GdiPath *pPath, const POINT *pPoint, BYTE flags)
{
- assert(pPath!=NULL);
+ assert(pPath!=NULL);
- /* FIXME: If newStroke is true, perhaps we want to check that we're
- * getting a PT_MOVETO
- */
+ /* FIXME: If newStroke is true, perhaps we want to check that we're
+ * getting a PT_MOVETO
+ */
- /* Check that path is open */
- if(pPath->state!=PATH_Open)
- return FALSE;
+ /* Check that path is open */
+ if(pPath->state!=PATH_Open)
+ return FALSE;
- /* Reserve enough memory for an extra path entry */
- if(!PATH_ReserveEntries(pPath, pPath->numEntriesUsed+1))
- return FALSE;
+ /* Reserve enough memory for an extra path entry */
+ if(!PATH_ReserveEntries(pPath, pPath->numEntriesUsed+1))
+ return FALSE;
- /* Store information in path entry */
- pPath->pPoints[pPath->numEntriesUsed]=*pPoint;
- pPath->pFlags[pPath->numEntriesUsed]=flags;
+ /* Store information in path entry */
+ pPath->pPoints[pPath->numEntriesUsed]=*pPoint;
+ pPath->pFlags[pPath->numEntriesUsed]=flags;
- /* If this is PT_CLOSEFIGURE, we have to start a new stroke next time */
- if((flags & PT_CLOSEFIGURE) == PT_CLOSEFIGURE)
- pPath->newStroke=TRUE;
+ /* If this is PT_CLOSEFIGURE, we have to start a new stroke next time */
+ if((flags & PT_CLOSEFIGURE) == PT_CLOSEFIGURE)
+ pPath->newStroke=TRUE;
- /* Increment entry count */
- pPath->numEntriesUsed++;
+ /* Increment entry count */
+ pPath->numEntriesUsed++;
- return TRUE;
+ return TRUE;
}
/* PATH_ReserveEntries
*/
static BOOL PATH_ReserveEntries(GdiPath *pPath, INT numEntries)
{
- INT numEntriesToAllocate;
- POINT *pPointsNew;
- BYTE *pFlagsNew;
+ INT numEntriesToAllocate;
+ POINT *pPointsNew;
+ BYTE *pFlagsNew;
- assert(pPath!=NULL);
- assert(numEntries>=0);
-
- /* Do we have to allocate more memory? */
- if(numEntries > pPath->numEntriesAllocated)
- {
- /* Find number of entries to allocate. We let the size of the array
- * grow exponentially, since that will guarantee linear time
- * complexity. */
- if(pPath->numEntriesAllocated)
- {
- numEntriesToAllocate=pPath->numEntriesAllocated;
- while(numEntriesToAllocate<numEntries)
- numEntriesToAllocate=numEntriesToAllocate*GROW_FACTOR_NUMER/
- GROW_FACTOR_DENOM;
- }
- else
- numEntriesToAllocate=numEntries;
+ assert(pPath!=NULL);
+ assert(numEntries>=0);
+
+ /* Do we have to allocate more memory? */
+ if(numEntries > pPath->numEntriesAllocated)
+ {
+ /* Find number of entries to allocate. We let the size of the array
+ * grow exponentially, since that will guarantee linear time
+ * complexity. */
+ if(pPath->numEntriesAllocated)
+ {
+ numEntriesToAllocate=pPath->numEntriesAllocated;
+ while(numEntriesToAllocate<numEntries)
+ numEntriesToAllocate=numEntriesToAllocate*GROW_FACTOR_NUMER/GROW_FACTOR_DENOM;
+ } else
+ numEntriesToAllocate=numEntries;
+
+ /* Allocate new arrays */
+ pPointsNew=(POINT *)ExAllocatePool(NonPagedPool, numEntriesToAllocate * sizeof(POINT));
+ if(!pPointsNew)
+ return FALSE;
+ pFlagsNew=(BYTE *)ExAllocatePool(NonPagedPool, numEntriesToAllocate * sizeof(BYTE));
+ if(!pFlagsNew)
+ {
+ ExFreePool(pPointsNew);
+ return FALSE;
+ }
- /* Allocate new arrays */
- pPointsNew=(POINT *)ExAllocatePool(NonPagedPool, numEntriesToAllocate * sizeof(POINT));
- if(!pPointsNew)
- return FALSE;
- pFlagsNew=(BYTE *)ExAllocatePool(NonPagedPool, numEntriesToAllocate * sizeof(BYTE));
- if(!pFlagsNew)
- {
- ExFreePool(pPointsNew);
- return FALSE;
- }
-
- /* Copy old arrays to new arrays and discard old arrays */
- if(pPath->pPoints)
- {
- assert(pPath->pFlags);
-
- memcpy(pPointsNew, pPath->pPoints,
- sizeof(POINT)*pPath->numEntriesUsed);
- memcpy(pFlagsNew, pPath->pFlags,
- sizeof(BYTE)*pPath->numEntriesUsed);
-
- ExFreePool(pPath->pPoints);
- ExFreePool(pPath->pFlags);
- }
- pPath->pPoints=pPointsNew;
- pPath->pFlags=pFlagsNew;
- pPath->numEntriesAllocated=numEntriesToAllocate;
- }
-
- return TRUE;
+ /* Copy old arrays to new arrays and discard old arrays */
+ if(pPath->pPoints)
+ {
+ assert(pPath->pFlags);
+
+ memcpy(pPointsNew, pPath->pPoints, sizeof(POINT)*pPath->numEntriesUsed);
+ memcpy(pFlagsNew, pPath->pFlags, sizeof(BYTE)*pPath->numEntriesUsed);
+
+ ExFreePool(pPath->pPoints);
+ ExFreePool(pPath->pFlags);
+ }
+ pPath->pPoints=pPointsNew;
+ pPath->pFlags=pFlagsNew;
+ pPath->numEntriesAllocated=numEntriesToAllocate;
+ }
+
+ return TRUE;
}
/* PATH_GetPathFromHDC
*/
static BOOL PATH_GetPathFromHDC(HDC hdc, GdiPath **ppPath)
{
- DC *pDC;
-
- pDC=DC_HandleToPtr(hdc);
- if(pDC)
- {
- *ppPath=&pDC->w.path;
- return TRUE;
- }
- else
- return FALSE;
+ DC *pDC;
+
+ pDC=DC_HandleToPtr(hdc);
+ if(pDC)
+ {
+ *ppPath=&pDC->w.path;
+ return TRUE;
+ } else
+ return FALSE;
}
/* PATH_DoArcPart
static BOOL PATH_DoArcPart(GdiPath *pPath, FLOAT_POINT corners[],
double angleStart, double angleEnd, BOOL addMoveTo)
{
- double halfAngle, a;
- double xNorm[4], yNorm[4];
- POINT point;
- int i;
-
- assert(fabs(angleEnd-angleStart)<=M_PI_2);
-
- /* FIXME: Is there an easier way of computing this? */
-
- /* Compute control points */
- halfAngle=(angleEnd-angleStart)/2.0;
- if(fabs(halfAngle)>1e-8)
- {
- a=4.0/3.0*(1-cos(halfAngle))/sin(halfAngle);
- xNorm[0]=cos(angleStart);
- yNorm[0]=sin(angleStart);
- xNorm[1]=xNorm[0] - a*yNorm[0];
- yNorm[1]=yNorm[0] + a*xNorm[0];
- xNorm[3]=cos(angleEnd);
- yNorm[3]=sin(angleEnd);
- xNorm[2]=xNorm[3] + a*yNorm[3];
- yNorm[2]=yNorm[3] - a*xNorm[3];
- }
- else
- for(i=0; i<4; i++)
- {
- xNorm[i]=cos(angleStart);
- yNorm[i]=sin(angleStart);
- }
+ double halfAngle, a;
+ double xNorm[4], yNorm[4];
+ POINT point;
+ int i;
+
+ assert(fabs(angleEnd-angleStart)<=M_PI_2);
+
+ /* FIXME: Is there an easier way of computing this? */
+
+ /* Compute control points */
+ halfAngle=(angleEnd-angleStart)/2.0;
+ if(fabs(halfAngle)>1e-8)
+ {
+ a=4.0/3.0*(1-cos(halfAngle))/sin(halfAngle);
+ xNorm[0]=cos(angleStart);
+ yNorm[0]=sin(angleStart);
+ xNorm[1]=xNorm[0] - a*yNorm[0];
+ yNorm[1]=yNorm[0] + a*xNorm[0];
+ xNorm[3]=cos(angleEnd);
+ yNorm[3]=sin(angleEnd);
+ xNorm[2]=xNorm[3] + a*yNorm[3];
+ yNorm[2]=yNorm[3] - a*xNorm[3];
+ } else
+ for(i=0; i<4; i++)
+ {
+ xNorm[i]=cos(angleStart);
+ yNorm[i]=sin(angleStart);
+ }
- /* Add starting point to path if desired */
- if(addMoveTo)
- {
- PATH_ScaleNormalizedPoint(corners, xNorm[0], yNorm[0], &point);
- if(!PATH_AddEntry(pPath, &point, PT_MOVETO))
- return FALSE;
- }
+ /* Add starting point to path if desired */
+ if(addMoveTo)
+ {
+ PATH_ScaleNormalizedPoint(corners, xNorm[0], yNorm[0], &point);
+ if(!PATH_AddEntry(pPath, &point, PT_MOVETO))
+ return FALSE;
+ }
- /* Add remaining control points */
- for(i=1; i<4; i++)
- {
- PATH_ScaleNormalizedPoint(corners, xNorm[i], yNorm[i], &point);
- if(!PATH_AddEntry(pPath, &point, PT_BEZIERTO))
- return FALSE;
- }
+ /* Add remaining control points */
+ for(i=1; i<4; i++)
+ {
+ PATH_ScaleNormalizedPoint(corners, xNorm[i], yNorm[i], &point);
+ if(!PATH_AddEntry(pPath, &point, PT_BEZIERTO))
+ return FALSE;
+ }
- return TRUE;
+ return TRUE;
}
/* PATH_ScaleNormalizedPoint
static void PATH_ScaleNormalizedPoint(FLOAT_POINT corners[], double x,
double y, POINT *pPoint)
{
- pPoint->x=GDI_ROUND( (double)corners[0].x +
- (double)(corners[1].x-corners[0].x)*0.5*(x+1.0) );
- pPoint->y=GDI_ROUND( (double)corners[0].y +
- (double)(corners[1].y-corners[0].y)*0.5*(y+1.0) );
+ pPoint->x=GDI_ROUND( (double)corners[0].x + (double)(corners[1].x-corners[0].x)*0.5*(x+1.0) );
+ pPoint->y=GDI_ROUND( (double)corners[0].y + (double)(corners[1].y-corners[0].y)*0.5*(y+1.0) );
}
/* PATH_NormalizePoint
const FLOAT_POINT *pPoint,
double *pX, double *pY)
{
- *pX=(double)(pPoint->x-corners[0].x)/(double)(corners[1].x-corners[0].x) *
- 2.0 - 1.0;
- *pY=(double)(pPoint->y-corners[0].y)/(double)(corners[1].y-corners[0].y) *
- 2.0 - 1.0;
+ *pX=(double)(pPoint->x-corners[0].x)/(double)(corners[1].x-corners[0].x) * 2.0 - 1.0;
+ *pY=(double)(pPoint->y-corners[0].y)/(double)(corners[1].y-corners[0].y) * 2.0 - 1.0;
}
-
-
#undef WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <ddk/ntddk.h>
STDCALL
W32kCreatePen(INT PenStyle, INT Width, COLORREF Color)
{
- LOGPEN logpen;
+ LOGPEN logpen;
- logpen.lopnStyle = PenStyle;
- logpen.lopnWidth.x = Width;
- logpen.lopnWidth.y = 0;
- logpen.lopnColor = Color;
+ logpen.lopnStyle = PenStyle;
+ logpen.lopnWidth.x = Width;
+ logpen.lopnWidth.y = 0;
+ logpen.lopnColor = Color;
- return W32kCreatePenIndirect(&logpen);
+ return W32kCreatePenIndirect(&logpen);
}
HPEN
STDCALL
W32kCreatePenIndirect(CONST PLOGPEN lgpn)
{
- PPENOBJ penPtr;
- HPEN hpen;
+ PPENOBJ penPtr;
+ HPEN hpen;
- if (lgpn->lopnStyle > PS_INSIDEFRAME) return 0;
+ if (lgpn->lopnStyle > PS_INSIDEFRAME) return 0;
- penPtr = PENOBJ_AllocPen();
- hpen = PENOBJ_PtrToHandle(penPtr);
- if (!hpen) return 0;
- PENOBJ_LockPen(hpen);
+ penPtr = PENOBJ_AllocPen();
+ hpen = PENOBJ_PtrToHandle(penPtr);
+ if (!hpen) return 0;
+ PENOBJ_LockPen(hpen);
- penPtr->logpen.lopnStyle = lgpn->lopnStyle;
- penPtr->logpen.lopnWidth = lgpn->lopnWidth;
- penPtr->logpen.lopnColor = lgpn->lopnColor;
+ penPtr->logpen.lopnStyle = lgpn->lopnStyle;
+ penPtr->logpen.lopnWidth = lgpn->lopnWidth;
+ penPtr->logpen.lopnColor = lgpn->lopnColor;
- PENOBJ_UnlockPen(hpen);
+ PENOBJ_UnlockPen(hpen);
- return hpen;
+ return hpen;
}
HPEN
-
-
#undef WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <ddk/ntddk.h>
-
-
#undef WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <ddk/ntddk.h>
#include <win32k/dc.h>
#include <win32k/text.h>
#include <win32k/kapi.h>
+#include <freetype/freetype.h>
// #define NDEBUG
#include <win32k/debug1.h>
+FT_Library library;
+
+BOOL InitFontSupport()
+{
+ ULONG error;
+
+ error = FT_Init_FreeType(&library);
+ if(error)
+ {
+ return FALSE;
+ } else return TRUE;
+}
+
int
STDCALL
W32kAddFontResource(LPCWSTR Filename)
STDCALL
W32kCreateFontIndirect(CONST LPLOGFONT lf)
{
- UNIMPLEMENTED;
+ DbgPrint("WARNING: W32kCreateFontIndirect is current unimplemented\n");
}
BOOL
PDC dc = DC_HandleToPtr(hDC);
if (!dc)
- {
- return 0x80000000;
- }
+ {
+ return 0x80000000;
+ }
oldColor = dc->w.textColor;
dc->w.textColor = color;
LPCWSTR String,
int Count)
{
- DC *dc = DC_HandleToPtr(hDC);
- SURFOBJ *SurfObj = AccessUserObject(dc->Surface);
- UNICODE_STRING UString;
- ANSI_STRING AString;
+ // Fixme: Call EngTextOut, which does the real work (calling DrvTextOut where appropriate)
+
+ DC *dc = DC_HandleToPtr(hDC);
+ SURFOBJ *SurfObj = AccessUserObject(dc->Surface);
+ UNICODE_STRING FileName;
+ int error, glyph_index, n, load_flags = FT_LOAD_RENDER, i, j;
+ FT_Face face;
+ FT_GlyphSlot glyph;
+ NTSTATUS Status;
+ HANDLE FileHandle;
+ OBJECT_ATTRIBUTES ObjectAttributes;
+ FILE_STANDARD_INFORMATION FileStdInfo;
+ PVOID buffer;
+ ULONG size, TextLeft = XStart, TextTop = YStart, SpaceBetweenChars = 5, StringLength;
+ FT_Vector origin;
+ FT_Bitmap bit, bit2, bit3;
+ POINTL SourcePoint;
+ RECTL DestRect;
+ HBITMAP HSourceGlyph;
+ PSURFOBJ SourceGlyphSurf;
+ SIZEL bitSize;
+ FT_CharMap found = 0;
+ FT_CharMap charmap;
+ PCHAR bitbuf;
+
+ // For now we're just going to use an internal font
+// grWriteCellString(SurfObj, XStart, YStart, AString->Buffer, 0xffffff);
+
+ // Prepare the Unicode FileName
+ RtlCreateUnicodeString(&FileName, L"\\SystemRoot\\fonts\\arial.ttf");
+
+ // Open the Module
+ InitializeObjectAttributes(&ObjectAttributes, &FileName, 0, NULL, NULL);
+
+ Status = NtOpenFile(&FileHandle, FILE_ALL_ACCESS, &ObjectAttributes, NULL, 0, 0);
+
+ if (!NT_SUCCESS(Status))
+ {
+ DbgPrint("Could not open module file: %wZ\n", L"c:/reactos/fonts/arial.ttf");
+ return 0;
+ }
+
+ // Get the size of the file
+ Status = NtQueryInformationFile(FileHandle, NULL, &FileStdInfo, sizeof(FileStdInfo), FileStandardInformation);
+ if (!NT_SUCCESS(Status))
+ {
+ DbgPrint("Could not get file size\n");
+ return 0;
+ }
+
+ // Allocate nonpageable memory for driver
+ size = FileStdInfo.EndOfFile.u.LowPart;
+ buffer = ExAllocatePool(NonPagedPool, size);
+
+ if (buffer == NULL)
+ {
+ DbgPrint("could not allocate memory for module");
+ return 0;
+ }
+
+ // Load driver into memory chunk
+ Status = NtReadFile(FileHandle, 0, 0, 0, 0, buffer, FileStdInfo.EndOfFile.u.LowPart, 0, 0);
+ if (!NT_SUCCESS(Status))
+ {
+ DbgPrint("could not read module file into memory");
+ ExFreePool(buffer);
+
+ return 0;
+ }
+
+ NtClose(FileHandle);
+
+ error = FT_New_Memory_Face(library,
+ buffer, // first byte in memory
+ size, // size in bytes
+ 0, // face_index
+ &face );
+ if ( error == FT_Err_Unknown_File_Format )
+ {
+ DbgPrint("Unknown font file format\n");
+ }
+ else if ( error )
+ {
+ DbgPrint("Error reading font file\n");
+ }
+
+ DbgPrint("Family name: %s\n", face->family_name);
+ DbgPrint("Style name: %s\n", face->style_name);
+ DbgPrint("Num glyphs: %u\n", face->num_glyphs);
+ DbgPrint("Height: %d\n", face->height);
+
+ if (face->charmap == NULL)
+ {
+ DbgPrint("WARNING: No charmap selected!\n");
+ DbgPrint("This font face has %d charmaps\n", face->num_charmaps);
+
+ for ( n = 0; n < face->num_charmaps; n++ )
+ {
+ charmap = face->charmaps[n];
+ DbgPrint("found charmap encoding: %u\n", charmap->encoding);
+ if (charmap->encoding != 0)
+ {
+ found = charmap;
+ break;
+ }
+ }
+ }
+ if (!found) DbgPrint("WARNING: Could not find desired charmap!\n");
+
+ error = FT_Set_Charmap(face, found);
+ if (error) DbgPrint("WARNING: Could not set the charmap!\n");
+
+ error = FT_Set_Char_Size(
+ face, // handle to face object
+ 16*64, // char_width in 1/64th of points
+ 16*64, // char_height in 1/64th of points
+ 300, // horizontal device resolution
+ 300 ); // vertical device resolution
+
+ StringLength = wcslen(String);
+ DbgPrint("StringLength: %u\n", StringLength);
+
+ for(i=0; i<StringLength; i++)
+ {
+ glyph_index = FT_Get_Char_Index(face, *String);
+
+ error = FT_Load_Glyph(
+ face, // handle to face object
+ glyph_index, // glyph index
+ FT_LOAD_DEFAULT ); // load flags (erase previous glyph)
+ if(error) DbgPrint("WARNING: Failed to load and render glyph!\n");
+
+ glyph = face->glyph;
+
+ if ( glyph->format == ft_glyph_format_outline )
+ {
+ DbgPrint("Outline Format Font\n");
+ error = FT_Render_Glyph( glyph, ft_render_mode_normal );
+ if(error) DbgPrint("WARNING: Failed to render glyph!\n");
+ } else {
+ DbgPrint("Bitmap Format Font\n");
+ bit3.rows = glyph->bitmap.rows;
+ bit3.width = glyph->bitmap.width;
+ bit3.pitch = glyph->bitmap.pitch;
+ bit3.buffer = glyph->bitmap.buffer;
+ }
- RtlCreateUnicodeString(&UString, (PWSTR)String);
- RtlUnicodeStringToAnsiString(&AString, &UString, TRUE);
+ SourcePoint.x = 0;
+ SourcePoint.y = 0;
+ DestRect.left = TextLeft;
+ DestRect.top = TextTop;
+ DestRect.right = TextLeft + glyph->bitmap.width-1;
+ DestRect.bottom = TextTop + glyph->bitmap.rows-1;
+ bitSize.cx = glyph->bitmap.width-1;
+ bitSize.cy = glyph->bitmap.rows-1;
- // For now we're just going to use an internal font
- grWriteCellString(SurfObj, XStart, YStart, AString.Buffer, 0xffffff);
+ HSourceGlyph = EngCreateBitmap(bitSize, glyph->bitmap.pitch /* -1 */ , BMF_8BPP, 0, glyph->bitmap.buffer);
+ SourceGlyphSurf = AccessUserObject(HSourceGlyph);
- RtlFreeAnsiString(&AString);
- RtlFreeUnicodeString(&UString);
+ EngBitBlt(SurfObj, SourceGlyphSurf,
+ NULL, NULL, NULL, &DestRect, &SourcePoint, NULL, NULL, NULL, NULL);
+
+ TextLeft += glyph->bitmap.width + SpaceBetweenChars;
+ String++;
+ }
+
+DbgPrint("BREAK\n"); for (;;) ;
+
+/* RtlFreeAnsiString(AString);
+ RtlFreeUnicodeString(UString); */
}
UINT
{
UNIMPLEMENTED;
}
-