From 4ecb1c4ca770f69139dfd6be043e2b065633fa72 Mon Sep 17 00:00:00 2001 From: Rafal Harabien Date: Mon, 5 Mar 2012 20:17:42 +0000 Subject: [PATCH] [GDIPLUS] - Sync to Wine 1.3.37 svn path=/trunk/; revision=56055 --- reactos/dll/win32/gdiplus/CMakeLists.txt | 2 + reactos/dll/win32/gdiplus/brush.c | 97 +- reactos/dll/win32/gdiplus/font.c | 187 +- reactos/dll/win32/gdiplus/gdiplus.c | 17 +- reactos/dll/win32/gdiplus/gdiplus.manifest | 5 + reactos/dll/win32/gdiplus/gdiplus.rc | 22 + reactos/dll/win32/gdiplus/gdiplus.spec | 1260 +++++------ reactos/dll/win32/gdiplus/gdiplus_private.h | 76 +- reactos/dll/win32/gdiplus/graphics.c | 2148 +++++++++++++------ reactos/dll/win32/gdiplus/graphicspath.c | 200 +- reactos/dll/win32/gdiplus/image.c | 317 ++- reactos/dll/win32/gdiplus/matrix.c | 48 +- reactos/dll/win32/gdiplus/metafile.c | 553 +++++ reactos/dll/win32/gdiplus/region.c | 23 +- reactos/include/psdk/gdiplus.h | 4 +- reactos/include/psdk/gdiplusenums.h | 288 ++- reactos/include/psdk/gdiplusflat.h | 12 + reactos/include/psdk/gdiplusgpstubs.h | 2 + reactos/include/psdk/gdiplusimaging.h | 2 +- reactos/include/psdk/gdiplustypes.h | 27 + reactos/media/doc/README.WINE | 4 +- 21 files changed, 3879 insertions(+), 1415 deletions(-) create mode 100644 reactos/dll/win32/gdiplus/gdiplus.manifest create mode 100644 reactos/dll/win32/gdiplus/gdiplus.rc create mode 100644 reactos/dll/win32/gdiplus/metafile.c diff --git a/reactos/dll/win32/gdiplus/CMakeLists.txt b/reactos/dll/win32/gdiplus/CMakeLists.txt index 639a863c659..6fd174f2e6a 100644 --- a/reactos/dll/win32/gdiplus/CMakeLists.txt +++ b/reactos/dll/win32/gdiplus/CMakeLists.txt @@ -19,10 +19,12 @@ list(APPEND SOURCE image.c imageattributes.c matrix.c + metafile.c pathiterator.c pen.c region.c stringformat.c + gdiplus.rc ${CMAKE_CURRENT_BINARY_DIR}/gdiplus_stubs.c ${CMAKE_CURRENT_BINARY_DIR}/gdiplus.def) diff --git a/reactos/dll/win32/gdiplus/brush.c b/reactos/dll/win32/gdiplus/brush.c index 74dc833d88d..ccb731aee38 100644 --- a/reactos/dll/win32/gdiplus/brush.c +++ b/reactos/dll/win32/gdiplus/brush.c @@ -191,8 +191,14 @@ GpStatus WINGDIPAPI GdipCloneBrush(GpBrush *brush, GpBrush **clone) GpStatus stat; GpTexture *texture = (GpTexture*)brush; GpTexture *new_texture; + UINT width, height; - stat = GdipCreateTexture(texture->image, texture->wrap, &new_texture); + stat = GdipGetImageWidth(texture->image, &width); + if (stat != Ok) return stat; + stat = GdipGetImageHeight(texture->image, &height); + if (stat != Ok) return stat; + + stat = GdipCreateTextureIA(texture->image, texture->imageattributes, 0, 0, width, height, &new_texture); if (stat == Ok) { @@ -246,6 +252,17 @@ static const char HatchBrushes[][8] = { { 0x00, 0x00, 0xff, 0xff, 0x00, 0x00, 0xff, 0xff }, /* HatchStyleDarkHorizontal */ }; +GpStatus get_hatch_data(HatchStyle hatchstyle, const char **result) +{ + if (hatchstyle < sizeof(HatchBrushes) / sizeof(HatchBrushes[0])) + { + *result = HatchBrushes[hatchstyle]; + return Ok; + } + else + return NotImplemented; +} + /****************************************************************************** * GdipCreateHatchBrush [GDIPLUS.@] */ @@ -789,7 +806,7 @@ GpStatus WINGDIPAPI GdipCreateTexture(GpImage *image, GpWrapMode wrapmode, GpTexture **texture) { UINT width, height; - GpImageAttributes attributes; + GpImageAttributes *attributes; GpStatus stat; TRACE("%p, %d %p\n", image, wrapmode, texture); @@ -801,10 +818,20 @@ GpStatus WINGDIPAPI GdipCreateTexture(GpImage *image, GpWrapMode wrapmode, if (stat != Ok) return stat; stat = GdipGetImageHeight(image, &height); if (stat != Ok) return stat; - attributes.wrap = wrapmode; - return GdipCreateTextureIA(image, &attributes, 0, 0, width, height, + stat = GdipCreateImageAttributes(&attributes); + + if (stat == Ok) + { + attributes->wrap = wrapmode; + + stat = GdipCreateTextureIA(image, attributes, 0, 0, width, height, texture); + + GdipDisposeImageAttributes(attributes); + } + + return stat; } /****************************************************************************** @@ -813,14 +840,25 @@ GpStatus WINGDIPAPI GdipCreateTexture(GpImage *image, GpWrapMode wrapmode, GpStatus WINGDIPAPI GdipCreateTexture2(GpImage *image, GpWrapMode wrapmode, REAL x, REAL y, REAL width, REAL height, GpTexture **texture) { - GpImageAttributes attributes; + GpImageAttributes *attributes; + GpStatus stat; TRACE("%p %d %f %f %f %f %p\n", image, wrapmode, x, y, width, height, texture); - attributes.wrap = wrapmode; - return GdipCreateTextureIA(image, &attributes, x, y, width, height, - texture); + stat = GdipCreateImageAttributes(&attributes); + + if (stat == Ok) + { + attributes->wrap = wrapmode; + + stat = GdipCreateTextureIA(image, attributes, x, y, width, height, + texture); + + GdipDisposeImageAttributes(attributes); + } + + return stat; } /****************************************************************************** @@ -870,16 +908,25 @@ GpStatus WINGDIPAPI GdipCreateTextureIA(GpImage *image, goto exit; } + if (imageattr) + { + status = GdipCloneImageAttributes(imageattr, &(*texture)->imageattributes); + } + else + { + status = GdipCreateImageAttributes(&(*texture)->imageattributes); + if (status == Ok) + (*texture)->imageattributes->wrap = WrapModeTile; + } + if (status != Ok) + goto exit; + (*texture)->brush.lb.lbStyle = BS_PATTERN; (*texture)->brush.lb.lbColor = 0; (*texture)->brush.lb.lbHatch = (ULONG_PTR)hbm; (*texture)->brush.gdibrush = CreateBrushIndirect(&(*texture)->brush.lb); (*texture)->brush.bt = BrushTypeTextureFill; - if (imageattr) - (*texture)->wrap = imageattr->wrap; - else - (*texture)->wrap = WrapModeTile; (*texture)->image = new_image; exit: @@ -892,6 +939,7 @@ exit: if (*texture) { GdipDeleteMatrix((*texture)->transform); + GdipDisposeImageAttributes((*texture)->imageattributes); GdipFree(*texture); *texture = NULL; } @@ -919,14 +967,22 @@ GpStatus WINGDIPAPI GdipCreateTextureIAI(GpImage *image, GDIPCONST GpImageAttrib GpStatus WINGDIPAPI GdipCreateTexture2I(GpImage *image, GpWrapMode wrapmode, INT x, INT y, INT width, INT height, GpTexture **texture) { - GpImageAttributes imageattr; + GpImageAttributes *imageattr; + GpStatus stat; TRACE("%p %d %d %d %d %d %p\n", image, wrapmode, x, y, width, height, texture); - imageattr.wrap = wrapmode; + stat = GdipCreateImageAttributes(&imageattr); - return GdipCreateTextureIA(image, &imageattr, x, y, width, height, texture); + if (stat == Ok) + { + imageattr->wrap = wrapmode; + + stat = GdipCreateTextureIA(image, imageattr, x, y, width, height, texture); + } + + return stat; } GpStatus WINGDIPAPI GdipGetBrushType(GpBrush *brush, GpBrushType *type) @@ -1000,6 +1056,8 @@ GpStatus WINGDIPAPI GdipDeleteBrush(GpBrush *brush) case BrushTypeTextureFill: GdipDeleteMatrix(((GpTexture*)brush)->transform); GdipDisposeImage(((GpTexture*)brush)->image); + GdipDisposeImageAttributes(((GpTexture*)brush)->imageattributes); + GdipFree(((GpTexture*)brush)->bitmap_bits); break; default: break; @@ -1222,11 +1280,16 @@ GpStatus WINGDIPAPI GdipGetPathGradientSurroundColorsWithCount(GpPathGradient GpStatus WINGDIPAPI GdipGetPathGradientSurroundColorCount(GpPathGradient *brush, INT *count) { + static int calls; + TRACE("(%p, %p)\n", brush, count); if (!brush || !count) return InvalidParameter; + if(!(calls++)) + FIXME("not implemented\n"); + return NotImplemented; } @@ -1293,7 +1356,7 @@ GpStatus WINGDIPAPI GdipGetTextureWrapMode(GpTexture *brush, GpWrapMode *wrapmod if(!brush || !wrapmode) return InvalidParameter; - *wrapmode = brush->wrap; + *wrapmode = brush->imageattributes->wrap; return Ok; } @@ -1773,7 +1836,7 @@ GpStatus WINGDIPAPI GdipSetTextureWrapMode(GpTexture *brush, GpWrapMode wrapmode if(!brush) return InvalidParameter; - brush->wrap = wrapmode; + brush->imageattributes->wrap = wrapmode; return Ok; } diff --git a/reactos/dll/win32/gdiplus/font.c b/reactos/dll/win32/gdiplus/font.c index 843cfb52683..169e28fd3ec 100644 --- a/reactos/dll/win32/gdiplus/font.c +++ b/reactos/dll/win32/gdiplus/font.c @@ -126,27 +126,27 @@ GpStatus WINGDIPAPI GdipCreateFont(GDIPCONST GpFontFamily *fontFamily, { case UnitWorld: /* FIXME: Figure out when World != Pixel */ - lfw->lfHeight = emSize; break; + (*font)->pixel_size = emSize; break; case UnitDisplay: FIXME("Unknown behavior for UnitDisplay! Please report!\n"); /* FIXME: Figure out how this works... * MSDN says that if "DISPLAY" is a monitor, then pixel should be * used. That's not what I got. Tests on Windows revealed no output, * and the tests in tests/font crash windows */ - lfw->lfHeight = 0; break; + (*font)->pixel_size = 0; break; case UnitPixel: - lfw->lfHeight = emSize; break; + (*font)->pixel_size = emSize; break; case UnitPoint: - lfw->lfHeight = point_to_pixel(emSize); break; + (*font)->pixel_size = point_to_pixel(emSize); break; case UnitInch: - lfw->lfHeight = inch_to_pixel(emSize); break; + (*font)->pixel_size = inch_to_pixel(emSize); break; case UnitDocument: - lfw->lfHeight = document_to_pixel(emSize); break; + (*font)->pixel_size = document_to_pixel(emSize); break; case UnitMillimeter: - lfw->lfHeight = mm_to_pixel(emSize); break; + (*font)->pixel_size = mm_to_pixel(emSize); break; } - lfw->lfHeight *= -1; + lfw->lfHeight = (*font)->pixel_size * -1; lfw->lfWeight = style & FontStyleBold ? 700 : 400; lfw->lfItalic = style & FontStyleItalic; @@ -190,7 +190,7 @@ GpStatus WINGDIPAPI GdipCreateFontFromLogfontW(HDC hdc, (*font)->lfw.lfUnderline = logfont->lfUnderline; (*font)->lfw.lfStrikeOut = logfont->lfStrikeOut; - (*font)->emSize = logfont->lfHeight; + (*font)->pixel_size = (*font)->emSize = logfont->lfHeight; (*font)->unit = UnitPixel; hfont = CreateFontIndirectW(&(*font)->lfw); @@ -816,10 +816,20 @@ GpStatus WINGDIPAPI GdipIsStyleAvailable(GDIPCONST GpFontFamily* family, GpStatus WINGDIPAPI GdipGetGenericFontFamilyMonospace(GpFontFamily **nativeFamily) { static const WCHAR CourierNew[] = {'C','o','u','r','i','e','r',' ','N','e','w','\0'}; + static const WCHAR LiberationMono[] = {'L','i','b','e','r','a','t','i','o','n',' ','M','o','n','o','\0'}; + GpStatus stat; if (nativeFamily == NULL) return InvalidParameter; - return GdipCreateFontFamilyFromName(CourierNew, NULL, nativeFamily); + stat = GdipCreateFontFamilyFromName(CourierNew, NULL, nativeFamily); + + if (stat == FontFamilyNotFound) + stat = GdipCreateFontFamilyFromName(LiberationMono, NULL, nativeFamily); + + if (stat == FontFamilyNotFound) + ERR("Missing 'Courier New' font\n"); + + return stat; } /***************************************************************************** @@ -837,12 +847,22 @@ GpStatus WINGDIPAPI GdipGetGenericFontFamilyMonospace(GpFontFamily **nativeFamil GpStatus WINGDIPAPI GdipGetGenericFontFamilySerif(GpFontFamily **nativeFamily) { static const WCHAR TimesNewRoman[] = {'T','i','m','e','s',' ','N','e','w',' ','R','o','m','a','n','\0'}; + static const WCHAR LiberationSerif[] = {'L','i','b','e','r','a','t','i','o','n',' ','S','e','r','i','f','\0'}; + GpStatus stat; TRACE("(%p)\n", nativeFamily); if (nativeFamily == NULL) return InvalidParameter; - return GdipCreateFontFamilyFromName(TimesNewRoman, NULL, nativeFamily); + stat = GdipCreateFontFamilyFromName(TimesNewRoman, NULL, nativeFamily); + + if (stat == FontFamilyNotFound) + stat = GdipCreateFontFamilyFromName(LiberationSerif, NULL, nativeFamily); + + if (stat == FontFamilyNotFound) + ERR("Missing 'Times New Roman' font\n"); + + return stat; } /***************************************************************************** @@ -930,17 +950,158 @@ GpStatus WINGDIPAPI GdipPrivateAddFontFile(GpFontCollection* fontCollection, return NotImplemented; } +/* Copied from msi/font.c */ + +typedef struct _tagTT_OFFSET_TABLE { + USHORT uMajorVersion; + USHORT uMinorVersion; + USHORT uNumOfTables; + USHORT uSearchRange; + USHORT uEntrySelector; + USHORT uRangeShift; +} TT_OFFSET_TABLE; + +typedef struct _tagTT_TABLE_DIRECTORY { + char szTag[4]; /* table name */ + ULONG uCheckSum; /* Check sum */ + ULONG uOffset; /* Offset from beginning of file */ + ULONG uLength; /* length of the table in bytes */ +} TT_TABLE_DIRECTORY; + +typedef struct _tagTT_NAME_TABLE_HEADER { + USHORT uFSelector; /* format selector. Always 0 */ + USHORT uNRCount; /* Name Records count */ + USHORT uStorageOffset; /* Offset for strings storage, + * from start of the table */ +} TT_NAME_TABLE_HEADER; + +#define NAME_ID_FULL_FONT_NAME 4 +#define NAME_ID_VERSION 5 + +typedef struct _tagTT_NAME_RECORD { + USHORT uPlatformID; + USHORT uEncodingID; + USHORT uLanguageID; + USHORT uNameID; + USHORT uStringLength; + USHORT uStringOffset; /* from start of storage area */ +} TT_NAME_RECORD; + +#define SWAPWORD(x) MAKEWORD(HIBYTE(x), LOBYTE(x)) +#define SWAPLONG(x) MAKELONG(SWAPWORD(HIWORD(x)), SWAPWORD(LOWORD(x))) + +/* + * Code based off of code located here + * http://www.codeproject.com/gdi/fontnamefromfile.asp + */ +static WCHAR *load_ttf_name_id( const char *mem, DWORD_PTR size, DWORD id, WCHAR *ret, DWORD len ) +{ + const TT_TABLE_DIRECTORY *tblDir; + TT_OFFSET_TABLE ttOffsetTable; + TT_NAME_TABLE_HEADER ttNTHeader; + TT_NAME_RECORD ttRecord; + DWORD ofs, pos; + int i; + + if (sizeof(TT_OFFSET_TABLE) > size) + return NULL; + ttOffsetTable = *(TT_OFFSET_TABLE*)mem; + ttOffsetTable.uNumOfTables = SWAPWORD(ttOffsetTable.uNumOfTables); + ttOffsetTable.uMajorVersion = SWAPWORD(ttOffsetTable.uMajorVersion); + ttOffsetTable.uMinorVersion = SWAPWORD(ttOffsetTable.uMinorVersion); + + if (ttOffsetTable.uMajorVersion != 1 || ttOffsetTable.uMinorVersion != 0) + return NULL; + + pos = sizeof(ttOffsetTable); + for (i = 0; i < ttOffsetTable.uNumOfTables; i++) + { + tblDir = (const TT_TABLE_DIRECTORY*)&mem[pos]; + pos += sizeof(*tblDir); + if (memcmp(tblDir->szTag,"name",4)==0) + { + ofs = SWAPLONG(tblDir->uOffset); + break; + } + } + if (i >= ttOffsetTable.uNumOfTables) + return NULL; + + pos = ofs + sizeof(ttNTHeader); + if (pos > size) + return NULL; + ttNTHeader = *(TT_NAME_TABLE_HEADER*)&mem[ofs]; + ttNTHeader.uNRCount = SWAPWORD(ttNTHeader.uNRCount); + ttNTHeader.uStorageOffset = SWAPWORD(ttNTHeader.uStorageOffset); + for(i=0; i size) + return NULL; + + ttRecord.uNameID = SWAPWORD(ttRecord.uNameID); + if (ttRecord.uNameID == id) + { + const char *buf; + + ttRecord.uStringLength = SWAPWORD(ttRecord.uStringLength); + ttRecord.uStringOffset = SWAPWORD(ttRecord.uStringOffset); + if (ofs + ttRecord.uStringOffset + ttNTHeader.uStorageOffset + ttRecord.uStringLength > size) + return NULL; + buf = mem + ofs + ttRecord.uStringOffset + ttNTHeader.uStorageOffset; + len = MultiByteToWideChar(CP_ACP, 0, buf, ttRecord.uStringLength, ret, len-1); + ret[len] = 0; + return ret; + } + } + return NULL; +} + +static INT CALLBACK add_font_proc(const LOGFONTW *lfw, const TEXTMETRICW *ntm, DWORD type, LPARAM lParam); + /***************************************************************************** * GdipPrivateAddMemoryFont [GDIPLUS.@] */ GpStatus WINGDIPAPI GdipPrivateAddMemoryFont(GpFontCollection* fontCollection, GDIPCONST void* memory, INT length) { - FIXME("%p, %p, %d\n", fontCollection, memory, length); + WCHAR buf[32], *name; + DWORD count = 0; + HANDLE font; + TRACE("%p, %p, %d\n", fontCollection, memory, length); - if (!(fontCollection && memory && length)) + if (!fontCollection || !memory || !length) return InvalidParameter; + name = load_ttf_name_id(memory, length, NAME_ID_FULL_FONT_NAME, buf, sizeof(buf)/sizeof(*buf)); + if (!name) + return OutOfMemory; + + font = AddFontMemResourceEx((void*)memory, length, NULL, &count); + TRACE("%s: %p/%u\n", debugstr_w(name), font, count); + if (!font || !count) + return InvalidParameter; + + if (count) + { + HDC hdc; + LOGFONTW lfw; + + hdc = GetDC(0); + + lfw.lfCharSet = DEFAULT_CHARSET; + lstrcpyW(lfw.lfFaceName, name); + lfw.lfPitchAndFamily = 0; + + if (!EnumFontFamiliesExW(hdc, &lfw, add_font_proc, (LPARAM)fontCollection, 0)) + { + ReleaseDC(0, hdc); + return OutOfMemory; + } + + ReleaseDC(0, hdc); + } return Ok; } diff --git a/reactos/dll/win32/gdiplus/gdiplus.c b/reactos/dll/win32/gdiplus/gdiplus.c index fb159be55b2..9c3478bc134 100644 --- a/reactos/dll/win32/gdiplus/gdiplus.c +++ b/reactos/dll/win32/gdiplus/gdiplus.c @@ -116,16 +116,17 @@ void WINAPI GdiplusNotificationUnhook(ULONG_PTR token) /***************************************************** * GdiplusShutdown [GDIPLUS.@] */ -void WINAPI GdiplusShutdown(ULONG_PTR token) -{ - /* FIXME: no object tracking */ -} - -/* "bricksntiles" expects a return value of 0, which native coincidentally gives */ ULONG WINAPI GdiplusShutdown_wrapper(ULONG_PTR token) { - GdiplusShutdown(token); + /* Notice the slightly different prototype from the official + * signature which forces us to use the _wrapper suffix. + */ + /* FIXME: no object tracking */ + + /* "bricksntiles" expects a return value of 0, which native + * coincidentally gives. + */ return 0; } @@ -406,7 +407,7 @@ BOOL lengthen_path(GpPath *path, INT len) void convert_32bppARGB_to_32bppPARGB(UINT width, UINT height, BYTE *dst_bits, INT dst_stride, const BYTE *src_bits, INT src_stride) { - UINT x, y; + INT x, y; for (y=0; y + + + + diff --git a/reactos/dll/win32/gdiplus/gdiplus.rc b/reactos/dll/win32/gdiplus/gdiplus.rc new file mode 100644 index 00000000000..56f6c229990 --- /dev/null +++ b/reactos/dll/win32/gdiplus/gdiplus.rc @@ -0,0 +1,22 @@ +/* + * Resource file for gdiplus + * + * Copyright 2011 Alexandre Julliard + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +/* @makedep: gdiplus.manifest */ +WINE_MANIFEST 24 gdiplus.manifest diff --git a/reactos/dll/win32/gdiplus/gdiplus.spec b/reactos/dll/win32/gdiplus/gdiplus.spec index 4cf15ab4d5e..93986584824 100644 --- a/reactos/dll/win32/gdiplus/gdiplus.spec +++ b/reactos/dll/win32/gdiplus/gdiplus.spec @@ -1,630 +1,630 @@ -@ stdcall GdipAddPathArc(ptr long long long long long long) -@ stdcall GdipAddPathArcI(ptr long long long long long long) -@ stdcall GdipAddPathBezier(ptr long long long long long long long long) -@ stdcall GdipAddPathBezierI(ptr long long long long long long long long) -@ stdcall GdipAddPathBeziers(ptr ptr long) -@ stdcall GdipAddPathBeziersI(ptr ptr long) -@ stdcall GdipAddPathClosedCurve2(ptr ptr long long) -@ stdcall GdipAddPathClosedCurve2I(ptr ptr long long) -@ stdcall GdipAddPathClosedCurve(ptr ptr long) -@ stdcall GdipAddPathClosedCurveI(ptr ptr long) -@ stdcall GdipAddPathCurve2(ptr ptr long long) -@ stdcall GdipAddPathCurve2I(ptr ptr long long) -@ stdcall GdipAddPathCurve3(ptr ptr long long long long) -@ stdcall GdipAddPathCurve3I(ptr ptr long long long long) -@ stdcall GdipAddPathCurve(ptr ptr long) -@ stdcall GdipAddPathCurveI(ptr ptr long) -@ stdcall GdipAddPathEllipse(ptr long long long long) -@ stdcall GdipAddPathEllipseI(ptr long long long long) -@ stdcall GdipAddPathLine2(ptr ptr long) -@ stdcall GdipAddPathLine2I(ptr ptr long) -@ stdcall GdipAddPathLine(ptr long long long long) -@ stdcall GdipAddPathLineI(ptr long long long long) -@ stdcall GdipAddPathPath(ptr ptr long) -@ stdcall GdipAddPathPie(ptr long long long long long long) -@ stdcall GdipAddPathPieI(ptr long long long long long long) -@ stdcall GdipAddPathPolygon(ptr ptr long) -@ stdcall GdipAddPathPolygonI(ptr ptr long) -@ stdcall GdipAddPathRectangle(ptr long long long long) -@ stdcall GdipAddPathRectangleI(ptr long long long long) -@ stdcall GdipAddPathRectangles(ptr ptr long) -@ stdcall GdipAddPathRectanglesI(ptr ptr long) -@ stdcall GdipAddPathString(ptr wstr long ptr long long ptr ptr) -@ stdcall GdipAddPathStringI(ptr wstr long ptr long long ptr ptr) -@ stdcall GdipAlloc(long) -@ stdcall GdipBeginContainer2(ptr ptr) -@ stdcall GdipBeginContainer(ptr ptr ptr long ptr) -@ stdcall GdipBeginContainerI(ptr ptr ptr long ptr) -@ stdcall GdipBitmapApplyEffect(ptr ptr ptr long ptr ptr) -@ stub GdipBitmapConvertFormat -@ stdcall GdipBitmapCreateApplyEffect(ptr long ptr ptr ptr ptr long ptr ptr) -@ stub GdipBitmapGetHistogram -@ stub GdipBitmapGetHistogramSize -@ stdcall GdipBitmapGetPixel(ptr long long ptr) -@ stdcall GdipBitmapLockBits(ptr ptr long long ptr) -@ stdcall GdipBitmapSetPixel(ptr long long long) -@ stdcall GdipBitmapSetResolution(ptr long long) -@ stdcall GdipBitmapUnlockBits(ptr ptr) -@ stdcall GdipClearPathMarkers(ptr) -@ stdcall GdipCloneBitmapArea(long long long long long ptr ptr) -@ stdcall GdipCloneBitmapAreaI(long long long long long ptr ptr) -@ stdcall GdipCloneBrush(ptr ptr) -@ stdcall GdipCloneCustomLineCap(ptr ptr) -@ stdcall GdipCloneFont(ptr ptr) -@ stdcall GdipCloneFontFamily(ptr ptr) -@ stdcall GdipCloneImage(ptr ptr) -@ stdcall GdipCloneImageAttributes(ptr ptr) -@ stdcall GdipCloneMatrix(ptr ptr) -@ stdcall GdipClonePath(ptr ptr) -@ stdcall GdipClonePen(ptr ptr) -@ stdcall GdipCloneRegion(ptr ptr) -@ stdcall GdipCloneStringFormat(ptr ptr) -@ stdcall GdipClosePathFigure(ptr) -@ stdcall GdipClosePathFigures(ptr) -@ stdcall GdipCombineRegionPath(ptr ptr long) -@ stdcall GdipCombineRegionRect(ptr ptr long) -@ stdcall GdipCombineRegionRectI(ptr ptr long) -@ stdcall GdipCombineRegionRegion(ptr ptr long) -@ stdcall GdipComment(ptr long ptr) -@ stdcall GdipConvertToEmfPlus(ptr ptr ptr long ptr ptr) -@ stdcall GdipConvertToEmfPlusToFile(ptr ptr ptr ptr long ptr ptr) -@ stub GdipConvertToEmfPlusToStream -@ stdcall GdipCreateAdjustableArrowCap(long long long ptr) -@ stub GdipCreateBitmapFromDirectDrawSurface -@ stdcall GdipCreateBitmapFromFile(wstr ptr) -@ stdcall GdipCreateBitmapFromFileICM(wstr ptr) -@ stdcall GdipCreateBitmapFromGdiDib(ptr ptr ptr) -@ stdcall GdipCreateBitmapFromGraphics(long long ptr ptr) -@ stdcall GdipCreateBitmapFromHBITMAP(long long ptr) -@ stdcall GdipCreateBitmapFromHICON(long ptr) -@ stdcall GdipCreateBitmapFromResource(long wstr ptr) -@ stdcall GdipCreateBitmapFromScan0(long long long long ptr ptr) -@ stdcall GdipCreateBitmapFromStream(ptr ptr) -@ stdcall GdipCreateBitmapFromStreamICM(ptr ptr) -@ stdcall GdipCreateCachedBitmap(ptr ptr ptr) -@ stdcall GdipCreateCustomLineCap(ptr ptr long long ptr) -@ stub GdipCreateEffect -@ stdcall GdipCreateFont(ptr long long long ptr) -@ stdcall GdipCreateFontFamilyFromName(wstr ptr ptr) -@ stdcall GdipCreateFontFromDC(long ptr) -@ stdcall GdipCreateFontFromLogfontA(long ptr ptr) -@ stdcall GdipCreateFontFromLogfontW(long ptr ptr) -@ stdcall GdipCreateFromHDC2(long long ptr) -@ stdcall GdipCreateFromHDC(long ptr) -@ stdcall GdipCreateFromHWND(long ptr) -@ stdcall GdipCreateFromHWNDICM(long ptr) -@ stdcall GdipCreateHBITMAPFromBitmap(ptr ptr long) -@ stdcall GdipCreateHICONFromBitmap(ptr ptr) -@ stdcall GdipCreateHalftonePalette() -@ stdcall GdipCreateHatchBrush(long long long ptr) -@ stdcall GdipCreateImageAttributes(ptr) -@ stdcall GdipCreateLineBrush(ptr ptr long long long ptr) -@ stdcall GdipCreateLineBrushFromRect(ptr long long long long ptr) -@ stdcall GdipCreateLineBrushFromRectI(ptr long long long long ptr) -@ stdcall GdipCreateLineBrushFromRectWithAngle(ptr long long long long long ptr) -@ stdcall GdipCreateLineBrushFromRectWithAngleI(ptr long long long long long ptr) -@ stdcall GdipCreateLineBrushI(ptr ptr long long long ptr) -@ stdcall GdipCreateMatrix2(long long long long long long ptr) -@ stdcall GdipCreateMatrix3(ptr ptr ptr) -@ stdcall GdipCreateMatrix3I(ptr ptr ptr) -@ stdcall GdipCreateMatrix(ptr) -@ stdcall GdipCreateMetafileFromEmf(ptr long ptr) -@ stdcall GdipCreateMetafileFromFile(ptr ptr) -@ stdcall GdipCreateMetafileFromStream(ptr ptr) -@ stdcall GdipCreateMetafileFromWmf(ptr long ptr ptr) -@ stdcall GdipCreateMetafileFromWmfFile(wstr ptr ptr) -@ stdcall GdipCreatePath2(ptr ptr long long ptr) -@ stdcall GdipCreatePath2I(ptr ptr long long ptr) -@ stdcall GdipCreatePath(long ptr) -@ stdcall GdipCreatePathGradient(ptr long long ptr) -@ stdcall GdipCreatePathGradientFromPath(ptr ptr) -@ stdcall GdipCreatePathGradientI(ptr long long ptr) -@ stdcall GdipCreatePathIter(ptr ptr) -@ stdcall GdipCreatePen1(long long long ptr) -@ stdcall GdipCreatePen2(ptr long long ptr) -@ stdcall GdipCreateRegion(ptr) -@ stdcall GdipCreateRegionHrgn(ptr ptr) -@ stdcall GdipCreateRegionPath(ptr ptr) -@ stdcall GdipCreateRegionRect(ptr ptr) -@ stdcall GdipCreateRegionRectI(ptr ptr) -@ stdcall GdipCreateRegionRgnData(ptr long ptr) -@ stdcall GdipCreateSolidFill(long ptr) -@ stdcall GdipCreateStreamOnFile(ptr long ptr) -@ stdcall GdipCreateStringFormat(long long ptr) -@ stdcall GdipCreateTexture2(ptr long long long long long ptr) -@ stdcall GdipCreateTexture2I(ptr long long long long long ptr) -@ stdcall GdipCreateTexture(ptr long ptr) -@ stdcall GdipCreateTextureIA(ptr ptr long long long long ptr) -@ stdcall GdipCreateTextureIAI(ptr ptr long long long long ptr) -@ stdcall GdipDeleteBrush(ptr) -@ stdcall GdipDeleteCachedBitmap(ptr) -@ stdcall GdipDeleteCustomLineCap(ptr) -@ stdcall GdipDeleteEffect(ptr) -@ stdcall GdipDeleteFont(ptr) -@ stdcall GdipDeleteFontFamily(ptr) -@ stdcall GdipDeleteGraphics(ptr) -@ stdcall GdipDeleteMatrix(ptr) -@ stdcall GdipDeletePath(ptr) -@ stdcall GdipDeletePathIter(ptr) -@ stdcall GdipDeletePen(ptr) -@ stdcall GdipDeletePrivateFontCollection(ptr) -@ stdcall GdipDeleteRegion(ptr) -@ stdcall GdipDeleteStringFormat(ptr) -@ stdcall GdipDisposeImage(ptr) -@ stdcall GdipDisposeImageAttributes(ptr) -@ stdcall GdipDrawArc(ptr ptr long long long long long long) -@ stdcall GdipDrawArcI(ptr ptr long long long long long long) -@ stdcall GdipDrawBezier(ptr ptr long long long long long long long long) -@ stdcall GdipDrawBezierI(ptr ptr long long long long long long long long) -@ stdcall GdipDrawBeziers(ptr ptr ptr long) -@ stdcall GdipDrawBeziersI(ptr ptr ptr long) -@ stdcall GdipDrawCachedBitmap(ptr ptr long long) -@ stdcall GdipDrawClosedCurve2(ptr ptr ptr long long) -@ stdcall GdipDrawClosedCurve2I(ptr ptr ptr long long) -@ stdcall GdipDrawClosedCurve(ptr ptr ptr long) -@ stdcall GdipDrawClosedCurveI(ptr ptr ptr long) -@ stdcall GdipDrawCurve2(ptr ptr ptr long long) -@ stdcall GdipDrawCurve2I(ptr ptr ptr long long) -@ stdcall GdipDrawCurve3(ptr ptr ptr long long long long) -@ stdcall GdipDrawCurve3I(ptr ptr ptr long long long long) -@ stdcall GdipDrawCurve(ptr ptr ptr long) -@ stdcall GdipDrawCurveI(ptr ptr ptr long) -@ stdcall GdipDrawDriverString(ptr ptr long ptr ptr ptr long ptr) -@ stdcall GdipDrawEllipse(ptr ptr long long long long) -@ stdcall GdipDrawEllipseI(ptr ptr long long long long) -@ stdcall GdipDrawImage(ptr ptr long long) -@ stub GdipDrawImageFX -@ stdcall GdipDrawImageI(ptr ptr long long) -@ stdcall GdipDrawImagePointRect(ptr ptr long long long long long long long) -@ stdcall GdipDrawImagePointRectI(ptr ptr long long long long long long long) -@ stdcall GdipDrawImagePoints(ptr ptr ptr long) -@ stdcall GdipDrawImagePointsI(ptr ptr ptr long) -@ stdcall GdipDrawImagePointsRect(ptr ptr ptr long long long long long long ptr ptr ptr) -@ stdcall GdipDrawImagePointsRectI(ptr ptr ptr long long long long long long ptr ptr ptr) -@ stdcall GdipDrawImageRect(ptr ptr long long long long) -@ stdcall GdipDrawImageRectI(ptr ptr long long long long) -@ stdcall GdipDrawImageRectRect(ptr ptr long long long long long long long long long ptr long ptr) -@ stdcall GdipDrawImageRectRectI(ptr ptr long long long long long long long long long ptr long ptr) -@ stdcall GdipDrawLine(ptr ptr long long long long) -@ stdcall GdipDrawLineI(ptr ptr long long long long) -@ stdcall GdipDrawLines(ptr ptr ptr long) -@ stdcall GdipDrawLinesI(ptr ptr ptr long) -@ stdcall GdipDrawPath(ptr ptr ptr) -@ stdcall GdipDrawPie(ptr ptr long long long long long long) -@ stdcall GdipDrawPieI(ptr ptr long long long long long long) -@ stdcall GdipDrawPolygon(ptr ptr ptr long) -@ stdcall GdipDrawPolygonI(ptr ptr ptr long) -@ stdcall GdipDrawRectangle(ptr ptr long long long long) -@ stdcall GdipDrawRectangleI(ptr ptr long long long long) -@ stdcall GdipDrawRectangles(ptr ptr ptr long) -@ stdcall GdipDrawRectanglesI(ptr ptr ptr long) -@ stdcall GdipDrawString(ptr ptr long ptr ptr ptr ptr) -@ stdcall GdipEmfToWmfBits(ptr long ptr long long) -@ stdcall GdipEndContainer(ptr ptr) -@ stub GdipEnumerateMetafileDestPoint -@ stub GdipEnumerateMetafileDestPointI -@ stub GdipEnumerateMetafileDestPoints -@ stub GdipEnumerateMetafileDestPointsI -@ stub GdipEnumerateMetafileDestRect -@ stub GdipEnumerateMetafileDestRectI -@ stub GdipEnumerateMetafileSrcRectDestPoint -@ stub GdipEnumerateMetafileSrcRectDestPointI -@ stub GdipEnumerateMetafileSrcRectDestPoints -@ stub GdipEnumerateMetafileSrcRectDestPointsI -@ stub GdipEnumerateMetafileSrcRectDestRect -@ stub GdipEnumerateMetafileSrcRectDestRectI -@ stdcall GdipFillClosedCurve2(ptr ptr ptr long long long) -@ stdcall GdipFillClosedCurve2I(ptr ptr ptr long long long) -@ stdcall GdipFillClosedCurve(ptr ptr ptr long) -@ stdcall GdipFillClosedCurveI(ptr ptr ptr long) -@ stdcall GdipFillEllipse(ptr ptr long long long long) -@ stdcall GdipFillEllipseI(ptr ptr long long long long) -@ stdcall GdipFillPath(ptr ptr ptr) -@ stdcall GdipFillPie(ptr ptr long long long long long long) -@ stdcall GdipFillPieI(ptr ptr long long long long long long) -@ stdcall GdipFillPolygon2(ptr ptr ptr long) -@ stdcall GdipFillPolygon2I(ptr ptr ptr long) -@ stdcall GdipFillPolygon(ptr ptr ptr long long) -@ stdcall GdipFillPolygonI(ptr ptr ptr long long) -@ stdcall GdipFillRectangle(ptr ptr long long long long) -@ stdcall GdipFillRectangleI(ptr ptr long long long long) -@ stdcall GdipFillRectangles(ptr ptr ptr long) -@ stdcall GdipFillRectanglesI(ptr ptr ptr long) -@ stdcall GdipFillRegion(ptr ptr ptr) -@ stdcall GdipFindFirstImageItem(ptr ptr) -@ stub GdipFindNextImageItem -@ stdcall GdipFlattenPath(ptr ptr long) -@ stdcall GdipFlush(ptr long) -@ stdcall GdipFree(ptr) -@ stdcall GdipGetAdjustableArrowCapFillState(ptr ptr) -@ stdcall GdipGetAdjustableArrowCapHeight(ptr ptr) -@ stdcall GdipGetAdjustableArrowCapMiddleInset(ptr ptr) -@ stdcall GdipGetAdjustableArrowCapWidth(ptr ptr) -@ stdcall GdipGetAllPropertyItems(ptr long long ptr) -@ stdcall GdipGetBrushType(ptr ptr) -@ stdcall GdipGetCellAscent(ptr long ptr) -@ stdcall GdipGetCellDescent(ptr long ptr) -@ stdcall GdipGetClip(ptr ptr) -@ stdcall GdipGetClipBounds(ptr ptr) -@ stdcall GdipGetClipBoundsI(ptr ptr) -@ stdcall GdipGetCompositingMode(ptr ptr) -@ stdcall GdipGetCompositingQuality(ptr ptr) -@ stdcall GdipGetCustomLineCapBaseCap(ptr ptr) -@ stdcall GdipGetCustomLineCapBaseInset(ptr ptr) -@ stub GdipGetCustomLineCapStrokeCaps -@ stdcall GdipGetCustomLineCapStrokeJoin(ptr ptr) -@ stub GdipGetCustomLineCapType -@ stdcall GdipGetCustomLineCapWidthScale(ptr ptr) -@ stdcall GdipGetDC(ptr ptr) -@ stdcall GdipGetDpiX(ptr ptr) -@ stdcall GdipGetDpiY(ptr ptr) -@ stub GdipGetEffectParameterSize -@ stub GdipGetEffectParameters -@ stdcall GdipGetEmHeight(ptr long ptr) -@ stub GdipGetEncoderParameterList -@ stdcall GdipGetEncoderParameterListSize(ptr ptr ptr) -@ stdcall GdipGetFamily(ptr ptr) -@ stdcall GdipGetFamilyName(ptr ptr long) -@ stdcall GdipGetFontCollectionFamilyCount(ptr ptr) -@ stdcall GdipGetFontCollectionFamilyList(ptr long ptr ptr) -@ stdcall GdipGetFontHeight(ptr ptr ptr) -@ stdcall GdipGetFontHeightGivenDPI(ptr long ptr) -@ stdcall GdipGetFontSize(ptr ptr) -@ stdcall GdipGetFontStyle(ptr ptr) -@ stdcall GdipGetFontUnit(ptr ptr) -@ stdcall GdipGetGenericFontFamilyMonospace(ptr) -@ stdcall GdipGetGenericFontFamilySansSerif(ptr) -@ stdcall GdipGetGenericFontFamilySerif(ptr) -@ stdcall GdipGetHatchBackgroundColor(ptr ptr) -@ stdcall GdipGetHatchForegroundColor(ptr ptr) -@ stdcall GdipGetHatchStyle(ptr ptr) -@ stub GdipGetHemfFromMetafile -@ stub GdipGetImageAttributesAdjustedPalette -@ stdcall GdipGetImageBounds(ptr ptr ptr) -@ stdcall GdipGetImageDecoders(long long ptr) -@ stdcall GdipGetImageDecodersSize(ptr ptr) -@ stdcall GdipGetImageDimension(ptr ptr ptr) -@ stdcall GdipGetImageEncoders(long long ptr) -@ stdcall GdipGetImageEncodersSize(ptr ptr) -@ stdcall GdipGetImageFlags(ptr ptr) -@ stdcall GdipGetImageGraphicsContext(ptr ptr) -@ stdcall GdipGetImageHeight(ptr ptr) -@ stdcall GdipGetImageHorizontalResolution(ptr ptr) -@ stdcall GdipGetImageItemData(ptr ptr) -@ stdcall GdipGetImagePalette(ptr ptr long) -@ stdcall GdipGetImagePaletteSize(ptr ptr) -@ stdcall GdipGetImagePixelFormat(ptr ptr) -@ stdcall GdipGetImageRawFormat(ptr ptr) -@ stdcall GdipGetImageThumbnail(ptr long long ptr ptr ptr) -@ stdcall GdipGetImageType(ptr ptr) -@ stdcall GdipGetImageVerticalResolution(ptr ptr) -@ stdcall GdipGetImageWidth(ptr ptr) -@ stdcall GdipGetInterpolationMode(ptr ptr) -@ stdcall GdipGetLineBlend(ptr ptr ptr long) -@ stdcall GdipGetLineBlendCount(ptr ptr) -@ stdcall GdipGetLineColors(ptr ptr) -@ stdcall GdipGetLineGammaCorrection(ptr ptr) -@ stdcall GdipGetLinePresetBlend(ptr ptr ptr long) -@ stdcall GdipGetLinePresetBlendCount(ptr ptr) -@ stdcall GdipGetLineRect(ptr ptr) -@ stdcall GdipGetLineRectI(ptr ptr) -@ stdcall GdipGetLineSpacing(ptr long ptr) -@ stdcall GdipGetLineTransform(ptr ptr) -@ stdcall GdipGetLineWrapMode(ptr ptr) -@ stdcall GdipGetLogFontA(ptr ptr ptr) -@ stdcall GdipGetLogFontW(ptr ptr ptr) -@ stdcall GdipGetMatrixElements(ptr ptr) -@ stub GdipGetMetafileDownLevelRasterizationLimit -@ stdcall GdipGetMetafileHeaderFromEmf(ptr ptr) -@ stdcall GdipGetMetafileHeaderFromFile(wstr ptr) -@ stdcall GdipGetMetafileHeaderFromMetafile(ptr ptr) -@ stdcall GdipGetMetafileHeaderFromStream(ptr ptr) -@ stub GdipGetMetafileHeaderFromWmf -@ stdcall GdipGetNearestColor(ptr ptr) -@ stdcall GdipGetPageScale(ptr ptr) -@ stdcall GdipGetPageUnit(ptr ptr) -@ stdcall GdipGetPathData(ptr ptr) -@ stdcall GdipGetPathFillMode(ptr ptr) -@ stdcall GdipGetPathGradientBlend(ptr ptr ptr long) -@ stdcall GdipGetPathGradientBlendCount(ptr ptr) -@ stdcall GdipGetPathGradientCenterColor(ptr ptr) -@ stdcall GdipGetPathGradientCenterPoint(ptr ptr) -@ stdcall GdipGetPathGradientCenterPointI(ptr ptr) -@ stdcall GdipGetPathGradientFocusScales(ptr ptr ptr) -@ stdcall GdipGetPathGradientGammaCorrection(ptr ptr) -@ stub GdipGetPathGradientPath -@ stdcall GdipGetPathGradientPointCount(ptr ptr) -@ stdcall GdipGetPathGradientPresetBlend(ptr ptr ptr long) -@ stdcall GdipGetPathGradientPresetBlendCount(ptr ptr) -@ stdcall GdipGetPathGradientRect(ptr ptr) -@ stdcall GdipGetPathGradientRectI(ptr ptr) -@ stdcall GdipGetPathGradientSurroundColorCount(ptr ptr) -@ stdcall GdipGetPathGradientSurroundColorsWithCount(ptr ptr ptr) -@ stdcall GdipGetPathGradientTransform(ptr ptr) -@ stdcall GdipGetPathGradientWrapMode(ptr ptr) -@ stdcall GdipGetPathLastPoint(ptr ptr) -@ stdcall GdipGetPathPoints(ptr ptr long) -@ stdcall GdipGetPathPointsI(ptr ptr long) -@ stdcall GdipGetPathTypes(ptr ptr long) -@ stdcall GdipGetPathWorldBounds(ptr ptr ptr ptr) -@ stdcall GdipGetPathWorldBoundsI(ptr ptr ptr ptr) -@ stdcall GdipGetPenBrushFill(ptr ptr) -@ stdcall GdipGetPenColor(ptr ptr) -@ stub GdipGetPenCompoundArray -@ stdcall GdipGetPenCompoundCount(ptr ptr) -@ stdcall GdipGetPenCustomEndCap(ptr ptr) -@ stdcall GdipGetPenCustomStartCap(ptr ptr) -@ stdcall GdipGetPenDashArray(ptr ptr long) -@ stdcall GdipGetPenDashCap197819(ptr ptr) -@ stdcall GdipGetPenDashCount(ptr ptr) -@ stdcall GdipGetPenDashOffset(ptr ptr) -@ stdcall GdipGetPenDashStyle(ptr ptr) -@ stdcall GdipGetPenEndCap(ptr ptr) -@ stdcall GdipGetPenFillType(ptr ptr) -@ stdcall GdipGetPenLineJoin(ptr ptr) -@ stdcall GdipGetPenMiterLimit(ptr ptr) -@ stdcall GdipGetPenMode(ptr ptr) -@ stdcall GdipGetPenStartCap(ptr ptr) -@ stdcall GdipGetPenTransform(ptr ptr) -@ stdcall GdipGetPenUnit(ptr ptr) -@ stdcall GdipGetPenWidth(ptr ptr) -@ stdcall GdipGetPixelOffsetMode(ptr ptr) -@ stdcall GdipGetPointCount(ptr ptr) -@ stdcall GdipGetPropertyCount(ptr ptr) -@ stdcall GdipGetPropertyIdList(ptr long ptr) -@ stdcall GdipGetPropertyItem(ptr long long ptr) -@ stdcall GdipGetPropertyItemSize(ptr long ptr) -@ stdcall GdipGetPropertySize(ptr ptr ptr) -@ stdcall GdipGetRegionBounds(ptr ptr ptr) -@ stdcall GdipGetRegionBoundsI(ptr ptr ptr) -@ stdcall GdipGetRegionData(ptr ptr long ptr) -@ stdcall GdipGetRegionDataSize(ptr ptr) -@ stdcall GdipGetRegionHRgn(ptr ptr ptr) -@ stdcall GdipGetRegionScans(ptr ptr ptr ptr) -@ stdcall GdipGetRegionScansCount(ptr ptr ptr) -@ stdcall GdipGetRegionScansI(ptr ptr ptr ptr) -@ stdcall GdipGetRenderingOrigin(ptr ptr ptr) -@ stdcall GdipGetSmoothingMode(ptr ptr) -@ stdcall GdipGetSolidFillColor(ptr ptr) -@ stdcall GdipGetStringFormatAlign(ptr ptr) -@ stdcall GdipGetStringFormatDigitSubstitution(ptr ptr ptr) -@ stdcall GdipGetStringFormatFlags(ptr ptr) -@ stdcall GdipGetStringFormatHotkeyPrefix(ptr ptr) -@ stdcall GdipGetStringFormatLineAlign(ptr ptr) -@ stdcall GdipGetStringFormatMeasurableCharacterRangeCount(ptr ptr) -@ stdcall GdipGetStringFormatTabStopCount(ptr ptr) -@ stdcall GdipGetStringFormatTabStops(ptr long ptr ptr) -@ stdcall GdipGetStringFormatTrimming(ptr ptr) -@ stdcall GdipGetTextContrast(ptr ptr) -@ stdcall GdipGetTextRenderingHint(ptr ptr) -@ stdcall GdipGetTextureImage(ptr ptr) -@ stdcall GdipGetTextureTransform(ptr ptr) -@ stdcall GdipGetTextureWrapMode(ptr ptr) -@ stdcall GdipGetVisibleClipBounds(ptr ptr) -@ stdcall GdipGetVisibleClipBoundsI(ptr ptr) -@ stdcall GdipGetWorldTransform(ptr ptr) -@ stdcall GdipGraphicsClear(ptr long) -@ stub GdipGraphicsSetAbort -@ stdcall GdipImageForceValidation(ptr) -@ stdcall GdipImageGetFrameCount(ptr ptr ptr) -@ stdcall GdipImageGetFrameDimensionsCount(ptr ptr) -@ stdcall GdipImageGetFrameDimensionsList(ptr ptr long) -@ stdcall GdipImageRotateFlip(ptr long) -@ stdcall GdipImageSelectActiveFrame(ptr ptr long) -@ stub GdipImageSetAbort -@ stub GdipInitializePalette -@ stdcall GdipInvertMatrix(ptr) -@ stdcall GdipIsClipEmpty(ptr ptr) -@ stdcall GdipIsEmptyRegion(ptr ptr ptr) -@ stdcall GdipIsEqualRegion(ptr ptr ptr ptr) -@ stdcall GdipIsInfiniteRegion(ptr ptr ptr) -@ stdcall GdipIsMatrixEqual(ptr ptr ptr) -@ stdcall GdipIsMatrixIdentity(ptr ptr) -@ stdcall GdipIsMatrixInvertible(ptr ptr) -@ stdcall GdipIsOutlineVisiblePathPoint(ptr long long ptr ptr ptr) -@ stdcall GdipIsOutlineVisiblePathPointI(ptr long long ptr ptr ptr) -@ stdcall GdipIsStyleAvailable(ptr long ptr) -@ stdcall GdipIsVisibleClipEmpty(ptr ptr) -@ stdcall GdipIsVisiblePathPoint(ptr long long ptr ptr) -@ stdcall GdipIsVisiblePathPointI(ptr long long ptr ptr) -@ stdcall GdipIsVisiblePoint(ptr long long ptr) -@ stdcall GdipIsVisiblePointI(ptr long long ptr) -@ stdcall GdipIsVisibleRect(ptr long long long long ptr) -@ stdcall GdipIsVisibleRectI(ptr long long long long ptr) -@ stdcall GdipIsVisibleRegionPoint(ptr long long ptr ptr) -@ stdcall GdipIsVisibleRegionPointI(ptr long long ptr ptr) -@ stdcall GdipIsVisibleRegionRect(ptr long long long long ptr ptr) -@ stdcall GdipIsVisibleRegionRectI(ptr long long long long ptr ptr) -@ stdcall GdipLoadImageFromFile(wstr ptr) -@ stdcall GdipLoadImageFromFileICM(wstr ptr) -@ stdcall GdipLoadImageFromStream(ptr ptr) -@ stdcall GdipLoadImageFromStreamICM(ptr ptr) -@ stdcall GdipMeasureCharacterRanges(ptr wstr long ptr ptr ptr long ptr) -@ stdcall GdipMeasureDriverString(ptr ptr long ptr ptr long ptr ptr) -@ stdcall GdipMeasureString(ptr wstr long ptr ptr ptr ptr ptr ptr) -@ stdcall GdipMultiplyLineTransform(ptr ptr long) -@ stdcall GdipMultiplyMatrix(ptr ptr long) -@ stdcall GdipMultiplyPathGradientTransform(ptr ptr long) -@ stdcall GdipMultiplyPenTransform(ptr ptr long) -@ stdcall GdipMultiplyTextureTransform(ptr ptr long) -@ stdcall GdipMultiplyWorldTransform(ptr ptr long) -@ stdcall GdipNewInstalledFontCollection(ptr) -@ stdcall GdipNewPrivateFontCollection(ptr) -@ stdcall GdipPathIterCopyData(ptr ptr ptr ptr long long) -@ stdcall GdipPathIterEnumerate(ptr ptr ptr ptr long) -@ stdcall GdipPathIterGetCount(ptr ptr) -@ stdcall GdipPathIterGetSubpathCount(ptr ptr) -@ stdcall GdipPathIterHasCurve(ptr ptr) -@ stdcall GdipPathIterIsValid(ptr ptr) -@ stdcall GdipPathIterNextMarker(ptr ptr ptr ptr) -@ stdcall GdipPathIterNextMarkerPath(ptr ptr ptr) -@ stdcall GdipPathIterNextPathType(ptr ptr ptr ptr ptr) -@ stdcall GdipPathIterNextSubpath(ptr ptr ptr ptr ptr) -@ stdcall GdipPathIterNextSubpathPath(ptr ptr ptr ptr) -@ stdcall GdipPathIterRewind(ptr) -@ stub GdipPlayMetafileRecord -@ stub GdipPlayTSClientRecord -@ stdcall GdipPrivateAddFontFile(ptr wstr) -@ stdcall GdipPrivateAddMemoryFont(ptr ptr long) -@ stdcall GdipRecordMetafile(long long ptr long wstr ptr) -@ stdcall GdipRecordMetafileFileName(wstr long long ptr long wstr ptr) -@ stdcall GdipRecordMetafileFileNameI(wstr long long ptr long wstr ptr) -@ stdcall GdipRecordMetafileI(long long ptr long wstr ptr) -@ stdcall GdipRecordMetafileStream(ptr long long ptr long wstr ptr) -@ stub GdipRecordMetafileStreamI -@ stdcall GdipReleaseDC(ptr ptr) -@ stdcall GdipRemovePropertyItem(ptr long) -@ stdcall GdipResetClip(ptr) -@ stub GdipResetImageAttributes -@ stdcall GdipResetLineTransform(ptr) -@ stub GdipResetPageTransform -@ stdcall GdipResetPath(ptr) -@ stub GdipResetPathGradientTransform -@ stdcall GdipResetPenTransform(ptr) -@ stdcall GdipResetTextureTransform(ptr) -@ stdcall GdipResetWorldTransform(ptr) -@ stdcall GdipRestoreGraphics(ptr long) -@ stdcall GdipReversePath(ptr) -@ stdcall GdipRotateLineTransform(ptr long long) -@ stdcall GdipRotateMatrix(ptr long long) -@ stdcall GdipRotatePathGradientTransform(ptr long long) -@ stdcall GdipRotatePenTransform(ptr long long) -@ stdcall GdipRotateTextureTransform(ptr long long) -@ stdcall GdipRotateWorldTransform(ptr long long) -@ stub GdipSaveAdd -@ stub GdipSaveAddImage -@ stdcall GdipSaveGraphics(ptr ptr) -@ stdcall GdipSaveImageToFile(ptr ptr ptr ptr) -@ stdcall GdipSaveImageToStream(ptr ptr ptr ptr) -@ stdcall GdipScaleLineTransform(ptr long long long) -@ stdcall GdipScaleMatrix(ptr long long long) -@ stdcall GdipScalePathGradientTransform(ptr long long long) -@ stdcall GdipScalePenTransform(ptr long long long) -@ stdcall GdipScaleTextureTransform(ptr long long long) -@ stdcall GdipScaleWorldTransform(ptr long long long) -@ stdcall GdipSetAdjustableArrowCapFillState(ptr long) -@ stdcall GdipSetAdjustableArrowCapHeight(ptr long) -@ stdcall GdipSetAdjustableArrowCapMiddleInset(ptr long) -@ stdcall GdipSetAdjustableArrowCapWidth(ptr long) -@ stdcall GdipSetClipGraphics(ptr ptr long) -@ stdcall GdipSetClipHrgn(ptr long long) -@ stdcall GdipSetClipPath(ptr ptr long) -@ stdcall GdipSetClipRect(ptr long long long long long) -@ stdcall GdipSetClipRectI(ptr long long long long long) -@ stdcall GdipSetClipRegion(ptr ptr long) -@ stdcall GdipSetCompositingMode(ptr long) -@ stdcall GdipSetCompositingQuality(ptr long) -@ stdcall GdipSetCustomLineCapBaseCap(ptr long) -@ stdcall GdipSetCustomLineCapBaseInset(ptr long) -@ stdcall GdipSetCustomLineCapStrokeCaps(ptr long long) -@ stdcall GdipSetCustomLineCapStrokeJoin(ptr long) -@ stdcall GdipSetCustomLineCapWidthScale(ptr long) -@ stdcall GdipSetEffectParameters(ptr ptr long) -@ stdcall GdipSetEmpty(ptr) -@ stdcall GdipSetImageAttributesCachedBackground(ptr long) -@ stdcall GdipSetImageAttributesColorKeys(ptr long long long long) -@ stdcall GdipSetImageAttributesColorMatrix(ptr long long ptr ptr long) -@ stdcall GdipSetImageAttributesGamma(ptr long long long) -@ stdcall GdipSetImageAttributesNoOp(ptr long long) -@ stdcall GdipSetImageAttributesOutputChannel(ptr long long long) -@ stdcall GdipSetImageAttributesOutputChannelColorProfile(ptr long long ptr) -@ stdcall GdipSetImageAttributesRemapTable(ptr long long long ptr) -@ stdcall GdipSetImageAttributesThreshold(ptr long long long) -@ stdcall GdipSetImageAttributesToIdentity(ptr long) -@ stdcall GdipSetImageAttributesWrapMode(ptr long long long) -@ stdcall GdipSetImagePalette(ptr ptr) -@ stdcall GdipSetInfinite(ptr) -@ stdcall GdipSetInterpolationMode(ptr long) -@ stdcall GdipSetLineBlend(ptr ptr ptr long) -@ stdcall GdipSetLineColors(ptr long long) -@ stdcall GdipSetLineGammaCorrection(ptr long) -@ stdcall GdipSetLineLinearBlend(ptr long long) -@ stdcall GdipSetLinePresetBlend(ptr ptr ptr long) -@ stdcall GdipSetLineSigmaBlend(ptr long long) -@ stdcall GdipSetLineTransform(ptr ptr) -@ stdcall GdipSetLineWrapMode(ptr long) -@ stdcall GdipSetMatrixElements(ptr long long long long long long) -@ stdcall GdipSetMetafileDownLevelRasterizationLimit(ptr long) -@ stdcall GdipSetPageScale(ptr long) -@ stdcall GdipSetPageUnit(ptr long) -@ stdcall GdipSetPathFillMode(ptr long) -@ stdcall GdipSetPathGradientBlend(ptr ptr ptr long) -@ stdcall GdipSetPathGradientCenterColor(ptr long) -@ stdcall GdipSetPathGradientCenterPoint(ptr ptr) -@ stdcall GdipSetPathGradientCenterPointI(ptr ptr) -@ stdcall GdipSetPathGradientFocusScales(ptr long long) -@ stdcall GdipSetPathGradientGammaCorrection(ptr long) -@ stdcall GdipSetPathGradientLinearBlend(ptr long long) -@ stub GdipSetPathGradientPath -@ stdcall GdipSetPathGradientPresetBlend(ptr ptr ptr long) -@ stdcall GdipSetPathGradientSigmaBlend(ptr long long) -@ stdcall GdipSetPathGradientSurroundColorsWithCount(ptr ptr ptr) -@ stdcall GdipSetPathGradientTransform(ptr ptr) -@ stdcall GdipSetPathGradientWrapMode(ptr long) -@ stdcall GdipSetPathMarker(ptr) -@ stdcall GdipSetPenBrushFill(ptr ptr) -@ stdcall GdipSetPenColor(ptr long) -@ stdcall GdipSetPenCompoundArray(ptr ptr long) -@ stdcall GdipSetPenCustomEndCap(ptr ptr) -@ stdcall GdipSetPenCustomStartCap(ptr ptr) -@ stdcall GdipSetPenDashArray(ptr ptr long) -@ stdcall GdipSetPenDashCap197819(ptr long) -@ stdcall GdipSetPenDashOffset(ptr long) -@ stdcall GdipSetPenDashStyle(ptr long) -@ stdcall GdipSetPenEndCap(ptr long) -@ stdcall GdipSetPenLineCap197819(ptr long long long) -@ stdcall GdipSetPenLineJoin(ptr long) -@ stdcall GdipSetPenMiterLimit(ptr long) -@ stdcall GdipSetPenMode(ptr long) -@ stdcall GdipSetPenStartCap(ptr long) -@ stdcall GdipSetPenTransform(ptr ptr) -@ stub GdipSetPenUnit -@ stdcall GdipSetPenWidth(ptr long) -@ stdcall GdipSetPixelOffsetMode(ptr long) -@ stdcall GdipSetPropertyItem(ptr ptr) -@ stdcall GdipSetRenderingOrigin(ptr long long) -@ stdcall GdipSetSmoothingMode(ptr long) -@ stdcall GdipSetSolidFillColor(ptr ptr) -@ stdcall GdipSetStringFormatAlign(ptr long) -@ stdcall GdipSetStringFormatDigitSubstitution(ptr long long) -@ stdcall GdipSetStringFormatFlags(ptr long) -@ stdcall GdipSetStringFormatHotkeyPrefix(ptr long) -@ stdcall GdipSetStringFormatLineAlign(ptr long) -@ stdcall GdipSetStringFormatMeasurableCharacterRanges(ptr long ptr) -@ stdcall GdipSetStringFormatTabStops(ptr long long ptr) -@ stdcall GdipSetStringFormatTrimming(ptr long) -@ stdcall GdipSetTextContrast(ptr long) -@ stdcall GdipSetTextRenderingHint(ptr long) -@ stdcall GdipSetTextureTransform(ptr ptr) -@ stdcall GdipSetTextureWrapMode(ptr long) -@ stdcall GdipSetWorldTransform(ptr ptr) -@ stdcall GdipShearMatrix(ptr long long long) -@ stdcall GdipStartPathFigure(ptr) -@ stdcall GdipStringFormatGetGenericDefault(ptr) -@ stdcall GdipStringFormatGetGenericTypographic(ptr) -@ stdcall GdipTestControl(long ptr) -@ stdcall GdipTransformMatrixPoints(ptr ptr long) -@ stdcall GdipTransformMatrixPointsI(ptr ptr long) -@ stdcall GdipTransformPath(ptr ptr) -@ stdcall GdipTransformPoints(ptr long long ptr long) -@ stdcall GdipTransformPointsI(ptr long long ptr long) -@ stdcall GdipTransformRegion(ptr ptr) -@ stdcall GdipTranslateClip(ptr long long) -@ stdcall GdipTranslateClipI(ptr long long) -@ stdcall GdipTranslateLineTransform(ptr long long long) -@ stdcall GdipTranslateMatrix(ptr long long long) -@ stdcall GdipTranslatePathGradientTransform(ptr long long long) -@ stdcall GdipTranslatePenTransform(ptr long long long) -@ stdcall GdipTranslateRegion(ptr long long) -@ stdcall GdipTranslateRegionI(ptr long long) -@ stdcall GdipTranslateTextureTransform(ptr long long long) -@ stdcall GdipTranslateWorldTransform(ptr long long long) -@ stdcall GdipVectorTransformMatrixPoints(ptr ptr long) -@ stdcall GdipVectorTransformMatrixPointsI(ptr ptr long) -@ stdcall GdipWarpPath(ptr ptr ptr long long long long long long long) -@ stdcall GdipWidenPath(ptr ptr ptr long) -@ stdcall GdipWindingModeOutline(ptr ptr long) -@ stdcall GdiplusNotificationHook(ptr) -@ stdcall GdiplusNotificationUnhook(ptr) -@ stdcall GdiplusShutdown(ptr) GdiplusShutdown_wrapper -@ stdcall GdiplusStartup(ptr ptr ptr) +1 stdcall GdipAddPathArc(ptr float float float float float float) +2 stdcall GdipAddPathArcI(ptr long long long long float float) +3 stdcall GdipAddPathBezier(ptr float float float float float float float float) +4 stdcall GdipAddPathBezierI(ptr long long long long long long long long) +5 stdcall GdipAddPathBeziers(ptr ptr long) +6 stdcall GdipAddPathBeziersI(ptr ptr long) +7 stdcall GdipAddPathClosedCurve2(ptr ptr long float) +8 stdcall GdipAddPathClosedCurve2I(ptr ptr long float) +9 stdcall GdipAddPathClosedCurve(ptr ptr long) +10 stdcall GdipAddPathClosedCurveI(ptr ptr long) +11 stdcall GdipAddPathCurve2(ptr ptr long float) +12 stdcall GdipAddPathCurve2I(ptr ptr long float) +13 stdcall GdipAddPathCurve3(ptr ptr long long long float) +14 stdcall GdipAddPathCurve3I(ptr ptr long long long float) +15 stdcall GdipAddPathCurve(ptr ptr long) +16 stdcall GdipAddPathCurveI(ptr ptr long) +17 stdcall GdipAddPathEllipse(ptr float float float float) +18 stdcall GdipAddPathEllipseI(ptr long long long long) +19 stdcall GdipAddPathLine2(ptr ptr long) +20 stdcall GdipAddPathLine2I(ptr ptr long) +21 stdcall GdipAddPathLine(ptr float float float float) +22 stdcall GdipAddPathLineI(ptr long long long long) +23 stdcall GdipAddPathPath(ptr ptr long) +24 stdcall GdipAddPathPie(ptr float float float float float float) +25 stdcall GdipAddPathPieI(ptr long long long long float float) +26 stdcall GdipAddPathPolygon(ptr ptr long) +27 stdcall GdipAddPathPolygonI(ptr ptr long) +28 stdcall GdipAddPathRectangle(ptr float float float float) +29 stdcall GdipAddPathRectangleI(ptr long long long long) +30 stdcall GdipAddPathRectangles(ptr ptr long) +31 stdcall GdipAddPathRectanglesI(ptr ptr long) +32 stdcall GdipAddPathString(ptr wstr long ptr long float ptr ptr) +33 stdcall GdipAddPathStringI(ptr wstr long ptr long float ptr ptr) +34 stdcall GdipAlloc(long) +35 stdcall GdipBeginContainer2(ptr ptr) +36 stdcall GdipBeginContainer(ptr ptr ptr long ptr) +37 stdcall GdipBeginContainerI(ptr ptr ptr long ptr) +38 stdcall GdipBitmapGetPixel(ptr long long ptr) +39 stdcall GdipBitmapLockBits(ptr ptr long long ptr) +40 stdcall GdipBitmapSetPixel(ptr long long long) +41 stdcall GdipBitmapSetResolution(ptr float float) +42 stdcall GdipBitmapUnlockBits(ptr ptr) +43 stdcall GdipClearPathMarkers(ptr) +44 stdcall GdipCloneBitmapArea(float float float float long ptr ptr) +45 stdcall GdipCloneBitmapAreaI(long long long long long ptr ptr) +46 stdcall GdipCloneBrush(ptr ptr) +47 stdcall GdipCloneCustomLineCap(ptr ptr) +48 stdcall GdipCloneFont(ptr ptr) +49 stdcall GdipCloneFontFamily(ptr ptr) +50 stdcall GdipCloneImage(ptr ptr) +51 stdcall GdipCloneImageAttributes(ptr ptr) +52 stdcall GdipCloneMatrix(ptr ptr) +53 stdcall GdipClonePath(ptr ptr) +54 stdcall GdipClonePen(ptr ptr) +55 stdcall GdipCloneRegion(ptr ptr) +56 stdcall GdipCloneStringFormat(ptr ptr) +57 stdcall GdipClosePathFigure(ptr) +58 stdcall GdipClosePathFigures(ptr) +59 stdcall GdipCombineRegionPath(ptr ptr long) +60 stdcall GdipCombineRegionRect(ptr ptr long) +61 stdcall GdipCombineRegionRectI(ptr ptr long) +62 stdcall GdipCombineRegionRegion(ptr ptr long) +63 stdcall GdipComment(ptr long ptr) +64 stdcall GdipCreateAdjustableArrowCap(float float long ptr) +65 stub GdipCreateBitmapFromDirectDrawSurface +66 stdcall GdipCreateBitmapFromFile(wstr ptr) +67 stdcall GdipCreateBitmapFromFileICM(wstr ptr) +68 stdcall GdipCreateBitmapFromGdiDib(ptr ptr ptr) +69 stdcall GdipCreateBitmapFromGraphics(long long ptr ptr) +70 stdcall GdipCreateBitmapFromHBITMAP(long long ptr) +71 stdcall GdipCreateBitmapFromHICON(long ptr) +72 stdcall GdipCreateBitmapFromResource(long wstr ptr) +73 stdcall GdipCreateBitmapFromScan0(long long long long ptr ptr) +74 stdcall GdipCreateBitmapFromStream(ptr ptr) +75 stdcall GdipCreateBitmapFromStreamICM(ptr ptr) +76 stdcall GdipCreateCachedBitmap(ptr ptr ptr) +77 stdcall GdipCreateCustomLineCap(ptr ptr long float ptr) +78 stdcall GdipCreateFont(ptr float long long ptr) +79 stdcall GdipCreateFontFamilyFromName(wstr ptr ptr) +80 stdcall GdipCreateFontFromDC(long ptr) +81 stdcall GdipCreateFontFromLogfontA(long ptr ptr) +82 stdcall GdipCreateFontFromLogfontW(long ptr ptr) +83 stdcall GdipCreateFromHDC2(long long ptr) +84 stdcall GdipCreateFromHDC(long ptr) +85 stdcall GdipCreateFromHWND(long ptr) +86 stdcall GdipCreateFromHWNDICM(long ptr) +87 stdcall GdipCreateHBITMAPFromBitmap(ptr ptr long) +88 stdcall GdipCreateHICONFromBitmap(ptr ptr) +89 stdcall GdipCreateHalftonePalette() +90 stdcall GdipCreateHatchBrush(long long long ptr) +91 stdcall GdipCreateImageAttributes(ptr) +92 stdcall GdipCreateLineBrush(ptr ptr long long long ptr) +93 stdcall GdipCreateLineBrushFromRect(ptr long long long long ptr) +94 stdcall GdipCreateLineBrushFromRectI(ptr long long long long ptr) +95 stdcall GdipCreateLineBrushFromRectWithAngle(ptr long long float long long ptr) +96 stdcall GdipCreateLineBrushFromRectWithAngleI(ptr long long float long long ptr) +97 stdcall GdipCreateLineBrushI(ptr ptr long long long ptr) +98 stdcall GdipCreateMatrix2(float float float float float float ptr) +99 stdcall GdipCreateMatrix3(ptr ptr ptr) +100 stdcall GdipCreateMatrix3I(ptr ptr ptr) +101 stdcall GdipCreateMatrix(ptr) +102 stdcall GdipCreateMetafileFromEmf(ptr long ptr) +103 stdcall GdipCreateMetafileFromFile(ptr ptr) +104 stdcall GdipCreateMetafileFromStream(ptr ptr) +105 stdcall GdipCreateMetafileFromWmf(ptr long ptr ptr) +106 stdcall GdipCreateMetafileFromWmfFile(wstr ptr ptr) +107 stdcall GdipCreatePath2(ptr ptr long long ptr) +108 stdcall GdipCreatePath2I(ptr ptr long long ptr) +109 stdcall GdipCreatePath(long ptr) +110 stdcall GdipCreatePathGradient(ptr long long ptr) +111 stdcall GdipCreatePathGradientFromPath(ptr ptr) +112 stdcall GdipCreatePathGradientI(ptr long long ptr) +113 stdcall GdipCreatePathIter(ptr ptr) +114 stdcall GdipCreatePen1(long float long ptr) +115 stdcall GdipCreatePen2(ptr float long ptr) +116 stdcall GdipCreateRegion(ptr) +117 stdcall GdipCreateRegionHrgn(ptr ptr) +118 stdcall GdipCreateRegionPath(ptr ptr) +119 stdcall GdipCreateRegionRect(ptr ptr) +120 stdcall GdipCreateRegionRectI(ptr ptr) +121 stdcall GdipCreateRegionRgnData(ptr long ptr) +122 stdcall GdipCreateSolidFill(long ptr) +123 stdcall GdipCreateStreamOnFile(ptr long ptr) +124 stdcall GdipCreateStringFormat(long long ptr) +125 stdcall GdipCreateTexture2(ptr long float float float float ptr) +126 stdcall GdipCreateTexture2I(ptr long long long long long ptr) +127 stdcall GdipCreateTexture(ptr long ptr) +128 stdcall GdipCreateTextureIA(ptr ptr float float float float ptr) +129 stdcall GdipCreateTextureIAI(ptr ptr long long long long ptr) +130 stdcall GdipDeleteBrush(ptr) +131 stdcall GdipDeleteCachedBitmap(ptr) +132 stdcall GdipDeleteCustomLineCap(ptr) +133 stdcall GdipDeleteFont(ptr) +134 stdcall GdipDeleteFontFamily(ptr) +135 stdcall GdipDeleteGraphics(ptr) +136 stdcall GdipDeleteMatrix(ptr) +137 stdcall GdipDeletePath(ptr) +138 stdcall GdipDeletePathIter(ptr) +139 stdcall GdipDeletePen(ptr) +140 stdcall GdipDeletePrivateFontCollection(ptr) +141 stdcall GdipDeleteRegion(ptr) +142 stdcall GdipDeleteStringFormat(ptr) +143 stdcall GdipDisposeImage(ptr) +144 stdcall GdipDisposeImageAttributes(ptr) +145 stdcall GdipDrawArc(ptr ptr float float float float float float) +146 stdcall GdipDrawArcI(ptr ptr long long long long float float) +147 stdcall GdipDrawBezier(ptr ptr float float float float float float float float) +148 stdcall GdipDrawBezierI(ptr ptr long long long long long long long long) +149 stdcall GdipDrawBeziers(ptr ptr ptr long) +150 stdcall GdipDrawBeziersI(ptr ptr ptr long) +151 stdcall GdipDrawCachedBitmap(ptr ptr long long) +152 stdcall GdipDrawClosedCurve2(ptr ptr ptr long float) +153 stdcall GdipDrawClosedCurve2I(ptr ptr ptr long float) +154 stdcall GdipDrawClosedCurve(ptr ptr ptr long) +155 stdcall GdipDrawClosedCurveI(ptr ptr ptr long) +156 stdcall GdipDrawCurve2(ptr ptr ptr long float) +157 stdcall GdipDrawCurve2I(ptr ptr ptr long float) +158 stdcall GdipDrawCurve3(ptr ptr ptr long long long float) +159 stdcall GdipDrawCurve3I(ptr ptr ptr long long long float) +160 stdcall GdipDrawCurve(ptr ptr ptr long) +161 stdcall GdipDrawCurveI(ptr ptr ptr long) +162 stdcall GdipDrawDriverString(ptr ptr long ptr ptr ptr long ptr) +163 stdcall GdipDrawEllipse(ptr ptr float float float float) +164 stdcall GdipDrawEllipseI(ptr ptr long long long long) +165 stdcall GdipDrawImage(ptr ptr float float) +166 stdcall GdipDrawImageI(ptr ptr long long) +167 stdcall GdipDrawImagePointRect(ptr ptr float float float float float float long) +168 stdcall GdipDrawImagePointRectI(ptr ptr long long long long long long long) +169 stdcall GdipDrawImagePoints(ptr ptr ptr long) +170 stdcall GdipDrawImagePointsI(ptr ptr ptr long) +171 stdcall GdipDrawImagePointsRect(ptr ptr ptr long float float float float long ptr ptr ptr) +172 stdcall GdipDrawImagePointsRectI(ptr ptr ptr long long long long long long ptr ptr ptr) +173 stdcall GdipDrawImageRect(ptr ptr float float float float) +174 stdcall GdipDrawImageRectI(ptr ptr long long long long) +175 stdcall GdipDrawImageRectRect(ptr ptr float float float float float float float float long ptr long ptr) +176 stdcall GdipDrawImageRectRectI(ptr ptr long long long long long long long long long ptr long ptr) +177 stdcall GdipDrawLine(ptr ptr float float float float) +178 stdcall GdipDrawLineI(ptr ptr long long long long) +179 stdcall GdipDrawLines(ptr ptr ptr long) +180 stdcall GdipDrawLinesI(ptr ptr ptr long) +181 stdcall GdipDrawPath(ptr ptr ptr) +182 stdcall GdipDrawPie(ptr ptr float float float float float float) +183 stdcall GdipDrawPieI(ptr ptr long long long long float float) +184 stdcall GdipDrawPolygon(ptr ptr ptr long) +185 stdcall GdipDrawPolygonI(ptr ptr ptr long) +186 stdcall GdipDrawRectangle(ptr ptr float float float float) +187 stdcall GdipDrawRectangleI(ptr ptr long long long long) +188 stdcall GdipDrawRectangles(ptr ptr ptr long) +189 stdcall GdipDrawRectanglesI(ptr ptr ptr long) +190 stdcall GdipDrawString(ptr ptr long ptr ptr ptr ptr) +191 stdcall GdipEmfToWmfBits(ptr long ptr long long) +192 stdcall GdipEndContainer(ptr ptr) +193 stub GdipEnumerateMetafileDestPoint +194 stub GdipEnumerateMetafileDestPointI +195 stub GdipEnumerateMetafileDestPoints +196 stub GdipEnumerateMetafileDestPointsI +197 stub GdipEnumerateMetafileDestRect +198 stub GdipEnumerateMetafileDestRectI +199 stub GdipEnumerateMetafileSrcRectDestPoint +200 stub GdipEnumerateMetafileSrcRectDestPointI +201 stdcall GdipEnumerateMetafileSrcRectDestPoints(ptr ptr ptr long ptr long ptr ptr ptr) +202 stub GdipEnumerateMetafileSrcRectDestPointsI +203 stub GdipEnumerateMetafileSrcRectDestRect +204 stub GdipEnumerateMetafileSrcRectDestRectI +205 stdcall GdipFillClosedCurve2(ptr ptr ptr long float long) +206 stdcall GdipFillClosedCurve2I(ptr ptr ptr long float long) +207 stdcall GdipFillClosedCurve(ptr ptr ptr long) +208 stdcall GdipFillClosedCurveI(ptr ptr ptr long) +209 stdcall GdipFillEllipse(ptr ptr float float float float) +210 stdcall GdipFillEllipseI(ptr ptr long long long long) +211 stdcall GdipFillPath(ptr ptr ptr) +212 stdcall GdipFillPie(ptr ptr float float float float float float) +213 stdcall GdipFillPieI(ptr ptr long long long long float float) +214 stdcall GdipFillPolygon2(ptr ptr ptr long) +215 stdcall GdipFillPolygon2I(ptr ptr ptr long) +216 stdcall GdipFillPolygon(ptr ptr ptr long long) +217 stdcall GdipFillPolygonI(ptr ptr ptr long long) +218 stdcall GdipFillRectangle(ptr ptr float float float float) +219 stdcall GdipFillRectangleI(ptr ptr long long long long) +220 stdcall GdipFillRectangles(ptr ptr ptr long) +221 stdcall GdipFillRectanglesI(ptr ptr ptr long) +222 stdcall GdipFillRegion(ptr ptr ptr) +223 stdcall GdipFlattenPath(ptr ptr float) +224 stdcall GdipFlush(ptr long) +225 stdcall GdipFree(ptr) +226 stdcall GdipGetAdjustableArrowCapFillState(ptr ptr) +227 stdcall GdipGetAdjustableArrowCapHeight(ptr ptr) +228 stdcall GdipGetAdjustableArrowCapMiddleInset(ptr ptr) +229 stdcall GdipGetAdjustableArrowCapWidth(ptr ptr) +230 stdcall GdipGetAllPropertyItems(ptr long long ptr) +231 stdcall GdipGetBrushType(ptr ptr) +232 stdcall GdipGetCellAscent(ptr long ptr) +233 stdcall GdipGetCellDescent(ptr long ptr) +234 stdcall GdipGetClip(ptr ptr) +235 stdcall GdipGetClipBounds(ptr ptr) +236 stdcall GdipGetClipBoundsI(ptr ptr) +237 stdcall GdipGetCompositingMode(ptr ptr) +238 stdcall GdipGetCompositingQuality(ptr ptr) +239 stdcall GdipGetCustomLineCapBaseCap(ptr ptr) +240 stdcall GdipGetCustomLineCapBaseInset(ptr ptr) +241 stub GdipGetCustomLineCapStrokeCaps +242 stdcall GdipGetCustomLineCapStrokeJoin(ptr ptr) +243 stub GdipGetCustomLineCapType +244 stdcall GdipGetCustomLineCapWidthScale(ptr ptr) +245 stdcall GdipGetDC(ptr ptr) +246 stdcall GdipGetDpiX(ptr ptr) +247 stdcall GdipGetDpiY(ptr ptr) +248 stdcall GdipGetEmHeight(ptr long ptr) +249 stub GdipGetEncoderParameterList +250 stdcall GdipGetEncoderParameterListSize(ptr ptr ptr) +251 stdcall GdipGetFamily(ptr ptr) +252 stdcall GdipGetFamilyName(ptr ptr long) +253 stdcall GdipGetFontCollectionFamilyCount(ptr ptr) +254 stdcall GdipGetFontCollectionFamilyList(ptr long ptr ptr) +255 stdcall GdipGetFontHeight(ptr ptr ptr) +256 stdcall GdipGetFontHeightGivenDPI(ptr float ptr) +257 stdcall GdipGetFontSize(ptr ptr) +258 stdcall GdipGetFontStyle(ptr ptr) +259 stdcall GdipGetFontUnit(ptr ptr) +260 stdcall GdipGetGenericFontFamilyMonospace(ptr) +261 stdcall GdipGetGenericFontFamilySansSerif(ptr) +262 stdcall GdipGetGenericFontFamilySerif(ptr) +263 stdcall GdipGetHatchBackgroundColor(ptr ptr) +264 stdcall GdipGetHatchForegroundColor(ptr ptr) +265 stdcall GdipGetHatchStyle(ptr ptr) +266 stdcall GdipGetHemfFromMetafile(ptr ptr) +267 stub GdipGetImageAttributesAdjustedPalette +268 stdcall GdipGetImageBounds(ptr ptr ptr) +269 stdcall GdipGetImageDecoders(long long ptr) +270 stdcall GdipGetImageDecodersSize(ptr ptr) +271 stdcall GdipGetImageDimension(ptr ptr ptr) +272 stdcall GdipGetImageEncoders(long long ptr) +273 stdcall GdipGetImageEncodersSize(ptr ptr) +274 stdcall GdipGetImageFlags(ptr ptr) +275 stdcall GdipGetImageGraphicsContext(ptr ptr) +276 stdcall GdipGetImageHeight(ptr ptr) +277 stdcall GdipGetImageHorizontalResolution(ptr ptr) +278 stdcall GdipGetImagePalette(ptr ptr long) +279 stdcall GdipGetImagePaletteSize(ptr ptr) +280 stdcall GdipGetImagePixelFormat(ptr ptr) +281 stdcall GdipGetImageRawFormat(ptr ptr) +282 stdcall GdipGetImageThumbnail(ptr long long ptr ptr ptr) +283 stdcall GdipGetImageType(ptr ptr) +284 stdcall GdipGetImageVerticalResolution(ptr ptr) +285 stdcall GdipGetImageWidth(ptr ptr) +286 stdcall GdipGetInterpolationMode(ptr ptr) +287 stdcall GdipGetLineBlend(ptr ptr ptr long) +288 stdcall GdipGetLineBlendCount(ptr ptr) +289 stdcall GdipGetLineColors(ptr ptr) +290 stdcall GdipGetLineGammaCorrection(ptr ptr) +291 stdcall GdipGetLinePresetBlend(ptr ptr ptr long) +292 stdcall GdipGetLinePresetBlendCount(ptr ptr) +293 stdcall GdipGetLineRect(ptr ptr) +294 stdcall GdipGetLineRectI(ptr ptr) +295 stdcall GdipGetLineSpacing(ptr long ptr) +296 stdcall GdipGetLineTransform(ptr ptr) +297 stdcall GdipGetLineWrapMode(ptr ptr) +298 stdcall GdipGetLogFontA(ptr ptr ptr) +299 stdcall GdipGetLogFontW(ptr ptr ptr) +300 stdcall GdipGetMatrixElements(ptr ptr) +301 stub GdipGetMetafileDownLevelRasterizationLimit +302 stdcall GdipGetMetafileHeaderFromEmf(ptr ptr) +303 stdcall GdipGetMetafileHeaderFromFile(wstr ptr) +304 stdcall GdipGetMetafileHeaderFromMetafile(ptr ptr) +305 stdcall GdipGetMetafileHeaderFromStream(ptr ptr) +306 stub GdipGetMetafileHeaderFromWmf +307 stdcall GdipGetNearestColor(ptr ptr) +308 stdcall GdipGetPageScale(ptr ptr) +309 stdcall GdipGetPageUnit(ptr ptr) +310 stdcall GdipGetPathData(ptr ptr) +311 stdcall GdipGetPathFillMode(ptr ptr) +312 stdcall GdipGetPathGradientBlend(ptr ptr ptr long) +313 stdcall GdipGetPathGradientBlendCount(ptr ptr) +314 stdcall GdipGetPathGradientCenterColor(ptr ptr) +315 stdcall GdipGetPathGradientCenterPoint(ptr ptr) +316 stdcall GdipGetPathGradientCenterPointI(ptr ptr) +317 stdcall GdipGetPathGradientFocusScales(ptr ptr ptr) +318 stdcall GdipGetPathGradientGammaCorrection(ptr ptr) +319 stub GdipGetPathGradientPath +320 stdcall GdipGetPathGradientPointCount(ptr ptr) +321 stdcall GdipGetPathGradientPresetBlend(ptr ptr ptr long) +322 stdcall GdipGetPathGradientPresetBlendCount(ptr ptr) +323 stdcall GdipGetPathGradientRect(ptr ptr) +324 stdcall GdipGetPathGradientRectI(ptr ptr) +325 stdcall GdipGetPathGradientSurroundColorCount(ptr ptr) +326 stdcall GdipGetPathGradientSurroundColorsWithCount(ptr ptr ptr) +327 stdcall GdipGetPathGradientTransform(ptr ptr) +328 stdcall GdipGetPathGradientWrapMode(ptr ptr) +329 stdcall GdipGetPathLastPoint(ptr ptr) +330 stdcall GdipGetPathPoints(ptr ptr long) +331 stdcall GdipGetPathPointsI(ptr ptr long) +332 stdcall GdipGetPathTypes(ptr ptr long) +333 stdcall GdipGetPathWorldBounds(ptr ptr ptr ptr) +334 stdcall GdipGetPathWorldBoundsI(ptr ptr ptr ptr) +335 stdcall GdipGetPenBrushFill(ptr ptr) +336 stdcall GdipGetPenColor(ptr ptr) +337 stub GdipGetPenCompoundArray +338 stdcall GdipGetPenCompoundCount(ptr ptr) +339 stdcall GdipGetPenCustomEndCap(ptr ptr) +340 stdcall GdipGetPenCustomStartCap(ptr ptr) +341 stdcall GdipGetPenDashArray(ptr ptr long) +342 stdcall GdipGetPenDashCap197819(ptr ptr) +343 stdcall GdipGetPenDashCount(ptr ptr) +344 stdcall GdipGetPenDashOffset(ptr ptr) +345 stdcall GdipGetPenDashStyle(ptr ptr) +346 stdcall GdipGetPenEndCap(ptr ptr) +347 stdcall GdipGetPenFillType(ptr ptr) +348 stdcall GdipGetPenLineJoin(ptr ptr) +349 stdcall GdipGetPenMiterLimit(ptr ptr) +350 stdcall GdipGetPenMode(ptr ptr) +351 stdcall GdipGetPenStartCap(ptr ptr) +352 stdcall GdipGetPenTransform(ptr ptr) +353 stdcall GdipGetPenUnit(ptr ptr) +354 stdcall GdipGetPenWidth(ptr ptr) +355 stdcall GdipGetPixelOffsetMode(ptr ptr) +356 stdcall GdipGetPointCount(ptr ptr) +357 stdcall GdipGetPropertyCount(ptr ptr) +358 stdcall GdipGetPropertyIdList(ptr long ptr) +359 stdcall GdipGetPropertyItem(ptr long long ptr) +360 stdcall GdipGetPropertyItemSize(ptr long ptr) +361 stdcall GdipGetPropertySize(ptr ptr ptr) +362 stdcall GdipGetRegionBounds(ptr ptr ptr) +363 stdcall GdipGetRegionBoundsI(ptr ptr ptr) +364 stdcall GdipGetRegionData(ptr ptr long ptr) +365 stdcall GdipGetRegionDataSize(ptr ptr) +366 stdcall GdipGetRegionHRgn(ptr ptr ptr) +367 stdcall GdipGetRegionScans(ptr ptr ptr ptr) +368 stdcall GdipGetRegionScansCount(ptr ptr ptr) +369 stdcall GdipGetRegionScansI(ptr ptr ptr ptr) +370 stdcall GdipGetRenderingOrigin(ptr ptr ptr) +371 stdcall GdipGetSmoothingMode(ptr ptr) +372 stdcall GdipGetSolidFillColor(ptr ptr) +373 stdcall GdipGetStringFormatAlign(ptr ptr) +374 stdcall GdipGetStringFormatDigitSubstitution(ptr ptr ptr) +375 stdcall GdipGetStringFormatFlags(ptr ptr) +376 stdcall GdipGetStringFormatHotkeyPrefix(ptr ptr) +377 stdcall GdipGetStringFormatLineAlign(ptr ptr) +378 stdcall GdipGetStringFormatMeasurableCharacterRangeCount(ptr ptr) +379 stdcall GdipGetStringFormatTabStopCount(ptr ptr) +380 stdcall GdipGetStringFormatTabStops(ptr long ptr ptr) +381 stdcall GdipGetStringFormatTrimming(ptr ptr) +382 stdcall GdipGetTextContrast(ptr ptr) +383 stdcall GdipGetTextRenderingHint(ptr ptr) +384 stdcall GdipGetTextureImage(ptr ptr) +385 stdcall GdipGetTextureTransform(ptr ptr) +386 stdcall GdipGetTextureWrapMode(ptr ptr) +387 stdcall GdipGetVisibleClipBounds(ptr ptr) +388 stdcall GdipGetVisibleClipBoundsI(ptr ptr) +389 stdcall GdipGetWorldTransform(ptr ptr) +390 stdcall GdipGraphicsClear(ptr long) +391 stdcall GdipImageForceValidation(ptr) +392 stdcall GdipImageGetFrameCount(ptr ptr ptr) +393 stdcall GdipImageGetFrameDimensionsCount(ptr ptr) +394 stdcall GdipImageGetFrameDimensionsList(ptr ptr long) +395 stdcall GdipImageRotateFlip(ptr long) +396 stdcall GdipImageSelectActiveFrame(ptr ptr long) +397 stdcall GdipInvertMatrix(ptr) +398 stdcall GdipIsClipEmpty(ptr ptr) +399 stdcall GdipIsEmptyRegion(ptr ptr ptr) +400 stdcall GdipIsEqualRegion(ptr ptr ptr ptr) +401 stdcall GdipIsInfiniteRegion(ptr ptr ptr) +402 stdcall GdipIsMatrixEqual(ptr ptr ptr) +403 stdcall GdipIsMatrixIdentity(ptr ptr) +404 stdcall GdipIsMatrixInvertible(ptr ptr) +405 stdcall GdipIsOutlineVisiblePathPoint(ptr float float ptr ptr ptr) +406 stdcall GdipIsOutlineVisiblePathPointI(ptr long long ptr ptr ptr) +407 stdcall GdipIsStyleAvailable(ptr long ptr) +408 stdcall GdipIsVisibleClipEmpty(ptr ptr) +409 stdcall GdipIsVisiblePathPoint(ptr float float ptr ptr) +410 stdcall GdipIsVisiblePathPointI(ptr long long ptr ptr) +411 stdcall GdipIsVisiblePoint(ptr float float ptr) +412 stdcall GdipIsVisiblePointI(ptr long long ptr) +413 stdcall GdipIsVisibleRect(ptr float float float float ptr) +414 stdcall GdipIsVisibleRectI(ptr long long long long ptr) +415 stdcall GdipIsVisibleRegionPoint(ptr float float ptr ptr) +416 stdcall GdipIsVisibleRegionPointI(ptr long long ptr ptr) +417 stdcall GdipIsVisibleRegionRect(ptr float float float float ptr ptr) +418 stdcall GdipIsVisibleRegionRectI(ptr long long long long ptr ptr) +419 stdcall GdipLoadImageFromFile(wstr ptr) +420 stdcall GdipLoadImageFromFileICM(wstr ptr) +421 stdcall GdipLoadImageFromStream(ptr ptr) +422 stdcall GdipLoadImageFromStreamICM(ptr ptr) +423 stdcall GdipMeasureCharacterRanges(ptr wstr long ptr ptr ptr long ptr) +424 stdcall GdipMeasureDriverString(ptr ptr long ptr ptr long ptr ptr) +425 stdcall GdipMeasureString(ptr wstr long ptr ptr ptr ptr ptr ptr) +426 stdcall GdipMultiplyLineTransform(ptr ptr long) +427 stdcall GdipMultiplyMatrix(ptr ptr long) +428 stdcall GdipMultiplyPathGradientTransform(ptr ptr long) +429 stdcall GdipMultiplyPenTransform(ptr ptr long) +430 stdcall GdipMultiplyTextureTransform(ptr ptr long) +431 stdcall GdipMultiplyWorldTransform(ptr ptr long) +432 stdcall GdipNewInstalledFontCollection(ptr) +433 stdcall GdipNewPrivateFontCollection(ptr) +434 stdcall GdipPathIterCopyData(ptr ptr ptr ptr long long) +435 stdcall GdipPathIterEnumerate(ptr ptr ptr ptr long) +436 stdcall GdipPathIterGetCount(ptr ptr) +437 stdcall GdipPathIterGetSubpathCount(ptr ptr) +438 stdcall GdipPathIterHasCurve(ptr ptr) +439 stdcall GdipPathIterIsValid(ptr ptr) +440 stdcall GdipPathIterNextMarker(ptr ptr ptr ptr) +441 stdcall GdipPathIterNextMarkerPath(ptr ptr ptr) +442 stdcall GdipPathIterNextPathType(ptr ptr ptr ptr ptr) +443 stdcall GdipPathIterNextSubpath(ptr ptr ptr ptr ptr) +444 stdcall GdipPathIterNextSubpathPath(ptr ptr ptr ptr) +445 stdcall GdipPathIterRewind(ptr) +446 stdcall GdipPlayMetafileRecord(ptr long long long ptr) +447 stdcall GdipPrivateAddFontFile(ptr wstr) +448 stdcall GdipPrivateAddMemoryFont(ptr ptr long) +449 stdcall GdipRecordMetafile(long long ptr long wstr ptr) +450 stdcall GdipRecordMetafileFileName(wstr long long ptr long wstr ptr) +451 stdcall GdipRecordMetafileFileNameI(wstr long long ptr long wstr ptr) +452 stdcall GdipRecordMetafileI(long long ptr long wstr ptr) +453 stdcall GdipRecordMetafileStream(ptr long long ptr long wstr ptr) +454 stub GdipRecordMetafileStreamI +455 stdcall GdipReleaseDC(ptr ptr) +456 stdcall GdipRemovePropertyItem(ptr long) +457 stdcall GdipResetClip(ptr) +458 stub GdipResetImageAttributes +459 stdcall GdipResetLineTransform(ptr) +460 stub GdipResetPageTransform +461 stdcall GdipResetPath(ptr) +462 stub GdipResetPathGradientTransform +463 stdcall GdipResetPenTransform(ptr) +464 stdcall GdipResetTextureTransform(ptr) +465 stdcall GdipResetWorldTransform(ptr) +466 stdcall GdipRestoreGraphics(ptr long) +467 stdcall GdipReversePath(ptr) +468 stdcall GdipRotateLineTransform(ptr float long) +469 stdcall GdipRotateMatrix(ptr float long) +470 stdcall GdipRotatePathGradientTransform(ptr float long) +471 stdcall GdipRotatePenTransform(ptr float long) +472 stdcall GdipRotateTextureTransform(ptr float long) +473 stdcall GdipRotateWorldTransform(ptr float long) +474 stub GdipSaveAdd +475 stub GdipSaveAddImage +476 stdcall GdipSaveGraphics(ptr ptr) +477 stdcall GdipSaveImageToFile(ptr ptr ptr ptr) +478 stdcall GdipSaveImageToStream(ptr ptr ptr ptr) +479 stdcall GdipScaleLineTransform(ptr float float long) +480 stdcall GdipScaleMatrix(ptr float float long) +481 stdcall GdipScalePathGradientTransform(ptr float float long) +482 stdcall GdipScalePenTransform(ptr float float long) +483 stdcall GdipScaleTextureTransform(ptr float float long) +484 stdcall GdipScaleWorldTransform(ptr float float long) +485 stdcall GdipSetAdjustableArrowCapFillState(ptr long) +486 stdcall GdipSetAdjustableArrowCapHeight(ptr float) +487 stdcall GdipSetAdjustableArrowCapMiddleInset(ptr float) +488 stdcall GdipSetAdjustableArrowCapWidth(ptr float) +489 stdcall GdipSetClipGraphics(ptr ptr long) +490 stdcall GdipSetClipHrgn(ptr long long) +491 stdcall GdipSetClipPath(ptr ptr long) +492 stdcall GdipSetClipRect(ptr float float float float long) +493 stdcall GdipSetClipRectI(ptr long long long long long) +494 stdcall GdipSetClipRegion(ptr ptr long) +495 stdcall GdipSetCompositingMode(ptr long) +496 stdcall GdipSetCompositingQuality(ptr long) +497 stdcall GdipSetCustomLineCapBaseCap(ptr long) +498 stdcall GdipSetCustomLineCapBaseInset(ptr float) +499 stdcall GdipSetCustomLineCapStrokeCaps(ptr long long) +500 stdcall GdipSetCustomLineCapStrokeJoin(ptr long) +501 stdcall GdipSetCustomLineCapWidthScale(ptr float) +502 stdcall GdipSetEmpty(ptr) +503 stdcall GdipSetImageAttributesCachedBackground(ptr long) +504 stdcall GdipSetImageAttributesColorKeys(ptr long long long long) +505 stdcall GdipSetImageAttributesColorMatrix(ptr long long ptr ptr long) +506 stdcall GdipSetImageAttributesGamma(ptr long long float) +507 stdcall GdipSetImageAttributesNoOp(ptr long long) +508 stdcall GdipSetImageAttributesOutputChannel(ptr long long long) +509 stdcall GdipSetImageAttributesOutputChannelColorProfile(ptr long long ptr) +510 stdcall GdipSetImageAttributesRemapTable(ptr long long long ptr) +511 stdcall GdipSetImageAttributesThreshold(ptr long long float) +512 stdcall GdipSetImageAttributesToIdentity(ptr long) +513 stdcall GdipSetImageAttributesWrapMode(ptr long long long) +514 stdcall GdipSetImagePalette(ptr ptr) +515 stdcall GdipSetInfinite(ptr) +516 stdcall GdipSetInterpolationMode(ptr long) +517 stdcall GdipSetLineBlend(ptr ptr ptr long) +518 stdcall GdipSetLineColors(ptr long long) +519 stdcall GdipSetLineGammaCorrection(ptr long) +520 stdcall GdipSetLineLinearBlend(ptr float float) +521 stdcall GdipSetLinePresetBlend(ptr ptr ptr long) +522 stdcall GdipSetLineSigmaBlend(ptr float float) +523 stdcall GdipSetLineTransform(ptr ptr) +524 stdcall GdipSetLineWrapMode(ptr long) +525 stdcall GdipSetMatrixElements(ptr float float float float float float) +526 stdcall GdipSetMetafileDownLevelRasterizationLimit(ptr long) +527 stdcall GdipSetPageScale(ptr float) +528 stdcall GdipSetPageUnit(ptr long) +529 stdcall GdipSetPathFillMode(ptr long) +530 stdcall GdipSetPathGradientBlend(ptr ptr ptr long) +531 stdcall GdipSetPathGradientCenterColor(ptr long) +532 stdcall GdipSetPathGradientCenterPoint(ptr ptr) +533 stdcall GdipSetPathGradientCenterPointI(ptr ptr) +534 stdcall GdipSetPathGradientFocusScales(ptr float float) +535 stdcall GdipSetPathGradientGammaCorrection(ptr long) +536 stdcall GdipSetPathGradientLinearBlend(ptr float float) +537 stub GdipSetPathGradientPath +538 stdcall GdipSetPathGradientPresetBlend(ptr ptr ptr long) +539 stdcall GdipSetPathGradientSigmaBlend(ptr float float) +540 stdcall GdipSetPathGradientSurroundColorsWithCount(ptr ptr ptr) +541 stdcall GdipSetPathGradientTransform(ptr ptr) +542 stdcall GdipSetPathGradientWrapMode(ptr long) +543 stdcall GdipSetPathMarker(ptr) +544 stdcall GdipSetPenBrushFill(ptr ptr) +545 stdcall GdipSetPenColor(ptr long) +546 stdcall GdipSetPenCompoundArray(ptr ptr long) +547 stdcall GdipSetPenCustomEndCap(ptr ptr) +548 stdcall GdipSetPenCustomStartCap(ptr ptr) +549 stdcall GdipSetPenDashArray(ptr ptr long) +550 stdcall GdipSetPenDashCap197819(ptr long) +551 stdcall GdipSetPenDashOffset(ptr float) +552 stdcall GdipSetPenDashStyle(ptr long) +553 stdcall GdipSetPenEndCap(ptr long) +554 stdcall GdipSetPenLineCap197819(ptr long long long) +555 stdcall GdipSetPenLineJoin(ptr long) +556 stdcall GdipSetPenMiterLimit(ptr float) +557 stdcall GdipSetPenMode(ptr long) +558 stdcall GdipSetPenStartCap(ptr long) +559 stdcall GdipSetPenTransform(ptr ptr) +560 stub GdipSetPenUnit +561 stdcall GdipSetPenWidth(ptr float) +562 stdcall GdipSetPixelOffsetMode(ptr long) +563 stdcall GdipSetPropertyItem(ptr ptr) +564 stdcall GdipSetRenderingOrigin(ptr long long) +565 stdcall GdipSetSmoothingMode(ptr long) +566 stdcall GdipSetSolidFillColor(ptr ptr) +567 stdcall GdipSetStringFormatAlign(ptr long) +568 stdcall GdipSetStringFormatDigitSubstitution(ptr long long) +569 stdcall GdipSetStringFormatFlags(ptr long) +570 stdcall GdipSetStringFormatHotkeyPrefix(ptr long) +571 stdcall GdipSetStringFormatLineAlign(ptr long) +572 stdcall GdipSetStringFormatMeasurableCharacterRanges(ptr long ptr) +573 stdcall GdipSetStringFormatTabStops(ptr float long ptr) +574 stdcall GdipSetStringFormatTrimming(ptr long) +575 stdcall GdipSetTextContrast(ptr long) +576 stdcall GdipSetTextRenderingHint(ptr long) +577 stdcall GdipSetTextureTransform(ptr ptr) +578 stdcall GdipSetTextureWrapMode(ptr long) +579 stdcall GdipSetWorldTransform(ptr ptr) +580 stdcall GdipShearMatrix(ptr float float long) +581 stdcall GdipStartPathFigure(ptr) +582 stdcall GdipStringFormatGetGenericDefault(ptr) +583 stdcall GdipStringFormatGetGenericTypographic(ptr) +584 stdcall GdipTestControl(long ptr) +585 stdcall GdipTransformMatrixPoints(ptr ptr long) +586 stdcall GdipTransformMatrixPointsI(ptr ptr long) +587 stdcall GdipTransformPath(ptr ptr) +588 stdcall GdipTransformPoints(ptr long long ptr long) +589 stdcall GdipTransformPointsI(ptr long long ptr long) +590 stdcall GdipTransformRegion(ptr ptr) +591 stdcall GdipTranslateClip(ptr float float) +592 stdcall GdipTranslateClipI(ptr long long) +593 stdcall GdipTranslateLineTransform(ptr float float long) +594 stdcall GdipTranslateMatrix(ptr float float long) +595 stdcall GdipTranslatePathGradientTransform(ptr float float long) +596 stdcall GdipTranslatePenTransform(ptr float float long) +597 stdcall GdipTranslateRegion(ptr float float) +598 stdcall GdipTranslateRegionI(ptr long long) +599 stdcall GdipTranslateTextureTransform(ptr float float long) +600 stdcall GdipTranslateWorldTransform(ptr float float long) +601 stdcall GdipVectorTransformMatrixPoints(ptr ptr long) +602 stdcall GdipVectorTransformMatrixPointsI(ptr ptr long) +603 stdcall GdipWarpPath(ptr ptr ptr long float float float float long float) +604 stdcall GdipWidenPath(ptr ptr ptr float) +605 stdcall GdipWindingModeOutline(ptr ptr float) +606 stdcall GdiplusNotificationHook(ptr) +607 stdcall GdiplusNotificationUnhook(ptr) +608 stdcall GdiplusShutdown(ptr) GdiplusShutdown_wrapper +609 stdcall GdiplusStartup(ptr ptr ptr) +610 stdcall GdipFindFirstImageItem(ptr ptr) +611 stub GdipFindNextImageItem +612 stdcall GdipGetImageItemData(ptr ptr) +613 stub GdipCreateEffect +614 stdcall GdipDeleteEffect(ptr) +615 stub GdipGetEffectParameterSize +616 stub GdipGetEffectParameters +617 stdcall GdipSetEffectParameters(ptr ptr long) +618 stub GdipInitializePalette +619 stdcall GdipBitmapCreateApplyEffect(ptr long ptr ptr ptr ptr long ptr ptr) +620 stdcall GdipBitmapApplyEffect(ptr ptr ptr long ptr ptr) +621 stub GdipBitmapGetHistogram +622 stub GdipBitmapGetHistogramSize +623 stub GdipBitmapConvertFormat +624 stub GdipImageSetAbort +625 stub GdipGraphicsSetAbort +626 stub GdipDrawImageFX +627 stdcall GdipConvertToEmfPlus(ptr ptr ptr long ptr ptr) +628 stdcall GdipConvertToEmfPlusToFile(ptr ptr ptr ptr long ptr ptr) +629 stub GdipConvertToEmfPlusToStream +630 stub GdipPlayTSClientRecord diff --git a/reactos/dll/win32/gdiplus/gdiplus_private.h b/reactos/dll/win32/gdiplus/gdiplus_private.h index b78e459a3ce..9afe15bc1ee 100644 --- a/reactos/dll/win32/gdiplus/gdiplus_private.h +++ b/reactos/dll/win32/gdiplus/gdiplus_private.h @@ -41,29 +41,38 @@ #define VERSION_MAGIC 0xdbc01001 #define TENSION_CONST (0.3) -COLORREF ARGB2COLORREF(ARGB color); -HBITMAP ARGB2BMP(ARGB color); +COLORREF ARGB2COLORREF(ARGB color) DECLSPEC_HIDDEN; +HBITMAP ARGB2BMP(ARGB color) DECLSPEC_HIDDEN; extern INT arc2polybezier(GpPointF * points, REAL x1, REAL y1, REAL x2, REAL y2, - REAL startAngle, REAL sweepAngle); -extern REAL gdiplus_atan2(REAL dy, REAL dx); -extern GpStatus hresult_to_status(HRESULT res); -extern REAL convert_unit(REAL logpixels, GpUnit unit); + REAL startAngle, REAL sweepAngle) DECLSPEC_HIDDEN; +extern REAL gdiplus_atan2(REAL dy, REAL dx) DECLSPEC_HIDDEN; +extern GpStatus hresult_to_status(HRESULT res) DECLSPEC_HIDDEN; +extern REAL convert_unit(REAL logpixels, GpUnit unit) DECLSPEC_HIDDEN; -extern GpStatus graphics_from_image(GpImage *image, GpGraphics **graphics); +extern GpStatus graphics_from_image(GpImage *image, GpGraphics **graphics) DECLSPEC_HIDDEN; + +extern GpStatus METAFILE_GetGraphicsContext(GpMetafile* metafile, GpGraphics **result) DECLSPEC_HIDDEN; +extern GpStatus METAFILE_GetDC(GpMetafile* metafile, HDC *hdc) DECLSPEC_HIDDEN; +extern GpStatus METAFILE_ReleaseDC(GpMetafile* metafile, HDC hdc) DECLSPEC_HIDDEN; +extern GpStatus METAFILE_GraphicsDeleted(GpMetafile* metafile) DECLSPEC_HIDDEN; extern void calc_curve_bezier(CONST GpPointF *pts, REAL tension, REAL *x1, - REAL *y1, REAL *x2, REAL *y2); + REAL *y1, REAL *x2, REAL *y2) DECLSPEC_HIDDEN; extern void calc_curve_bezier_endp(REAL xend, REAL yend, REAL xadj, REAL yadj, - REAL tension, REAL *x, REAL *y); + REAL tension, REAL *x, REAL *y) DECLSPEC_HIDDEN; -extern void free_installed_fonts(void); +extern void free_installed_fonts(void) DECLSPEC_HIDDEN; -extern BOOL lengthen_path(GpPath *path, INT len); +extern void get_font_hfont(GpGraphics *graphics, GDIPCONST GpFont *font, HFONT *hfont) DECLSPEC_HIDDEN; -extern GpStatus trace_path(GpGraphics *graphics, GpPath *path); +extern BOOL lengthen_path(GpPath *path, INT len) DECLSPEC_HIDDEN; + +extern GpStatus trace_path(GpGraphics *graphics, GpPath *path) DECLSPEC_HIDDEN; typedef struct region_element region_element; -extern void delete_element(region_element *element); +extern void delete_element(region_element *element) DECLSPEC_HIDDEN; + +extern GpStatus get_hatch_data(HatchStyle hatchstyle, const char **result) DECLSPEC_HIDDEN; static inline INT roundr(REAL x) { @@ -103,16 +112,16 @@ static inline ARGB color_over(ARGB bg, ARGB fg) return (a<<24)|(r<<16)|(g<<8)|b; } -extern const char *debugstr_rectf(CONST RectF* rc); +extern const char *debugstr_rectf(CONST RectF* rc) DECLSPEC_HIDDEN; -extern const char *debugstr_pointf(CONST PointF* pt); +extern const char *debugstr_pointf(CONST PointF* pt) DECLSPEC_HIDDEN; extern void convert_32bppARGB_to_32bppPARGB(UINT width, UINT height, - BYTE *dst_bits, INT dst_stride, const BYTE *src_bits, INT src_stride); + BYTE *dst_bits, INT dst_stride, const BYTE *src_bits, INT src_stride) DECLSPEC_HIDDEN; -extern GpStatus convert_pixels(UINT width, UINT height, +extern GpStatus convert_pixels(INT width, INT height, INT dst_stride, BYTE *dst_bits, PixelFormat dst_format, - INT src_stride, const BYTE *src_bits, PixelFormat src_format, ARGB *src_palette); + INT src_stride, const BYTE *src_bits, PixelFormat src_format, ARGB *src_palette) DECLSPEC_HIDDEN; struct GpPen{ UINT style; @@ -213,7 +222,8 @@ struct GpTexture{ GpBrush brush; GpMatrix *transform; GpImage *image; - WrapMode wrap; /* not used yet */ + GpImageAttributes *imageattributes; + BYTE *bitmap_bits; /* image bits converted to ARGB and run through imageattributes */ }; struct GpPath{ @@ -263,6 +273,22 @@ struct GpMetafile{ GpImage image; GpRectF bounds; GpUnit unit; + MetafileType metafile_type; + HENHMETAFILE hemf; + + /* recording */ + HDC record_dc; + GpGraphics *record_graphics; + BYTE *comment_data; + DWORD comment_data_size; + DWORD comment_data_length; + + /* playback */ + GpGraphics *playback_graphics; + HDC playback_dc; + GpPointF playback_points[3]; + HANDLETABLE *handle_table; + int handle_count; }; struct GpBitmap{ @@ -278,6 +304,7 @@ struct GpBitmap{ BYTE *bits; /* actual image bits if this is a DIB */ INT stride; /* stride of bits if this is a DIB */ BYTE *own_bits; /* image bits that need to be freed with this object */ + INT lockx, locky; /* X and Y coordinates of the rect when a bitmap is locked for writing. */ }; struct GpCachedBitmap{ @@ -317,6 +344,7 @@ struct GpImageAttributes{ struct GpFont{ LOGFONTW lfw; REAL emSize; + REAL pixel_size; UINT height; LONG line_spacing; Unit unit; @@ -394,4 +422,14 @@ struct GpRegion{ region_element node; }; +typedef GpStatus (*gdip_format_string_callback)(HDC hdc, + GDIPCONST WCHAR *string, INT index, INT length, GDIPCONST GpFont *font, + GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, + INT lineno, const RectF *bounds, void *user_data); + +GpStatus gdip_format_string(HDC hdc, + GDIPCONST WCHAR *string, INT length, GDIPCONST GpFont *font, + GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, + gdip_format_string_callback callback, void *user_data) DECLSPEC_HIDDEN; + #endif diff --git a/reactos/dll/win32/gdiplus/graphics.c b/reactos/dll/win32/gdiplus/graphics.c index e85a8ba3614..65a381502a6 100644 --- a/reactos/dll/win32/gdiplus/graphics.c +++ b/reactos/dll/win32/gdiplus/graphics.c @@ -147,6 +147,9 @@ static void restore_dc(GpGraphics *graphics, INT state) RestoreDC(graphics->hdc, state); } +static GpStatus get_graphics_transform(GpGraphics *graphics, GpCoordinateSpace dst_space, + GpCoordinateSpace src_space, GpMatrix **matrix); + /* This helper applies all the changes that the points listed in ptf need in * order to be drawn on the device context. In the end, this should include at * least: @@ -203,6 +206,11 @@ static GpStatus alpha_blend_pixels(GpGraphics *graphics, INT dst_x, INT dst_y, return Ok; } + else if (graphics->image && graphics->image->type == ImageTypeMetafile) + { + ERR("This should not be used for metafiles; fix caller\n"); + return NotImplemented; + } else { HDC hdc; @@ -253,6 +261,15 @@ static ARGB blend_colors(ARGB start, ARGB end, REAL position) { ARGB result=0; ARGB i; + INT a1, a2, a3; + + a1 = (start >> 24) & 0xff; + a2 = (end >> 24) & 0xff; + + a3 = (int)(a1*(1.0f - position)+a2*(position)); + + result |= a3 << 24; + for (i=0xff; i<=0xff0000; i = i << 8) result |= (int)((start&i)*(1.0f - position)+(end&i)*(position))&i; return result; @@ -319,130 +336,358 @@ static ARGB blend_line_gradient(GpLineGradient* brush, REAL position) } } +static ARGB transform_color(ARGB color, const ColorMatrix *matrix) +{ + REAL val[5], res[4]; + int i, j; + unsigned char a, r, g, b; + + val[0] = ((color >> 16) & 0xff) / 255.0; /* red */ + val[1] = ((color >> 8) & 0xff) / 255.0; /* green */ + val[2] = (color & 0xff) / 255.0; /* blue */ + val[3] = ((color >> 24) & 0xff) / 255.0; /* alpha */ + val[4] = 1.0; /* translation */ + + for (i=0; i<4; i++) + { + res[i] = 0.0; + + for (j=0; j<5; j++) + res[i] += matrix->m[j][i] * val[j]; + } + + a = min(max(floorf(res[3]*255.0), 0.0), 255.0); + r = min(max(floorf(res[0]*255.0), 0.0), 255.0); + g = min(max(floorf(res[1]*255.0), 0.0), 255.0); + b = min(max(floorf(res[2]*255.0), 0.0), 255.0); + + return (a << 24) | (r << 16) | (g << 8) | b; +} + +static int color_is_gray(ARGB color) +{ + unsigned char r, g, b; + + r = (color >> 16) & 0xff; + g = (color >> 8) & 0xff; + b = color & 0xff; + + return (r == g) && (g == b); +} + +static void apply_image_attributes(const GpImageAttributes *attributes, LPBYTE data, + UINT width, UINT height, INT stride, ColorAdjustType type) +{ + UINT x, y, i; + + if (attributes->colorkeys[type].enabled || + attributes->colorkeys[ColorAdjustTypeDefault].enabled) + { + const struct color_key *key; + BYTE min_blue, min_green, min_red; + BYTE max_blue, max_green, max_red; + + if (attributes->colorkeys[type].enabled) + key = &attributes->colorkeys[type]; + else + key = &attributes->colorkeys[ColorAdjustTypeDefault]; + + min_blue = key->low&0xff; + min_green = (key->low>>8)&0xff; + min_red = (key->low>>16)&0xff; + + max_blue = key->high&0xff; + max_green = (key->high>>8)&0xff; + max_red = (key->high>>16)&0xff; + + for (x=0; x>8)&0xff; + red = (*src_color>>16)&0xff; + if (blue >= min_blue && green >= min_green && red >= min_red && + blue <= max_blue && green <= max_green && red <= max_red) + *src_color = 0x00000000; + } + } + + if (attributes->colorremaptables[type].enabled || + attributes->colorremaptables[ColorAdjustTypeDefault].enabled) + { + const struct color_remap_table *table; + + if (attributes->colorremaptables[type].enabled) + table = &attributes->colorremaptables[type]; + else + table = &attributes->colorremaptables[ColorAdjustTypeDefault]; + + for (x=0; xmapsize; i++) + { + if (*src_color == table->colormap[i].oldColor.Argb) + { + *src_color = table->colormap[i].newColor.Argb; + break; + } + } + } + } + + if (attributes->colormatrices[type].enabled || + attributes->colormatrices[ColorAdjustTypeDefault].enabled) + { + const struct color_matrix *colormatrices; + + if (attributes->colormatrices[type].enabled) + colormatrices = &attributes->colormatrices[type]; + else + colormatrices = &attributes->colormatrices[ColorAdjustTypeDefault]; + + for (x=0; xflags == ColorMatrixFlagsDefault || + !color_is_gray(*src_color)) + { + *src_color = transform_color(*src_color, &colormatrices->colormatrix); + } + else if (colormatrices->flags == ColorMatrixFlagsAltGray) + { + *src_color = transform_color(*src_color, &colormatrices->graymatrix); + } + } + } + + if (attributes->gamma_enabled[type] || + attributes->gamma_enabled[ColorAdjustTypeDefault]) + { + REAL gamma; + + if (attributes->gamma_enabled[type]) + gamma = attributes->gamma[type]; + else + gamma = attributes->gamma[ColorAdjustTypeDefault]; + + for (x=0; x>8)&0xff; + red = (*src_color>>16)&0xff; + + /* FIXME: We should probably use a table for this. */ + blue = floorf(powf(blue / 255.0, gamma) * 255.0); + green = floorf(powf(green / 255.0, gamma) * 255.0); + red = floorf(powf(red / 255.0, gamma) * 255.0); + + *src_color = (*src_color & 0xff000000) | (red << 16) | (green << 8) | blue; + } + } +} + +/* Given a bitmap and its source rectangle, find the smallest rectangle in the + * bitmap that contains all the pixels we may need to draw it. */ +static void get_bitmap_sample_size(InterpolationMode interpolation, WrapMode wrap, + GpBitmap* bitmap, REAL srcx, REAL srcy, REAL srcwidth, REAL srcheight, + GpRect *rect) +{ + INT left, top, right, bottom; + + switch (interpolation) + { + case InterpolationModeHighQualityBilinear: + case InterpolationModeHighQualityBicubic: + /* FIXME: Include a greater range for the prefilter? */ + case InterpolationModeBicubic: + case InterpolationModeBilinear: + left = (INT)(floorf(srcx)); + top = (INT)(floorf(srcy)); + right = (INT)(ceilf(srcx+srcwidth)); + bottom = (INT)(ceilf(srcy+srcheight)); + break; + case InterpolationModeNearestNeighbor: + default: + left = roundr(srcx); + top = roundr(srcy); + right = roundr(srcx+srcwidth); + bottom = roundr(srcy+srcheight); + break; + } + + if (wrap == WrapModeClamp) + { + if (left < 0) + left = 0; + if (top < 0) + top = 0; + if (right >= bitmap->width) + right = bitmap->width-1; + if (bottom >= bitmap->height) + bottom = bitmap->height-1; + } + else + { + /* In some cases we can make the rectangle smaller here, but the logic + * is hard to get right, and tiling suggests we're likely to use the + * entire source image. */ + if (left < 0 || right >= bitmap->width) + { + left = 0; + right = bitmap->width-1; + } + + if (top < 0 || bottom >= bitmap->height) + { + top = 0; + bottom = bitmap->height-1; + } + } + + rect->X = left; + rect->Y = top; + rect->Width = right - left + 1; + rect->Height = bottom - top + 1; +} + +static ARGB sample_bitmap_pixel(GDIPCONST GpRect *src_rect, LPBYTE bits, UINT width, + UINT height, INT x, INT y, GDIPCONST GpImageAttributes *attributes) +{ + if (attributes->wrap == WrapModeClamp) + { + if (x < 0 || y < 0 || x >= width || y >= height) + return attributes->outside_color; + } + else + { + /* Tiling. Make sure co-ordinates are positive as it simplifies the math. */ + if (x < 0) + x = width*2 + x % (width * 2); + if (y < 0) + y = height*2 + y % (height * 2); + + if ((attributes->wrap & 1) == 1) + { + /* Flip X */ + if ((x / width) % 2 == 0) + x = x % width; + else + x = width - 1 - x % width; + } + else + x = x % width; + + if ((attributes->wrap & 2) == 2) + { + /* Flip Y */ + if ((y / height) % 2 == 0) + y = y % height; + else + y = height - 1 - y % height; + } + else + y = y % height; + } + + if (x < src_rect->X || y < src_rect->Y || x >= src_rect->X + src_rect->Width || y >= src_rect->Y + src_rect->Height) + { + ERR("out of range pixel requested\n"); + return 0xffcd0084; + } + + return ((DWORD*)(bits))[(x - src_rect->X) + (y - src_rect->Y) * src_rect->Width]; +} + +static ARGB resample_bitmap_pixel(GDIPCONST GpRect *src_rect, LPBYTE bits, UINT width, + UINT height, GpPointF *point, GDIPCONST GpImageAttributes *attributes, + InterpolationMode interpolation) +{ + static int fixme; + + switch (interpolation) + { + default: + if (!fixme++) + FIXME("Unimplemented interpolation %i\n", interpolation); + /* fall-through */ + case InterpolationModeBilinear: + { + REAL leftxf, topyf; + INT leftx, rightx, topy, bottomy; + ARGB topleft, topright, bottomleft, bottomright; + ARGB top, bottom; + float x_offset; + + leftxf = floorf(point->X); + leftx = (INT)leftxf; + rightx = (INT)ceilf(point->X); + topyf = floorf(point->Y); + topy = (INT)topyf; + bottomy = (INT)ceilf(point->Y); + + if (leftx == rightx && topy == bottomy) + return sample_bitmap_pixel(src_rect, bits, width, height, + leftx, topy, attributes); + + topleft = sample_bitmap_pixel(src_rect, bits, width, height, + leftx, topy, attributes); + topright = sample_bitmap_pixel(src_rect, bits, width, height, + rightx, topy, attributes); + bottomleft = sample_bitmap_pixel(src_rect, bits, width, height, + leftx, bottomy, attributes); + bottomright = sample_bitmap_pixel(src_rect, bits, width, height, + rightx, bottomy, attributes); + + x_offset = point->X - leftxf; + top = blend_colors(topleft, topright, x_offset); + bottom = blend_colors(bottomleft, bottomright, x_offset); + + return blend_colors(top, bottom, point->Y - topyf); + } + case InterpolationModeNearestNeighbor: + return sample_bitmap_pixel(src_rect, bits, width, height, + roundr(point->X), roundr(point->Y), attributes); + } +} + +static INT brush_can_fill_path(GpBrush *brush) +{ + switch (brush->bt) + { + case BrushTypeSolidColor: + return 1; + case BrushTypeHatchFill: + { + GpHatch *hatch = (GpHatch*)brush; + return ((hatch->forecol & 0xff000000) == 0xff000000) && + ((hatch->backcol & 0xff000000) == 0xff000000); + } + case BrushTypeLinearGradient: + case BrushTypeTextureFill: + /* Gdi32 isn't much help with these, so we should use brush_fill_pixels instead. */ + default: + return 0; + } +} + static void brush_fill_path(GpGraphics *graphics, GpBrush* brush) { switch (brush->bt) { - case BrushTypeLinearGradient: - { - GpLineGradient *line = (GpLineGradient*)brush; - RECT rc; - - SelectClipPath(graphics->hdc, RGN_AND); - if (GetClipBox(graphics->hdc, &rc) != NULLREGION) - { - GpPointF endpointsf[2]; - POINT endpointsi[2]; - POINT poly[4]; - - SelectObject(graphics->hdc, GetStockObject(NULL_PEN)); - - endpointsf[0] = line->startpoint; - endpointsf[1] = line->endpoint; - transform_and_round_points(graphics, endpointsi, endpointsf, 2); - - if (abs(endpointsi[0].x-endpointsi[1].x) > abs(endpointsi[0].y-endpointsi[1].y)) - { - /* vertical-ish gradient */ - int startx, endx; /* x co-ordinates of endpoints shifted to intersect the top of the visible rectangle */ - int startbottomx; /* x co-ordinate of start point shifted to intersect the bottom of the visible rectangle */ - int width; - COLORREF col; - HBRUSH hbrush, hprevbrush; - int leftx, rightx; /* x co-ordinates where the leftmost and rightmost gradient lines hit the top of the visible rectangle */ - int x; - int tilt; /* horizontal distance covered by a gradient line */ - - startx = roundr((rc.top - endpointsf[0].Y) * (endpointsf[1].Y - endpointsf[0].Y) / (endpointsf[0].X - endpointsf[1].X) + endpointsf[0].X); - endx = roundr((rc.top - endpointsf[1].Y) * (endpointsf[1].Y - endpointsf[0].Y) / (endpointsf[0].X - endpointsf[1].X) + endpointsf[1].X); - width = endx - startx; - startbottomx = roundr((rc.bottom - endpointsf[0].Y) * (endpointsf[1].Y - endpointsf[0].Y) / (endpointsf[0].X - endpointsf[1].X) + endpointsf[0].X); - tilt = startx - startbottomx; - - if (startx >= startbottomx) - { - leftx = rc.left; - rightx = rc.right + tilt; - } - else - { - leftx = rc.left + tilt; - rightx = rc.right; - } - - poly[0].y = rc.bottom; - poly[1].y = rc.top; - poly[2].y = rc.top; - poly[3].y = rc.bottom; - - for (x=leftx; x<=rightx; x++) - { - ARGB argb = blend_line_gradient(line, (x-startx)/(REAL)width); - col = ARGB2COLORREF(argb); - hbrush = CreateSolidBrush(col); - hprevbrush = SelectObject(graphics->hdc, hbrush); - poly[0].x = x - tilt - 1; - poly[1].x = x - 1; - poly[2].x = x; - poly[3].x = x - tilt; - Polygon(graphics->hdc, poly, 4); - SelectObject(graphics->hdc, hprevbrush); - DeleteObject(hbrush); - } - } - else if (endpointsi[0].y != endpointsi[1].y) - { - /* horizontal-ish gradient */ - int starty, endy; /* y co-ordinates of endpoints shifted to intersect the left of the visible rectangle */ - int startrighty; /* y co-ordinate of start point shifted to intersect the right of the visible rectangle */ - int height; - COLORREF col; - HBRUSH hbrush, hprevbrush; - int topy, bottomy; /* y co-ordinates where the topmost and bottommost gradient lines hit the left of the visible rectangle */ - int y; - int tilt; /* vertical distance covered by a gradient line */ - - starty = roundr((rc.left - endpointsf[0].X) * (endpointsf[0].X - endpointsf[1].X) / (endpointsf[1].Y - endpointsf[0].Y) + endpointsf[0].Y); - endy = roundr((rc.left - endpointsf[1].X) * (endpointsf[0].X - endpointsf[1].X) / (endpointsf[1].Y - endpointsf[0].Y) + endpointsf[1].Y); - height = endy - starty; - startrighty = roundr((rc.right - endpointsf[0].X) * (endpointsf[0].X - endpointsf[1].X) / (endpointsf[1].Y - endpointsf[0].Y) + endpointsf[0].Y); - tilt = starty - startrighty; - - if (starty >= startrighty) - { - topy = rc.top; - bottomy = rc.bottom + tilt; - } - else - { - topy = rc.top + tilt; - bottomy = rc.bottom; - } - - poly[0].x = rc.right; - poly[1].x = rc.left; - poly[2].x = rc.left; - poly[3].x = rc.right; - - for (y=topy; y<=bottomy; y++) - { - ARGB argb = blend_line_gradient(line, (y-starty)/(REAL)height); - col = ARGB2COLORREF(argb); - hbrush = CreateSolidBrush(col); - hprevbrush = SelectObject(graphics->hdc, hbrush); - poly[0].y = y - tilt - 1; - poly[1].y = y - 1; - poly[2].y = y; - poly[3].y = y - tilt; - Polygon(graphics->hdc, poly, 4); - SelectObject(graphics->hdc, hprevbrush); - DeleteObject(hbrush); - } - } - /* else startpoint == endpoint */ - } - break; - } case BrushTypeSolidColor: { GpSolidFill *fill = (GpSolidFill*)brush; @@ -484,6 +729,234 @@ static void brush_fill_path(GpGraphics *graphics, GpBrush* brush) } } +static INT brush_can_fill_pixels(GpBrush *brush) +{ + switch (brush->bt) + { + case BrushTypeSolidColor: + case BrushTypeHatchFill: + case BrushTypeLinearGradient: + case BrushTypeTextureFill: + return 1; + default: + return 0; + } +} + +static GpStatus brush_fill_pixels(GpGraphics *graphics, GpBrush *brush, + DWORD *argb_pixels, GpRect *fill_area, UINT cdwStride) +{ + switch (brush->bt) + { + case BrushTypeSolidColor: + { + int x, y; + GpSolidFill *fill = (GpSolidFill*)brush; + for (x=0; xWidth; x++) + for (y=0; yHeight; y++) + argb_pixels[x + y*cdwStride] = fill->color; + return Ok; + } + case BrushTypeHatchFill: + { + int x, y; + GpHatch *fill = (GpHatch*)brush; + const char *hatch_data; + + if (get_hatch_data(fill->hatchstyle, &hatch_data) != Ok) + return NotImplemented; + + for (x=0; xWidth; x++) + for (y=0; yHeight; y++) + { + int hx, hy; + + /* FIXME: Account for the rendering origin */ + hx = (x + fill_area->X) % 8; + hy = (y + fill_area->Y) % 8; + + if ((hatch_data[7-hy] & (0x80 >> hx)) != 0) + argb_pixels[x + y*cdwStride] = fill->forecol; + else + argb_pixels[x + y*cdwStride] = fill->backcol; + } + + return Ok; + } + case BrushTypeLinearGradient: + { + GpLineGradient *fill = (GpLineGradient*)brush; + GpPointF draw_points[3], line_points[3]; + GpStatus stat; + static const GpRectF box_1 = { 0.0, 0.0, 1.0, 1.0 }; + GpMatrix *world_to_gradient; /* FIXME: Store this in the brush? */ + int x, y; + + draw_points[0].X = fill_area->X; + draw_points[0].Y = fill_area->Y; + draw_points[1].X = fill_area->X+1; + draw_points[1].Y = fill_area->Y; + draw_points[2].X = fill_area->X; + draw_points[2].Y = fill_area->Y+1; + + /* Transform the points to a co-ordinate space where X is the point's + * position in the gradient, 0.0 being the start point and 1.0 the + * end point. */ + stat = GdipTransformPoints(graphics, CoordinateSpaceWorld, + CoordinateSpaceDevice, draw_points, 3); + + if (stat == Ok) + { + line_points[0] = fill->startpoint; + line_points[1] = fill->endpoint; + line_points[2].X = fill->startpoint.X + (fill->startpoint.Y - fill->endpoint.Y); + line_points[2].Y = fill->startpoint.Y + (fill->endpoint.X - fill->startpoint.X); + + stat = GdipCreateMatrix3(&box_1, line_points, &world_to_gradient); + } + + if (stat == Ok) + { + stat = GdipInvertMatrix(world_to_gradient); + + if (stat == Ok) + stat = GdipTransformMatrixPoints(world_to_gradient, draw_points, 3); + + GdipDeleteMatrix(world_to_gradient); + } + + if (stat == Ok) + { + REAL x_delta = draw_points[1].X - draw_points[0].X; + REAL y_delta = draw_points[2].X - draw_points[0].X; + + for (y=0; yHeight; y++) + { + for (x=0; xWidth; x++) + { + REAL pos = draw_points[0].X + x * x_delta + y * y_delta; + + argb_pixels[x + y*cdwStride] = blend_line_gradient(fill, pos); + } + } + } + + return stat; + } + case BrushTypeTextureFill: + { + GpTexture *fill = (GpTexture*)brush; + GpPointF draw_points[3]; + GpStatus stat; + GpMatrix *world_to_texture; + int x, y; + GpBitmap *bitmap; + int src_stride; + GpRect src_area; + + if (fill->image->type != ImageTypeBitmap) + { + FIXME("metafile texture brushes not implemented\n"); + return NotImplemented; + } + + bitmap = (GpBitmap*)fill->image; + src_stride = sizeof(ARGB) * bitmap->width; + + src_area.X = src_area.Y = 0; + src_area.Width = bitmap->width; + src_area.Height = bitmap->height; + + draw_points[0].X = fill_area->X; + draw_points[0].Y = fill_area->Y; + draw_points[1].X = fill_area->X+1; + draw_points[1].Y = fill_area->Y; + draw_points[2].X = fill_area->X; + draw_points[2].Y = fill_area->Y+1; + + /* Transform the points to the co-ordinate space of the bitmap. */ + stat = GdipTransformPoints(graphics, CoordinateSpaceWorld, + CoordinateSpaceDevice, draw_points, 3); + + if (stat == Ok) + { + stat = GdipCloneMatrix(fill->transform, &world_to_texture); + } + + if (stat == Ok) + { + stat = GdipInvertMatrix(world_to_texture); + + if (stat == Ok) + stat = GdipTransformMatrixPoints(world_to_texture, draw_points, 3); + + GdipDeleteMatrix(world_to_texture); + } + + if (stat == Ok && !fill->bitmap_bits) + { + BitmapData lockeddata; + + fill->bitmap_bits = GdipAlloc(sizeof(ARGB) * bitmap->width * bitmap->height); + if (!fill->bitmap_bits) + stat = OutOfMemory; + + if (stat == Ok) + { + lockeddata.Width = bitmap->width; + lockeddata.Height = bitmap->height; + lockeddata.Stride = src_stride; + lockeddata.PixelFormat = PixelFormat32bppARGB; + lockeddata.Scan0 = fill->bitmap_bits; + + stat = GdipBitmapLockBits(bitmap, &src_area, ImageLockModeRead|ImageLockModeUserInputBuf, + PixelFormat32bppARGB, &lockeddata); + } + + if (stat == Ok) + stat = GdipBitmapUnlockBits(bitmap, &lockeddata); + + if (stat == Ok) + apply_image_attributes(fill->imageattributes, fill->bitmap_bits, + bitmap->width, bitmap->height, + src_stride, ColorAdjustTypeBitmap); + + if (stat != Ok) + { + GdipFree(fill->bitmap_bits); + fill->bitmap_bits = NULL; + } + } + + if (stat == Ok) + { + REAL x_dx = draw_points[1].X - draw_points[0].X; + REAL x_dy = draw_points[1].Y - draw_points[0].Y; + REAL y_dx = draw_points[2].X - draw_points[0].X; + REAL y_dy = draw_points[2].Y - draw_points[0].Y; + + for (y=0; yHeight; y++) + { + for (x=0; xWidth; x++) + { + GpPointF point; + point.X = draw_points[0].X + x * x_dx + y * y_dx; + point.Y = draw_points[0].Y + y * x_dy + y * y_dy; + + argb_pixels[x + y*cdwStride] = resample_bitmap_pixel( + &src_area, fill->bitmap_bits, bitmap->width, bitmap->height, + &point, fill->imageattributes, graphics->interpolation); + } + } + } + + return stat; + } + default: + return NotImplemented; + } +} + /* GdipDrawPie/GdipFillPie helper function */ static void draw_pie(GpGraphics *graphics, REAL x, REAL y, REAL width, REAL height, REAL startAngle, REAL sweepAngle) @@ -1191,6 +1664,47 @@ end: return stat; } +void get_font_hfont(GpGraphics *graphics, GDIPCONST GpFont *font, HFONT *hfont) +{ + HDC hdc = CreateCompatibleDC(0); + GpPointF pt[3]; + REAL angle, rel_width, rel_height; + LOGFONTW lfw; + HFONT unscaled_font; + TEXTMETRICW textmet; + + pt[0].X = 0.0; + pt[0].Y = 0.0; + pt[1].X = 1.0; + pt[1].Y = 0.0; + pt[2].X = 0.0; + pt[2].Y = 1.0; + if (graphics) + GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, pt, 3); + angle = -gdiplus_atan2((pt[1].Y - pt[0].Y), (pt[1].X - pt[0].X)); + rel_width = sqrt((pt[1].Y-pt[0].Y)*(pt[1].Y-pt[0].Y)+ + (pt[1].X-pt[0].X)*(pt[1].X-pt[0].X)); + rel_height = sqrt((pt[2].Y-pt[0].Y)*(pt[2].Y-pt[0].Y)+ + (pt[2].X-pt[0].X)*(pt[2].X-pt[0].X)); + + lfw = font->lfw; + lfw.lfHeight = roundr(-font->pixel_size * rel_height); + unscaled_font = CreateFontIndirectW(&lfw); + + SelectObject(hdc, unscaled_font); + GetTextMetricsW(hdc, &textmet); + + lfw = font->lfw; + lfw.lfHeight = roundr(-font->pixel_size * rel_height); + lfw.lfWidth = roundr(textmet.tmAveCharWidth * rel_width / rel_height); + lfw.lfEscapement = lfw.lfOrientation = roundr((angle / M_PI) * 1800.0); + + *hfont = CreateFontIndirectW(&lfw); + + DeleteDC(hdc); + DeleteObject(unscaled_font); +} + GpStatus WINGDIPAPI GdipCreateFromHDC(HDC hdc, GpGraphics **graphics) { TRACE("(%p, %p)\n", hdc, graphics); @@ -1234,7 +1748,7 @@ GpStatus WINGDIPAPI GdipCreateFromHDC2(HDC hdc, HANDLE hDevice, GpGraphics **gra (*graphics)->owndc = FALSE; (*graphics)->smoothing = SmoothingModeDefault; (*graphics)->compqual = CompositingQualityDefault; - (*graphics)->interpolation = InterpolationModeDefault; + (*graphics)->interpolation = InterpolationModeBilinear; (*graphics)->pixeloffset = PixelOffsetModeDefault; (*graphics)->compmode = CompositingModeSourceOver; (*graphics)->unit = UnitDisplay; @@ -1273,7 +1787,7 @@ GpStatus graphics_from_image(GpImage *image, GpGraphics **graphics) (*graphics)->image = image; (*graphics)->smoothing = SmoothingModeDefault; (*graphics)->compqual = CompositingQualityDefault; - (*graphics)->interpolation = InterpolationModeDefault; + (*graphics)->interpolation = InterpolationModeBilinear; (*graphics)->pixeloffset = PixelOffsetModeDefault; (*graphics)->compmode = CompositingModeSourceOver; (*graphics)->unit = UnitDisplay; @@ -1463,11 +1977,19 @@ GpStatus WINGDIPAPI GdipCreateStreamOnFile(GDIPCONST WCHAR * filename, GpStatus WINGDIPAPI GdipDeleteGraphics(GpGraphics *graphics) { GraphicsContainerItem *cont, *next; + GpStatus stat; TRACE("(%p)\n", graphics); if(!graphics) return InvalidParameter; if(graphics->busy) return ObjectBusy; + if (graphics->image && graphics->image->type == ImageTypeMetafile) + { + stat = METAFILE_GraphicsDeleted((GpMetafile*)graphics->image); + if (stat != Ok) + return stat; + } + if(graphics->owndc) ReleaseDC(graphics->hwnd, graphics->hdc); @@ -2006,15 +2528,38 @@ GpStatus WINGDIPAPI GdipDrawImagePointRectI(GpGraphics *graphics, GpImage *image GpStatus WINGDIPAPI GdipDrawImagePoints(GpGraphics *graphics, GpImage *image, GDIPCONST GpPointF *dstpoints, INT count) { - FIXME("(%p, %p, %p, %d): stub\n", graphics, image, dstpoints, count); - return NotImplemented; + UINT width, height; + + TRACE("(%p, %p, %p, %d)\n", graphics, image, dstpoints, count); + + if(!image) + return InvalidParameter; + + GdipGetImageWidth(image, &width); + GdipGetImageHeight(image, &height); + + return GdipDrawImagePointsRect(graphics, image, dstpoints, count, 0, 0, + width, height, UnitPixel, NULL, NULL, NULL); } GpStatus WINGDIPAPI GdipDrawImagePointsI(GpGraphics *graphics, GpImage *image, GDIPCONST GpPoint *dstpoints, INT count) { - FIXME("(%p, %p, %p, %d): stub\n", graphics, image, dstpoints, count); - return NotImplemented; + GpPointF ptf[3]; + + TRACE("(%p, %p, %p, %d)\n", graphics, image, dstpoints, count); + + if (count != 3 || !dstpoints) + return InvalidParameter; + + ptf[0].X = (REAL)dstpoints[0].X; + ptf[0].Y = (REAL)dstpoints[0].Y; + ptf[1].X = (REAL)dstpoints[1].X; + ptf[1].Y = (REAL)dstpoints[1].Y; + ptf[2].X = (REAL)dstpoints[2].X; + ptf[2].Y = (REAL)dstpoints[2].Y; + + return GdipDrawImagePoints(graphics, image, ptf, count); } GpStatus WINGDIPAPI GdipDrawImagePointsRect(GpGraphics *graphics, GpImage *image, @@ -2031,6 +2576,9 @@ GpStatus WINGDIPAPI GdipDrawImagePointsRect(GpGraphics *graphics, GpImage *image count, srcx, srcy, srcwidth, srcheight, srcUnit, imageAttributes, callback, callbackData); + if (count > 3) + return NotImplemented; + if(!graphics || !image || !points || count != 3) return InvalidParameter; @@ -2040,6 +2588,8 @@ GpStatus WINGDIPAPI GdipDrawImagePointsRect(GpGraphics *graphics, GpImage *image memcpy(ptf, points, 3 * sizeof(GpPointF)); ptf[3].X = ptf[2].X + ptf[1].X - ptf[0].X; ptf[3].Y = ptf[2].Y + ptf[1].Y - ptf[0].Y; + if (!srcwidth || !srcheight || ptf[3].X == ptf[0].X || ptf[3].Y == ptf[0].Y) + return Ok; transform_and_round_points(graphics, pti, ptf, 4); if (image->picture) @@ -2083,24 +2633,36 @@ GpStatus WINGDIPAPI GdipDrawImagePointsRect(GpGraphics *graphics, GpImage *image else return NotImplemented; + srcx = srcx * dx; + srcy = srcy * dy; + srcwidth = srcwidth * dx; + srcheight = srcheight * dy; + if (imageAttributes || (graphics->image && graphics->image->type == ImageTypeBitmap) || !((GpBitmap*)image)->hbitmap || - ptf[1].Y != ptf[0].Y || ptf[2].X != ptf[0].X) + ptf[1].Y != ptf[0].Y || ptf[2].X != ptf[0].X || + ptf[1].X - ptf[0].X != srcwidth || ptf[2].Y - ptf[0].Y != srcheight || + srcx < 0 || srcy < 0 || + srcx + srcwidth > bitmap->width || srcy + srcheight > bitmap->height) use_software = 1; if (use_software) { - RECT src_area, dst_area; - int i, x, y, stride; + RECT dst_area; + GpRect src_area; + int i, x, y, src_stride, dst_stride; GpMatrix *dst_to_src; REAL m11, m12, m21, m22, mdx, mdy; - LPBYTE data; + LPBYTE src_data, dst_data; + BitmapData lockeddata; + InterpolationMode interpolation = graphics->interpolation; + GpPointF dst_to_src_points[3] = {{0.0, 0.0}, {1.0, 0.0}, {0.0, 1.0}}; + REAL x_dx, x_dy, y_dx, y_dy; + static const GpImageAttributes defaultImageAttributes = {WrapModeClamp, 0, FALSE}; - src_area.left = srcx*dx; - src_area.top = srcy*dy; - src_area.right = (srcx+srcwidth)*dx; - src_area.bottom = (srcy+srcheight)*dy; + if (!imageAttributes) + imageAttributes = &defaultImageAttributes; dst_area.left = dst_area.right = pti[0].x; dst_area.top = dst_area.bottom = pti[0].y; @@ -2129,137 +2691,88 @@ GpStatus WINGDIPAPI GdipDrawImagePointsRect(GpGraphics *graphics, GpImage *image return stat; } - data = GdipAlloc(sizeof(ARGB) * (dst_area.right - dst_area.left) * (dst_area.bottom - dst_area.top)); - if (!data) + dst_data = GdipAlloc(sizeof(ARGB) * (dst_area.right - dst_area.left) * (dst_area.bottom - dst_area.top)); + if (!dst_data) { GdipDeleteMatrix(dst_to_src); return OutOfMemory; } - stride = sizeof(ARGB) * (dst_area.right - dst_area.left); + dst_stride = sizeof(ARGB) * (dst_area.right - dst_area.left); - if (imageAttributes && - (imageAttributes->wrap != WrapModeClamp || - imageAttributes->outside_color != 0x00000000 || - imageAttributes->clamp)) + get_bitmap_sample_size(interpolation, imageAttributes->wrap, + bitmap, srcx, srcy, srcwidth, srcheight, &src_area); + + src_data = GdipAlloc(sizeof(ARGB) * src_area.Width * src_area.Height); + if (!src_data) { - static int fixme; - if (!fixme++) - FIXME("Image wrap mode not implemented\n"); + GdipFree(dst_data); + GdipDeleteMatrix(dst_to_src); + return OutOfMemory; } + src_stride = sizeof(ARGB) * src_area.Width; + + /* Read the bits we need from the source bitmap into an ARGB buffer. */ + lockeddata.Width = src_area.Width; + lockeddata.Height = src_area.Height; + lockeddata.Stride = src_stride; + lockeddata.PixelFormat = PixelFormat32bppARGB; + lockeddata.Scan0 = src_data; + + stat = GdipBitmapLockBits(bitmap, &src_area, ImageLockModeRead|ImageLockModeUserInputBuf, + PixelFormat32bppARGB, &lockeddata); + + if (stat == Ok) + stat = GdipBitmapUnlockBits(bitmap, &lockeddata); + + if (stat != Ok) + { + if (src_data != dst_data) + GdipFree(src_data); + GdipFree(dst_data); + GdipDeleteMatrix(dst_to_src); + return OutOfMemory; + } + + apply_image_attributes(imageAttributes, src_data, + src_area.Width, src_area.Height, + src_stride, ColorAdjustTypeBitmap); + + /* Transform the bits as needed to the destination. */ + GdipTransformMatrixPoints(dst_to_src, dst_to_src_points, 3); + + x_dx = dst_to_src_points[1].X - dst_to_src_points[0].X; + x_dy = dst_to_src_points[1].Y - dst_to_src_points[0].Y; + y_dx = dst_to_src_points[2].X - dst_to_src_points[0].X; + y_dy = dst_to_src_points[2].Y - dst_to_src_points[0].Y; for (x=dst_area.left; x= src_area.right || - src_y < src_area.top || src_y >= src_area.bottom) - *src_color = 0; + if (src_pointf.X >= srcx && src_pointf.X < srcx + srcwidth && src_pointf.Y >= srcy && src_pointf.Y < srcy+srcheight) + *dst_color = resample_bitmap_pixel(&src_area, src_data, bitmap->width, bitmap->height, &src_pointf, imageAttributes, interpolation); else - GdipBitmapGetPixel(bitmap, src_x, src_y, src_color); + *dst_color = 0; } } GdipDeleteMatrix(dst_to_src); - if (imageAttributes) - { - if (imageAttributes->colorkeys[ColorAdjustTypeBitmap].enabled || - imageAttributes->colorkeys[ColorAdjustTypeDefault].enabled) - { - const struct color_key *key; - BYTE min_blue, min_green, min_red; - BYTE max_blue, max_green, max_red; - - if (imageAttributes->colorkeys[ColorAdjustTypeBitmap].enabled) - key = &imageAttributes->colorkeys[ColorAdjustTypeBitmap]; - else - key = &imageAttributes->colorkeys[ColorAdjustTypeDefault]; - - min_blue = key->low&0xff; - min_green = (key->low>>8)&0xff; - min_red = (key->low>>16)&0xff; - - max_blue = key->high&0xff; - max_green = (key->high>>8)&0xff; - max_red = (key->high>>16)&0xff; - - for (x=dst_area.left; x>8)&0xff; - red = (*src_color>>16)&0xff; - if (blue >= min_blue && green >= min_green && red >= min_red && - blue <= max_blue && green <= max_green && red <= max_red) - *src_color = 0x00000000; - } - } - - if (imageAttributes->colorremaptables[ColorAdjustTypeBitmap].enabled || - imageAttributes->colorremaptables[ColorAdjustTypeDefault].enabled) - { - const struct color_remap_table *table; - - if (imageAttributes->colorremaptables[ColorAdjustTypeBitmap].enabled) - table = &imageAttributes->colorremaptables[ColorAdjustTypeBitmap]; - else - table = &imageAttributes->colorremaptables[ColorAdjustTypeDefault]; - - for (x=dst_area.left; xmapsize; i++) - { - if (*src_color == table->colormap[i].oldColor.Argb) - { - *src_color = table->colormap[i].newColor.Argb; - break; - } - } - } - } - - if (imageAttributes->colormatrices[ColorAdjustTypeBitmap].enabled || - imageAttributes->colormatrices[ColorAdjustTypeDefault].enabled) - { - static int fixme; - if (!fixme++) - FIXME("Color transforms not implemented\n"); - } - - if (imageAttributes->gamma_enabled[ColorAdjustTypeBitmap] || - imageAttributes->gamma_enabled[ColorAdjustTypeDefault]) - { - static int fixme; - if (!fixme++) - FIXME("Gamma adjustment not implemented\n"); - } - } + GdipFree(src_data); stat = alpha_blend_pixels(graphics, dst_area.left, dst_area.top, - data, dst_area.right - dst_area.left, dst_area.bottom - dst_area.top, stride); + dst_data, dst_area.right - dst_area.left, dst_area.bottom - dst_area.top, dst_stride); - GdipFree(data); + GdipFree(dst_data); return stat; } @@ -2330,12 +2843,12 @@ GpStatus WINGDIPAPI GdipDrawImagePointsRect(GpGraphics *graphics, GpImage *image bf.AlphaFormat = AC_SRC_ALPHA; GdiAlphaBlend(graphics->hdc, pti[0].x, pti[0].y, pti[1].x-pti[0].x, pti[2].y-pti[0].y, - hdc, srcx*dx, srcy*dy, srcwidth*dx, srcheight*dy, bf); + hdc, srcx, srcy, srcwidth, srcheight, bf); } else { StretchBlt(graphics->hdc, pti[0].x, pti[0].y, pti[1].x-pti[0].x, pti[2].y-pti[0].y, - hdc, srcx*dx, srcy*dy, srcwidth*dx, srcheight*dy, SRCCOPY); + hdc, srcx, srcy, srcwidth, srcheight, SRCCOPY); } if (temp_hdc) @@ -2885,9 +3398,8 @@ GpStatus WINGDIPAPI GdipFillClosedCurveI(GpGraphics *graphics, GpBrush *brush, GpStatus WINGDIPAPI GdipFillEllipse(GpGraphics *graphics, GpBrush *brush, REAL x, REAL y, REAL width, REAL height) { - INT save_state; - GpPointF ptf[2]; - POINT pti[2]; + GpStatus stat; + GpPath *path; TRACE("(%p, %p, %.2f, %.2f, %.2f, %.2f)\n", graphics, brush, x, y, width, height); @@ -2897,31 +3409,19 @@ GpStatus WINGDIPAPI GdipFillEllipse(GpGraphics *graphics, GpBrush *brush, REAL x if(graphics->busy) return ObjectBusy; - if(!graphics->hdc) + stat = GdipCreatePath(FillModeAlternate, &path); + + if (stat == Ok) { - FIXME("graphics object has no HDC\n"); - return Ok; + stat = GdipAddPathEllipse(path, x, y, width, height); + + if (stat == Ok) + stat = GdipFillPath(graphics, brush, path); + + GdipDeletePath(path); } - ptf[0].X = x; - ptf[0].Y = y; - ptf[1].X = x + width; - ptf[1].Y = y + height; - - save_state = SaveDC(graphics->hdc); - EndPath(graphics->hdc); - - transform_and_round_points(graphics, pti, ptf, 2); - - BeginPath(graphics->hdc); - Ellipse(graphics->hdc, pti[0].x, pti[0].y, pti[1].x, pti[1].y); - EndPath(graphics->hdc); - - brush_fill_path(graphics, brush); - - RestoreDC(graphics->hdc, save_state); - - return Ok; + return stat; } GpStatus WINGDIPAPI GdipFillEllipseI(GpGraphics *graphics, GpBrush *brush, INT x, @@ -2932,24 +3432,13 @@ GpStatus WINGDIPAPI GdipFillEllipseI(GpGraphics *graphics, GpBrush *brush, INT x return GdipFillEllipse(graphics,brush,(REAL)x,(REAL)y,(REAL)width,(REAL)height); } -GpStatus WINGDIPAPI GdipFillPath(GpGraphics *graphics, GpBrush *brush, GpPath *path) +static GpStatus GDI32_GdipFillPath(GpGraphics *graphics, GpBrush *brush, GpPath *path) { INT save_state; GpStatus retval; - TRACE("(%p, %p, %p)\n", graphics, brush, path); - - if(!brush || !graphics || !path) - return InvalidParameter; - - if(graphics->busy) - return ObjectBusy; - - if(!graphics->hdc) - { - FIXME("graphics object has no HDC\n"); - return Ok; - } + if(!graphics->hdc || !brush_can_fill_path(brush)) + return NotImplemented; save_state = SaveDC(graphics->hdc); EndPath(graphics->hdc); @@ -2974,10 +3463,60 @@ end: return retval; } +static GpStatus SOFTWARE_GdipFillPath(GpGraphics *graphics, GpBrush *brush, GpPath *path) +{ + GpStatus stat; + GpRegion *rgn; + + if (!brush_can_fill_pixels(brush)) + return NotImplemented; + + /* FIXME: This could probably be done more efficiently without regions. */ + + stat = GdipCreateRegionPath(path, &rgn); + + if (stat == Ok) + { + stat = GdipFillRegion(graphics, brush, rgn); + + GdipDeleteRegion(rgn); + } + + return stat; +} + +GpStatus WINGDIPAPI GdipFillPath(GpGraphics *graphics, GpBrush *brush, GpPath *path) +{ + GpStatus stat = NotImplemented; + + TRACE("(%p, %p, %p)\n", graphics, brush, path); + + if(!brush || !graphics || !path) + return InvalidParameter; + + if(graphics->busy) + return ObjectBusy; + + if (!graphics->image) + stat = GDI32_GdipFillPath(graphics, brush, path); + + if (stat == NotImplemented) + stat = SOFTWARE_GdipFillPath(graphics, brush, path); + + if (stat == NotImplemented) + { + FIXME("Not implemented for brushtype %i\n", brush->bt); + stat = Ok; + } + + return stat; +} + GpStatus WINGDIPAPI GdipFillPie(GpGraphics *graphics, GpBrush *brush, REAL x, REAL y, REAL width, REAL height, REAL startAngle, REAL sweepAngle) { - INT save_state; + GpStatus stat; + GpPath *path; TRACE("(%p, %p, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f)\n", graphics, brush, x, y, width, height, startAngle, sweepAngle); @@ -2988,24 +3527,19 @@ GpStatus WINGDIPAPI GdipFillPie(GpGraphics *graphics, GpBrush *brush, REAL x, if(graphics->busy) return ObjectBusy; - if(!graphics->hdc) + stat = GdipCreatePath(FillModeAlternate, &path); + + if (stat == Ok) { - FIXME("graphics object has no HDC\n"); - return Ok; + stat = GdipAddPathPie(path, x, y, width, height, startAngle, sweepAngle); + + if (stat == Ok) + stat = GdipFillPath(graphics, brush, path); + + GdipDeletePath(path); } - save_state = SaveDC(graphics->hdc); - EndPath(graphics->hdc); - - BeginPath(graphics->hdc); - draw_pie(graphics, x, y, width, height, startAngle, sweepAngle); - EndPath(graphics->hdc); - - brush_fill_path(graphics, brush); - - RestoreDC(graphics->hdc, save_state); - - return Ok; + return stat; } GpStatus WINGDIPAPI GdipFillPieI(GpGraphics *graphics, GpBrush *brush, INT x, @@ -3020,10 +3554,8 @@ GpStatus WINGDIPAPI GdipFillPieI(GpGraphics *graphics, GpBrush *brush, INT x, GpStatus WINGDIPAPI GdipFillPolygon(GpGraphics *graphics, GpBrush *brush, GDIPCONST GpPointF *points, INT count, GpFillMode fillMode) { - INT save_state; - GpPointF *ptf = NULL; - POINT *pti = NULL; - GpStatus retval = Ok; + GpStatus stat; + GpPath *path; TRACE("(%p, %p, %p, %d, %d)\n", graphics, brush, points, count, fillMode); @@ -3033,50 +3565,26 @@ GpStatus WINGDIPAPI GdipFillPolygon(GpGraphics *graphics, GpBrush *brush, if(graphics->busy) return ObjectBusy; - if(!graphics->hdc) + stat = GdipCreatePath(fillMode, &path); + + if (stat == Ok) { - FIXME("graphics object has no HDC\n"); - return Ok; + stat = GdipAddPathPolygon(path, points, count); + + if (stat == Ok) + stat = GdipFillPath(graphics, brush, path); + + GdipDeletePath(path); } - ptf = GdipAlloc(count * sizeof(GpPointF)); - pti = GdipAlloc(count * sizeof(POINT)); - if(!ptf || !pti){ - retval = OutOfMemory; - goto end; - } - - memcpy(ptf, points, count * sizeof(GpPointF)); - - save_state = SaveDC(graphics->hdc); - EndPath(graphics->hdc); - SetPolyFillMode(graphics->hdc, (fillMode == FillModeAlternate ? ALTERNATE - : WINDING)); - - transform_and_round_points(graphics, pti, ptf, count); - - BeginPath(graphics->hdc); - Polygon(graphics->hdc, pti, count); - EndPath(graphics->hdc); - - brush_fill_path(graphics, brush); - - RestoreDC(graphics->hdc, save_state); - -end: - GdipFree(ptf); - GdipFree(pti); - - return retval; + return stat; } GpStatus WINGDIPAPI GdipFillPolygonI(GpGraphics *graphics, GpBrush *brush, GDIPCONST GpPoint *points, INT count, GpFillMode fillMode) { - INT save_state, i; - GpPointF *ptf = NULL; - POINT *pti = NULL; - GpStatus retval = Ok; + GpStatus stat; + GpPath *path; TRACE("(%p, %p, %p, %d, %d)\n", graphics, brush, points, count, fillMode); @@ -3086,44 +3594,19 @@ GpStatus WINGDIPAPI GdipFillPolygonI(GpGraphics *graphics, GpBrush *brush, if(graphics->busy) return ObjectBusy; - if(!graphics->hdc) + stat = GdipCreatePath(fillMode, &path); + + if (stat == Ok) { - FIXME("graphics object has no HDC\n"); - return Ok; + stat = GdipAddPathPolygonI(path, points, count); + + if (stat == Ok) + stat = GdipFillPath(graphics, brush, path); + + GdipDeletePath(path); } - ptf = GdipAlloc(count * sizeof(GpPointF)); - pti = GdipAlloc(count * sizeof(POINT)); - if(!ptf || !pti){ - retval = OutOfMemory; - goto end; - } - - for(i = 0; i < count; i ++){ - ptf[i].X = (REAL) points[i].X; - ptf[i].Y = (REAL) points[i].Y; - } - - save_state = SaveDC(graphics->hdc); - EndPath(graphics->hdc); - SetPolyFillMode(graphics->hdc, (fillMode == FillModeAlternate ? ALTERNATE - : WINDING)); - - transform_and_round_points(graphics, pti, ptf, count); - - BeginPath(graphics->hdc); - Polygon(graphics->hdc, pti, count); - EndPath(graphics->hdc); - - brush_fill_path(graphics, brush); - - RestoreDC(graphics->hdc, save_state); - -end: - GdipFree(ptf); - GdipFree(pti); - - return retval; + return stat; } GpStatus WINGDIPAPI GdipFillPolygon2(GpGraphics *graphics, GpBrush *brush, @@ -3145,9 +3628,8 @@ GpStatus WINGDIPAPI GdipFillPolygon2I(GpGraphics *graphics, GpBrush *brush, GpStatus WINGDIPAPI GdipFillRectangle(GpGraphics *graphics, GpBrush *brush, REAL x, REAL y, REAL width, REAL height) { - INT save_state; - GpPointF ptf[4]; - POINT pti[4]; + GpStatus stat; + GpPath *path; TRACE("(%p, %p, %.2f, %.2f, %.2f, %.2f)\n", graphics, brush, x, y, width, height); @@ -3157,81 +3639,27 @@ GpStatus WINGDIPAPI GdipFillRectangle(GpGraphics *graphics, GpBrush *brush, if(graphics->busy) return ObjectBusy; - if(!graphics->hdc) + stat = GdipCreatePath(FillModeAlternate, &path); + + if (stat == Ok) { - FIXME("graphics object has no HDC\n"); - return Ok; + stat = GdipAddPathRectangle(path, x, y, width, height); + + if (stat == Ok) + stat = GdipFillPath(graphics, brush, path); + + GdipDeletePath(path); } - ptf[0].X = x; - ptf[0].Y = y; - ptf[1].X = x + width; - ptf[1].Y = y; - ptf[2].X = x + width; - ptf[2].Y = y + height; - ptf[3].X = x; - ptf[3].Y = y + height; - - save_state = SaveDC(graphics->hdc); - EndPath(graphics->hdc); - - transform_and_round_points(graphics, pti, ptf, 4); - - BeginPath(graphics->hdc); - Polygon(graphics->hdc, pti, 4); - EndPath(graphics->hdc); - - brush_fill_path(graphics, brush); - - RestoreDC(graphics->hdc, save_state); - - return Ok; + return stat; } GpStatus WINGDIPAPI GdipFillRectangleI(GpGraphics *graphics, GpBrush *brush, INT x, INT y, INT width, INT height) { - INT save_state; - GpPointF ptf[4]; - POINT pti[4]; - TRACE("(%p, %p, %d, %d, %d, %d)\n", graphics, brush, x, y, width, height); - if(!graphics || !brush) - return InvalidParameter; - - if(graphics->busy) - return ObjectBusy; - - if(!graphics->hdc) - { - FIXME("graphics object has no HDC\n"); - return Ok; - } - - ptf[0].X = x; - ptf[0].Y = y; - ptf[1].X = x + width; - ptf[1].Y = y; - ptf[2].X = x + width; - ptf[2].Y = y + height; - ptf[3].X = x; - ptf[3].Y = y + height; - - save_state = SaveDC(graphics->hdc); - EndPath(graphics->hdc); - - transform_and_round_points(graphics, pti, ptf, 4); - - BeginPath(graphics->hdc); - Polygon(graphics->hdc, pti, 4); - EndPath(graphics->hdc); - - brush_fill_path(graphics, brush); - - RestoreDC(graphics->hdc, save_state); - - return Ok; + return GdipFillRectangle(graphics, brush, x, y, width, height); } GpStatus WINGDIPAPI GdipFillRectangles(GpGraphics *graphics, GpBrush *brush, GDIPCONST GpRectF *rects, @@ -3282,30 +3710,16 @@ GpStatus WINGDIPAPI GdipFillRectanglesI(GpGraphics *graphics, GpBrush *brush, GD return ret; } -/***************************************************************************** - * GdipFillRegion [GDIPLUS.@] - */ -GpStatus WINGDIPAPI GdipFillRegion(GpGraphics* graphics, GpBrush* brush, - GpRegion* region) +static GpStatus GDI32_GdipFillRegion(GpGraphics* graphics, GpBrush* brush, + GpRegion* region) { INT save_state; GpStatus status; HRGN hrgn; RECT rc; - TRACE("(%p, %p, %p)\n", graphics, brush, region); - - if (!(graphics && brush && region)) - return InvalidParameter; - - if(graphics->busy) - return ObjectBusy; - - if(!graphics->hdc) - { - FIXME("graphics object has no HDC\n"); - return Ok; - } + if(!graphics->hdc || !brush_can_fill_path(brush)) + return NotImplemented; status = GdipGetRegionHRgn(region, graphics, &hrgn); if(status != Ok) @@ -3332,6 +3746,197 @@ GpStatus WINGDIPAPI GdipFillRegion(GpGraphics* graphics, GpBrush* brush, return Ok; } +static GpStatus SOFTWARE_GdipFillRegion(GpGraphics *graphics, GpBrush *brush, + GpRegion* region) +{ + GpStatus stat; + GpRegion *temp_region; + GpMatrix *world_to_device, *identity; + GpRectF graphics_bounds; + UINT scans_count, i; + INT dummy; + GpRect *scans = NULL; + DWORD *pixel_data; + + if (!brush_can_fill_pixels(brush)) + return NotImplemented; + + stat = get_graphics_bounds(graphics, &graphics_bounds); + + if (stat == Ok) + stat = GdipCloneRegion(region, &temp_region); + + if (stat == Ok) + { + stat = get_graphics_transform(graphics, CoordinateSpaceDevice, + CoordinateSpaceWorld, &world_to_device); + + if (stat == Ok) + { + stat = GdipTransformRegion(temp_region, world_to_device); + + GdipDeleteMatrix(world_to_device); + } + + if (stat == Ok) + stat = GdipCombineRegionRect(temp_region, &graphics_bounds, CombineModeIntersect); + + if (stat == Ok) + stat = GdipCreateMatrix(&identity); + + if (stat == Ok) + { + stat = GdipGetRegionScansCount(temp_region, &scans_count, identity); + + if (stat == Ok && scans_count != 0) + { + scans = GdipAlloc(sizeof(*scans) * scans_count); + if (!scans) + stat = OutOfMemory; + + if (stat == Ok) + { + stat = GdipGetRegionScansI(temp_region, scans, &dummy, identity); + + if (stat != Ok) + GdipFree(scans); + } + } + + GdipDeleteMatrix(identity); + } + + GdipDeleteRegion(temp_region); + } + + if (stat == Ok && scans_count == 0) + return Ok; + + if (stat == Ok) + { + if (!graphics->image) + { + /* If we have to go through gdi32, use as few alpha blends as possible. */ + INT min_x, min_y, max_x, max_y; + UINT data_width, data_height; + + min_x = scans[0].X; + min_y = scans[0].Y; + max_x = scans[0].X+scans[0].Width; + max_y = scans[0].Y+scans[0].Height; + + for (i=1; i max_size) + max_size = size; + } + + pixel_data = GdipAlloc(sizeof(*pixel_data) * max_size); + if (!pixel_data) + stat = OutOfMemory; + + if (stat == Ok) + { + for (i=0; ibusy) + return ObjectBusy; + + if (!graphics->image) + stat = GDI32_GdipFillRegion(graphics, brush, region); + + if (stat == NotImplemented) + stat = SOFTWARE_GdipFillRegion(graphics, brush, region); + + if (stat == NotImplemented) + { + FIXME("not implemented for brushtype %i\n", brush->bt); + stat = Ok; + } + + return stat; +} + GpStatus WINGDIPAPI GdipFlush(GpGraphics *graphics, GpFlushIntention intention) { TRACE("(%p,%u)\n", graphics, intention); @@ -3725,12 +4330,7 @@ GpStatus WINGDIPAPI GdipIsVisibleRectI(GpGraphics *graphics, INT x, INT y, INT w return GdipIsVisibleRect(graphics, (REAL)x, (REAL)y, (REAL)width, (REAL)height, result); } -typedef GpStatus (*gdip_format_string_callback)(GpGraphics *graphics, - GDIPCONST WCHAR *string, INT index, INT length, GDIPCONST GpFont *font, - GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, - INT lineno, const RectF *bounds, void *user_data); - -static GpStatus gdip_format_string(GpGraphics *graphics, +GpStatus gdip_format_string(HDC hdc, GDIPCONST WCHAR *string, INT length, GDIPCONST GpFont *font, GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, gdip_format_string_callback callback, void *user_data) @@ -3752,7 +4352,7 @@ static GpStatus gdip_format_string(GpGraphics *graphics, nheight = roundr(rect->Height); if (rect->Width >= INT_MAX || rect->Width < 0.5) nwidth = INT_MAX; - if (rect->Height >= INT_MAX || rect->Width < 0.5) nheight = INT_MAX; + if (rect->Height >= INT_MAX || rect->Height < 0.5) nheight = INT_MAX; for(i = 0, j = 0; i < length; i++){ /* FIXME: This makes the indexes passed to callback inaccurate. */ @@ -3769,7 +4369,7 @@ static GpStatus gdip_format_string(GpGraphics *graphics, else halign = StringAlignmentNear; while(sum < length){ - GetTextExtentExPointW(graphics->hdc, stringdup + sum, length - sum, + GetTextExtentExPointW(hdc, stringdup + sum, length - sum, nwidth, &fit, NULL, &size); fitcpy = fit; @@ -3807,7 +4407,7 @@ static GpStatus gdip_format_string(GpGraphics *graphics, else lineend = fit; - GetTextExtentExPointW(graphics->hdc, stringdup + sum, lineend, + GetTextExtentExPointW(hdc, stringdup + sum, lineend, nwidth, &j, NULL, &size); bounds.Width = size.cx; @@ -3833,7 +4433,7 @@ static GpStatus gdip_format_string(GpGraphics *graphics, break; } - stat = callback(graphics, stringdup, sum, lineend, + stat = callback(hdc, stringdup, sum, lineend, font, rect, format, lineno, &bounds, user_data); if (stat != Ok) @@ -3860,7 +4460,7 @@ struct measure_ranges_args { GpRegion **regions; }; -static GpStatus measure_ranges_callback(GpGraphics *graphics, +static GpStatus measure_ranges_callback(HDC hdc, GDIPCONST WCHAR *string, INT index, INT length, GDIPCONST GpFont *font, GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, INT lineno, const RectF *bounds, void *user_data) @@ -3881,11 +4481,11 @@ static GpStatus measure_ranges_callback(GpGraphics *graphics, range_rect.Y = bounds->Y; range_rect.Height = bounds->Height; - GetTextExtentExPointW(graphics->hdc, string + index, range_start - index, + GetTextExtentExPointW(hdc, string + index, range_start - index, INT_MAX, NULL, NULL, &range_size); range_rect.X = bounds->X + range_size.cx; - GetTextExtentExPointW(graphics->hdc, string + index, range_end - index, + GetTextExtentExPointW(hdc, string + index, range_end - index, INT_MAX, NULL, NULL, &range_size); range_rect.Width = (bounds->X + range_size.cx) - range_rect.X; @@ -3907,7 +4507,7 @@ GpStatus WINGDIPAPI GdipMeasureCharacterRanges(GpGraphics* graphics, int i; HFONT oldfont; struct measure_ranges_args args; - HDC temp_hdc=NULL; + HDC hdc, temp_hdc=NULL; TRACE("(%p %s %d %p %s %p %d %p)\n", graphics, debugstr_w(string), length, font, debugstr_rectf(layoutRect), stringFormat, regionCount, regions); @@ -3920,14 +4520,16 @@ GpStatus WINGDIPAPI GdipMeasureCharacterRanges(GpGraphics* graphics, if(!graphics->hdc) { - temp_hdc = graphics->hdc = CreateCompatibleDC(0); + hdc = temp_hdc = CreateCompatibleDC(0); if (!temp_hdc) return OutOfMemory; } + else + hdc = graphics->hdc; if (stringFormat->attr) TRACE("may be ignoring some format flags: attr %x\n", stringFormat->attr); - oldfont = SelectObject(graphics->hdc, CreateFontIndirectW(&font->lfw)); + oldfont = SelectObject(hdc, CreateFontIndirectW(&font->lfw)); for (i=0; irange_count; i++) { @@ -3938,16 +4540,13 @@ GpStatus WINGDIPAPI GdipMeasureCharacterRanges(GpGraphics* graphics, args.regions = regions; - stat = gdip_format_string(graphics, string, length, font, layoutRect, stringFormat, + stat = gdip_format_string(hdc, string, length, font, layoutRect, stringFormat, measure_ranges_callback, &args); - DeleteObject(SelectObject(graphics->hdc, oldfont)); + DeleteObject(SelectObject(hdc, oldfont)); if (temp_hdc) - { - graphics->hdc = NULL; DeleteDC(temp_hdc); - } return stat; } @@ -3958,7 +4557,7 @@ struct measure_string_args { INT *linesfilled; }; -static GpStatus measure_string_callback(GpGraphics *graphics, +static GpStatus measure_string_callback(HDC hdc, GDIPCONST WCHAR *string, INT index, INT length, GDIPCONST GpFont *font, GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, INT lineno, const RectF *bounds, void *user_data) @@ -3991,7 +4590,7 @@ GpStatus WINGDIPAPI GdipMeasureString(GpGraphics *graphics, { HFONT oldfont; struct measure_string_args args; - HDC temp_hdc=NULL; + HDC temp_hdc=NULL, hdc; TRACE("(%p, %s, %i, %p, %s, %p, %p, %p, %p)\n", graphics, debugstr_wn(string, length), length, font, debugstr_rectf(rect), format, @@ -4002,9 +4601,11 @@ GpStatus WINGDIPAPI GdipMeasureString(GpGraphics *graphics, if(!graphics->hdc) { - temp_hdc = graphics->hdc = CreateCompatibleDC(0); + hdc = temp_hdc = CreateCompatibleDC(0); if (!temp_hdc) return OutOfMemory; } + else + hdc = graphics->hdc; if(linesfilled) *linesfilled = 0; if(codepointsfitted) *codepointsfitted = 0; @@ -4012,7 +4613,7 @@ GpStatus WINGDIPAPI GdipMeasureString(GpGraphics *graphics, if(format) TRACE("may be ignoring some format flags: attr %x\n", format->attr); - oldfont = SelectObject(graphics->hdc, CreateFontIndirectW(&font->lfw)); + oldfont = SelectObject(hdc, CreateFontIndirectW(&font->lfw)); bounds->X = rect->X; bounds->Y = rect->Y; @@ -4023,40 +4624,37 @@ GpStatus WINGDIPAPI GdipMeasureString(GpGraphics *graphics, args.codepointsfitted = codepointsfitted; args.linesfilled = linesfilled; - gdip_format_string(graphics, string, length, font, rect, format, + gdip_format_string(hdc, string, length, font, rect, format, measure_string_callback, &args); - DeleteObject(SelectObject(graphics->hdc, oldfont)); + DeleteObject(SelectObject(hdc, oldfont)); if (temp_hdc) - { - graphics->hdc = NULL; DeleteDC(temp_hdc); - } return Ok; } struct draw_string_args { - POINT drawbase; - UINT drawflags; - REAL ang_cos, ang_sin; + GpGraphics *graphics; + GDIPCONST GpBrush *brush; + REAL x, y, rel_width, rel_height, ascent; }; -static GpStatus draw_string_callback(GpGraphics *graphics, +static GpStatus draw_string_callback(HDC hdc, GDIPCONST WCHAR *string, INT index, INT length, GDIPCONST GpFont *font, GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, INT lineno, const RectF *bounds, void *user_data) { struct draw_string_args *args = user_data; - RECT drawcoord; + PointF position; - drawcoord.left = drawcoord.right = args->drawbase.x + roundr(args->ang_sin * bounds->Y); - drawcoord.top = drawcoord.bottom = args->drawbase.y + roundr(args->ang_cos * bounds->Y); + position.X = args->x + bounds->X / args->rel_width; + position.Y = args->y + bounds->Y / args->rel_height + args->ascent; - DrawTextW(graphics->hdc, string + index, length, &drawcoord, args->drawflags); - - return Ok; + return GdipDrawDriverString(args->graphics, &string[index], length, font, + args->brush, &position, + DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance, NULL); } GpStatus WINGDIPAPI GdipDrawString(GpGraphics *graphics, GDIPCONST WCHAR *string, @@ -4065,14 +4663,15 @@ GpStatus WINGDIPAPI GdipDrawString(GpGraphics *graphics, GDIPCONST WCHAR *string { HRGN rgn = NULL; HFONT gdifont; - LOGFONTW lfw; - TEXTMETRICW textmet; GpPointF pt[3], rectcpy[4]; POINT corners[4]; - REAL angle, rel_width, rel_height; - INT offsety = 0, save_state; + REAL rel_width, rel_height; + INT save_state; + REAL offsety = 0.0; struct draw_string_args args; RectF scaled_rect; + HDC hdc, temp_hdc=NULL; + TEXTMETRICW textmetric; TRACE("(%p, %s, %i, %p, %s, %p, %p)\n", graphics, debugstr_wn(string, length), length, font, debugstr_rectf(rect), format, brush); @@ -4080,15 +4679,13 @@ GpStatus WINGDIPAPI GdipDrawString(GpGraphics *graphics, GDIPCONST WCHAR *string if(!graphics || !string || !font || !brush || !rect) return InvalidParameter; - if((brush->bt != BrushTypeSolidColor)){ - FIXME("not implemented for given parameters\n"); - return NotImplemented; - } - - if(!graphics->hdc) + if(graphics->hdc) { - FIXME("graphics object has no HDC\n"); - return Ok; + hdc = graphics->hdc; + } + else + { + hdc = temp_hdc = CreateCompatibleDC(0); } if(format){ @@ -4107,9 +4704,7 @@ GpStatus WINGDIPAPI GdipDrawString(GpGraphics *graphics, GDIPCONST WCHAR *string } } - save_state = SaveDC(graphics->hdc); - SetBkMode(graphics->hdc, TRANSPARENT); - SetTextColor(graphics->hdc, brush->lb.lbColor); + save_state = SaveDC(hdc); pt[0].X = 0.0; pt[0].Y = 0.0; @@ -4118,9 +4713,6 @@ GpStatus WINGDIPAPI GdipDrawString(GpGraphics *graphics, GDIPCONST WCHAR *string pt[2].X = 0.0; pt[2].Y = 1.0; GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, pt, 3); - angle = -gdiplus_atan2((pt[1].Y - pt[0].Y), (pt[1].X - pt[0].X)); - args.ang_cos = cos(angle); - args.ang_sin = sin(angle); rel_width = sqrt((pt[1].Y-pt[0].Y)*(pt[1].Y-pt[0].Y)+ (pt[1].X-pt[0].X)*(pt[1].X-pt[0].X)); rel_height = sqrt((pt[2].Y-pt[0].Y)*(pt[2].Y-pt[0].Y)+ @@ -4141,49 +4733,33 @@ GpStatus WINGDIPAPI GdipDrawString(GpGraphics *graphics, GDIPCONST WCHAR *string { /* FIXME: If only the width or only the height is 0, we should probably still clip */ rgn = CreatePolygonRgn(corners, 4, ALTERNATE); - SelectClipRgn(graphics->hdc, rgn); + SelectClipRgn(hdc, rgn); } - /* Use gdi to find the font, then perform transformations on it (height, - * width, angle). */ - SelectObject(graphics->hdc, CreateFontIndirectW(&font->lfw)); - GetTextMetricsW(graphics->hdc, &textmet); - lfw = font->lfw; + get_font_hfont(graphics, font, &gdifont); + SelectObject(hdc, gdifont); - lfw.lfHeight = roundr(((REAL)lfw.lfHeight) * rel_height); - lfw.lfWidth = roundr(textmet.tmAveCharWidth * rel_width); + args.graphics = graphics; + args.brush = brush; - lfw.lfEscapement = lfw.lfOrientation = roundr((angle / M_PI) * 1800.0); + args.x = rect->X; + args.y = rect->Y + offsety; - gdifont = CreateFontIndirectW(&lfw); - DeleteObject(SelectObject(graphics->hdc, CreateFontIndirectW(&lfw))); + args.rel_width = rel_width; + args.rel_height = rel_height; - if (!format || format->align == StringAlignmentNear) - { - args.drawbase.x = corners[0].x; - args.drawbase.y = corners[0].y; - args.drawflags = DT_NOCLIP | DT_EXPANDTABS; - } - else if (format->align == StringAlignmentCenter) - { - args.drawbase.x = (corners[0].x + corners[1].x)/2; - args.drawbase.y = (corners[0].y + corners[1].y)/2; - args.drawflags = DT_NOCLIP | DT_EXPANDTABS | DT_CENTER; - } - else /* (format->align == StringAlignmentFar) */ - { - args.drawbase.x = corners[1].x; - args.drawbase.y = corners[1].y; - args.drawflags = DT_NOCLIP | DT_EXPANDTABS | DT_RIGHT; - } + GetTextMetricsW(hdc, &textmetric); + args.ascent = textmetric.tmAscent / rel_height; - gdip_format_string(graphics, string, length, font, &scaled_rect, format, + gdip_format_string(hdc, string, length, font, &scaled_rect, format, draw_string_callback, &args); DeleteObject(rgn); DeleteObject(gdifont); - RestoreDC(graphics->hdc, save_state); + RestoreDC(hdc, save_state); + + DeleteDC(temp_hdc); return Ok; } @@ -4383,12 +4959,18 @@ GpStatus WINGDIPAPI GdipSetInterpolationMode(GpGraphics *graphics, { TRACE("(%p, %d)\n", graphics, mode); - if(!graphics) + if(!graphics || mode == InterpolationModeInvalid || mode > InterpolationModeHighQualityBicubic) return InvalidParameter; if(graphics->busy) return ObjectBusy; + if (mode == InterpolationModeDefault || mode == InterpolationModeLowQuality) + mode = InterpolationModeBilinear; + + if (mode == InterpolationModeHighQuality) + mode = InterpolationModeHighQualityBicubic; + graphics->interpolation = mode; return Ok; @@ -4501,7 +5083,7 @@ GpStatus WINGDIPAPI GdipSetTextRenderingHint(GpGraphics *graphics, { TRACE("(%p, %d)\n", graphics, hint); - if(!graphics) + if(!graphics || hint > TextRenderingHintClearTypeGridFit) return InvalidParameter; if(graphics->busy) @@ -4761,6 +5343,8 @@ static const COLORREF DC_BACKGROUND_KEY = 0x0c0b0d; GpStatus WINGDIPAPI GdipGetDC(GpGraphics *graphics, HDC *hdc) { + GpStatus stat=Ok; + TRACE("(%p, %p)\n", graphics, hdc); if(!graphics || !hdc) @@ -4769,13 +5353,16 @@ GpStatus WINGDIPAPI GdipGetDC(GpGraphics *graphics, HDC *hdc) if(graphics->busy) return ObjectBusy; - if (!graphics->hdc || + if (graphics->image && graphics->image->type == ImageTypeMetafile) + { + stat = METAFILE_GetDC((GpMetafile*)graphics->image, hdc); + } + else if (!graphics->hdc || (graphics->image && graphics->image->type == ImageTypeBitmap && ((GpBitmap*)graphics->image)->format & PixelFormatAlpha)) { /* Create a fake HDC and fill it with a constant color. */ HDC temp_hdc; HBITMAP hbitmap; - GpStatus stat; GpRectF bounds; BITMAPINFOHEADER bmih; int i; @@ -4824,22 +5411,26 @@ GpStatus WINGDIPAPI GdipGetDC(GpGraphics *graphics, HDC *hdc) *hdc = graphics->hdc; } - graphics->busy = TRUE; + if (stat == Ok) + graphics->busy = TRUE; - return Ok; + return stat; } GpStatus WINGDIPAPI GdipReleaseDC(GpGraphics *graphics, HDC hdc) { + GpStatus stat=Ok; + TRACE("(%p, %p)\n", graphics, hdc); - if(!graphics || !hdc) + if(!graphics || !hdc || !graphics->busy) return InvalidParameter; - if((graphics->hdc != hdc && graphics->temp_hdc != hdc) || !(graphics->busy)) - return InvalidParameter; - - if (graphics->temp_hdc == hdc) + if (graphics->image && graphics->image->type == ImageTypeMetafile) + { + stat = METAFILE_ReleaseDC((GpMetafile*)graphics->image, hdc); + } + else if (graphics->temp_hdc == hdc) { DWORD* pos; int i; @@ -4866,10 +5457,15 @@ GpStatus WINGDIPAPI GdipReleaseDC(GpGraphics *graphics, HDC hdc) graphics->temp_hdc = NULL; graphics->temp_hbitmap = NULL; } + else if (hdc != graphics->hdc) + { + stat = InvalidParameter; + } - graphics->busy = FALSE; + if (stat == Ok) + graphics->busy = FALSE; - return Ok; + return stat; } GpStatus WINGDIPAPI GdipGetClip(GpGraphics *graphics, GpRegion *region) @@ -4896,25 +5492,13 @@ GpStatus WINGDIPAPI GdipGetClip(GpGraphics *graphics, GpRegion *region) return Ok; } -GpStatus WINGDIPAPI GdipTransformPoints(GpGraphics *graphics, GpCoordinateSpace dst_space, - GpCoordinateSpace src_space, GpPointF *points, INT count) +static GpStatus get_graphics_transform(GpGraphics *graphics, GpCoordinateSpace dst_space, + GpCoordinateSpace src_space, GpMatrix **matrix) { - GpMatrix *matrix; - GpStatus stat; + GpStatus stat = GdipCreateMatrix(matrix); REAL unitscale; - if(!graphics || !points || count <= 0) - return InvalidParameter; - - if(graphics->busy) - return ObjectBusy; - - TRACE("(%p, %d, %d, %p, %d)\n", graphics, dst_space, src_space, points, count); - - if (src_space == dst_space) return Ok; - - stat = GdipCreateMatrix(&matrix); - if (stat == Ok) + if (dst_space != src_space && stat == Ok) { unitscale = convert_unit(graphics_res(graphics), graphics->unit); @@ -4925,12 +5509,12 @@ GpStatus WINGDIPAPI GdipTransformPoints(GpGraphics *graphics, GpCoordinateSpace switch (src_space) { case CoordinateSpaceWorld: - GdipMultiplyMatrix(matrix, graphics->worldtrans, MatrixOrderAppend); + GdipMultiplyMatrix(*matrix, graphics->worldtrans, MatrixOrderAppend); break; case CoordinateSpacePage: break; case CoordinateSpaceDevice: - GdipScaleMatrix(matrix, 1.0/unitscale, 1.0/unitscale, MatrixOrderAppend); + GdipScaleMatrix(*matrix, 1.0/unitscale, 1.0/unitscale, MatrixOrderAppend); break; } @@ -4945,7 +5529,7 @@ GpStatus WINGDIPAPI GdipTransformPoints(GpGraphics *graphics, GpCoordinateSpace { stat = GdipInvertMatrix(inverted_transform); if (stat == Ok) - GdipMultiplyMatrix(matrix, inverted_transform, MatrixOrderAppend); + GdipMultiplyMatrix(*matrix, inverted_transform, MatrixOrderAppend); GdipDeleteMatrix(inverted_transform); } break; @@ -4953,12 +5537,34 @@ GpStatus WINGDIPAPI GdipTransformPoints(GpGraphics *graphics, GpCoordinateSpace case CoordinateSpacePage: break; case CoordinateSpaceDevice: - GdipScaleMatrix(matrix, unitscale, unitscale, MatrixOrderAppend); + GdipScaleMatrix(*matrix, unitscale, unitscale, MatrixOrderAppend); break; } + } + return stat; +} - if (stat == Ok) - stat = GdipTransformMatrixPoints(matrix, points, count); +GpStatus WINGDIPAPI GdipTransformPoints(GpGraphics *graphics, GpCoordinateSpace dst_space, + GpCoordinateSpace src_space, GpPointF *points, INT count) +{ + GpMatrix *matrix; + GpStatus stat; + + if(!graphics || !points || count <= 0) + return InvalidParameter; + + if(graphics->busy) + return ObjectBusy; + + TRACE("(%p, %d, %d, %p, %d)\n", graphics, dst_space, src_space, points, count); + + if (src_space == dst_space) return Ok; + + stat = get_graphics_transform(graphics, dst_space, src_space, &matrix); + + if (stat == Ok) + { + stat = GdipTransformMatrixPoints(matrix, points, count); GdipDeleteMatrix(matrix); } @@ -5051,8 +5657,347 @@ GpStatus WINGDIPAPI GdipMeasureDriverString(GpGraphics *graphics, GDIPCONST UINT GDIPCONST GpFont *font, GDIPCONST PointF *positions, INT flags, GDIPCONST GpMatrix *matrix, RectF *boundingBox) { - FIXME("(%p %p %d %p %p %d %p %p): stub\n", graphics, text, length, font, positions, flags, matrix, boundingBox); - return NotImplemented; + static const INT unsupported_flags = ~(DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance); + HFONT hfont; + HDC hdc; + REAL min_x, min_y, max_x, max_y, x, y; + int i; + TEXTMETRICW textmetric; + const WORD *glyph_indices; + WORD *dynamic_glyph_indices=NULL; + REAL rel_width, rel_height, ascent, descent; + GpPointF pt[3]; + + TRACE("(%p %p %d %p %p %d %p %p)\n", graphics, text, length, font, positions, flags, matrix, boundingBox); + + if (!graphics || !text || !font || !positions || !boundingBox) + return InvalidParameter; + + if (length == -1) + length = strlenW(text); + + if (length == 0) + { + boundingBox->X = 0.0; + boundingBox->Y = 0.0; + boundingBox->Width = 0.0; + boundingBox->Height = 0.0; + } + + if (flags & unsupported_flags) + FIXME("Ignoring flags %x\n", flags & unsupported_flags); + + if (matrix) + FIXME("Ignoring matrix\n"); + + get_font_hfont(graphics, font, &hfont); + + hdc = CreateCompatibleDC(0); + SelectObject(hdc, hfont); + + GetTextMetricsW(hdc, &textmetric); + + pt[0].X = 0.0; + pt[0].Y = 0.0; + pt[1].X = 1.0; + pt[1].Y = 0.0; + pt[2].X = 0.0; + pt[2].Y = 1.0; + GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, pt, 3); + rel_width = sqrt((pt[1].Y-pt[0].Y)*(pt[1].Y-pt[0].Y)+ + (pt[1].X-pt[0].X)*(pt[1].X-pt[0].X)); + rel_height = sqrt((pt[2].Y-pt[0].Y)*(pt[2].Y-pt[0].Y)+ + (pt[2].X-pt[0].X)*(pt[2].X-pt[0].X)); + + if (flags & DriverStringOptionsCmapLookup) + { + glyph_indices = dynamic_glyph_indices = GdipAlloc(sizeof(WORD) * length); + if (!glyph_indices) + { + DeleteDC(hdc); + DeleteObject(hfont); + return OutOfMemory; + } + + GetGlyphIndicesW(hdc, text, length, dynamic_glyph_indices, 0); + } + else + glyph_indices = text; + + min_x = max_x = x = positions[0].X; + min_y = max_y = y = positions[0].Y; + + ascent = textmetric.tmAscent / rel_height; + descent = textmetric.tmDescent / rel_height; + + for (i=0; i y - ascent) min_y = y - ascent; + if (max_y < y + descent) max_y = y + descent; + if (min_x > x) min_x = x; + + x += char_width / rel_width; + + if (max_x < x) max_x = x; + } + + GdipFree(dynamic_glyph_indices); + DeleteDC(hdc); + DeleteObject(hfont); + + boundingBox->X = min_x; + boundingBox->Y = min_y; + boundingBox->Width = max_x - min_x; + boundingBox->Height = max_y - min_y; + + return Ok; +} + +static GpStatus GDI32_GdipDrawDriverString(GpGraphics *graphics, GDIPCONST UINT16 *text, INT length, + GDIPCONST GpFont *font, GDIPCONST GpBrush *brush, + GDIPCONST PointF *positions, INT flags, + GDIPCONST GpMatrix *matrix ) +{ + static const INT unsupported_flags = ~(DriverStringOptionsRealizedAdvance|DriverStringOptionsCmapLookup); + INT save_state; + GpPointF pt; + HFONT hfont; + UINT eto_flags=0; + + if (flags & unsupported_flags) + FIXME("Ignoring flags %x\n", flags & unsupported_flags); + + if (matrix) + FIXME("Ignoring matrix\n"); + + if (!(flags & DriverStringOptionsCmapLookup)) + eto_flags |= ETO_GLYPH_INDEX; + + save_state = SaveDC(graphics->hdc); + SetBkMode(graphics->hdc, TRANSPARENT); + SetTextColor(graphics->hdc, brush->lb.lbColor); + + pt = positions[0]; + GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, &pt, 1); + + get_font_hfont(graphics, font, &hfont); + SelectObject(graphics->hdc, hfont); + + SetTextAlign(graphics->hdc, TA_BASELINE|TA_LEFT); + + ExtTextOutW(graphics->hdc, roundr(pt.X), roundr(pt.Y), eto_flags, NULL, text, length, NULL); + + RestoreDC(graphics->hdc, save_state); + + DeleteObject(hfont); + + return Ok; +} + +static GpStatus SOFTWARE_GdipDrawDriverString(GpGraphics *graphics, GDIPCONST UINT16 *text, INT length, + GDIPCONST GpFont *font, GDIPCONST GpBrush *brush, + GDIPCONST PointF *positions, INT flags, + GDIPCONST GpMatrix *matrix ) +{ + static const INT unsupported_flags = ~(DriverStringOptionsCmapLookup|DriverStringOptionsRealizedAdvance); + GpStatus stat; + PointF *real_positions, real_position; + POINT *pti; + HFONT hfont; + HDC hdc; + int min_x=INT_MAX, min_y=INT_MAX, max_x=INT_MIN, max_y=INT_MIN, i, x, y; + DWORD max_glyphsize=0; + GLYPHMETRICS glyphmetrics; + static const MAT2 identity = {{0,1}, {0,0}, {0,0}, {0,1}}; + BYTE *glyph_mask; + BYTE *text_mask; + int text_mask_stride; + BYTE *pixel_data; + int pixel_data_stride; + GpRect pixel_area; + UINT ggo_flags = GGO_GRAY8_BITMAP; + + if (length <= 0) + return Ok; + + if (!(flags & DriverStringOptionsCmapLookup)) + ggo_flags |= GGO_GLYPH_INDEX; + + if (flags & unsupported_flags) + FIXME("Ignoring flags %x\n", flags & unsupported_flags); + + if (matrix) + FIXME("Ignoring matrix\n"); + + pti = GdipAlloc(sizeof(POINT) * length); + if (!pti) + return OutOfMemory; + + if (flags & DriverStringOptionsRealizedAdvance) + { + real_position = positions[0]; + + transform_and_round_points(graphics, pti, &real_position, 1); + } + else + { + real_positions = GdipAlloc(sizeof(PointF) * length); + if (!real_positions) + { + GdipFree(pti); + return OutOfMemory; + } + + memcpy(real_positions, positions, sizeof(PointF) * length); + + transform_and_round_points(graphics, pti, real_positions, length); + + GdipFree(real_positions); + } + + get_font_hfont(graphics, font, &hfont); + + hdc = CreateCompatibleDC(0); + SelectObject(hdc, hfont); + + /* Get the boundaries of the text to be drawn */ + for (i=0; i max_glyphsize) + max_glyphsize = glyphsize; + + left = pti[i].x + glyphmetrics.gmptGlyphOrigin.x; + top = pti[i].y - glyphmetrics.gmptGlyphOrigin.y; + right = pti[i].x + glyphmetrics.gmptGlyphOrigin.x + glyphmetrics.gmBlackBoxX; + bottom = pti[i].y - glyphmetrics.gmptGlyphOrigin.y + glyphmetrics.gmBlackBoxY; + + if (left < min_x) min_x = left; + if (top < min_y) min_y = top; + if (right > max_x) max_x = right; + if (bottom > max_y) max_y = bottom; + + if (i+1 < length && (flags & DriverStringOptionsRealizedAdvance) == DriverStringOptionsRealizedAdvance) + { + pti[i+1].x = pti[i].x + glyphmetrics.gmCellIncX; + pti[i+1].y = pti[i].y + glyphmetrics.gmCellIncY; + } + } + + glyph_mask = GdipAlloc(max_glyphsize); + text_mask = GdipAlloc((max_x - min_x) * (max_y - min_y)); + text_mask_stride = max_x - min_x; + + if (!(glyph_mask && text_mask)) + { + GdipFree(glyph_mask); + GdipFree(text_mask); + GdipFree(pti); + DeleteDC(hdc); + DeleteObject(hfont); + return OutOfMemory; + } + + /* Generate a mask for the text */ + for (i=0; ihdc && + ((flags & DriverStringOptionsRealizedAdvance) || length <= 1) && + brush->bt == BrushTypeSolidColor && + (((GpSolidFill*)brush)->color & 0xff000000) == 0xff000000) + stat = GDI32_GdipDrawDriverString(graphics, text, length, font, brush, + positions, flags, matrix); + + if (stat == NotImplemented) + stat = SOFTWARE_GdipDrawDriverString(graphics, text, length, font, brush, + positions, flags, matrix); + + return stat; } GpStatus WINGDIPAPI GdipRecordMetafileStream(IStream *stream, HDC hdc, EmfType type, GDIPCONST GpRect *frameRect, diff --git a/reactos/dll/win32/gdiplus/graphicspath.c b/reactos/dll/win32/gdiplus/graphicspath.c index 983ead95008..120802cd287 100644 --- a/reactos/dll/win32/gdiplus/graphicspath.c +++ b/reactos/dll/win32/gdiplus/graphicspath.c @@ -384,8 +384,7 @@ GpStatus WINGDIPAPI GdipAddPathClosedCurve2(GpPath *path, GDIPCONST GpPointF *po /* close figure */ if(stat == Ok){ - INT count = path->pathdata.Count; - path->pathdata.Types[count - 1] |= PathPointTypeCloseSubpath; + path->pathdata.Types[path->pathdata.Count - 1] |= PathPointTypeCloseSubpath; path->newfigure = TRUE; } @@ -745,7 +744,7 @@ GpStatus WINGDIPAPI GdipAddPathPie(GpPath *path, REAL x, REAL y, REAL width, REA arc2polybezier(ptf, x, y, width, height, startAngle, sweepAngle); - status = GdipAddPathLine(path, (width - x)/2, (height - y)/2, ptf[0].X, ptf[0].Y); + status = GdipAddPathLine(path, x + width/2, y + height/2, ptf[0].X, ptf[0].Y); if(status != Ok){ GdipFree(ptf); return status; @@ -831,16 +830,187 @@ GpStatus WINGDIPAPI GdipAddPathPolygonI(GpPath *path, GDIPCONST GpPoint *points, return status; } +static float fromfixedpoint(const FIXED v) +{ + float f = ((float)v.fract) / (1<<(sizeof(v.fract)*8)); + f += v.value; + return f; +} + +struct format_string_args +{ + GpPath *path; + UINT maxY; +}; + +static GpStatus format_string_callback(HDC dc, + GDIPCONST WCHAR *string, INT index, INT length, GDIPCONST GpFont *font, + GDIPCONST RectF *rect, GDIPCONST GpStringFormat *format, + INT lineno, const RectF *bounds, void *priv) +{ + static const MAT2 identity = { {0,1}, {0,0}, {0,0}, {0,1} }; + struct format_string_args *args = priv; + GpPath *path = args->path; + GpStatus status = Ok; + float x = bounds->X; + float y = bounds->Y; + int i; + + for (i = index; i < length; ++i) + { + GLYPHMETRICS gm; + TTPOLYGONHEADER *ph = NULL; + char *start; + DWORD len, ofs = 0; + UINT bb_end; + len = GetGlyphOutlineW(dc, string[i], GGO_BEZIER, &gm, 0, NULL, &identity); + if (len == GDI_ERROR) + { + status = GenericError; + break; + } + ph = GdipAlloc(len); + start = (char *)ph; + if (!ph || !lengthen_path(path, len / sizeof(POINTFX))) + { + status = OutOfMemory; + break; + } + GetGlyphOutlineW(dc, string[i], GGO_BEZIER, &gm, len, start, &identity); + bb_end = gm.gmBlackBoxY + gm.gmptGlyphOrigin.y; + if (bb_end + y > args->maxY) + args->maxY = bb_end + y; + + ofs = 0; + while (ofs < len) + { + DWORD ofs_start = ofs; + ph = (TTPOLYGONHEADER*)&start[ofs]; + path->pathdata.Types[path->pathdata.Count] = PathPointTypeStart; + path->pathdata.Points[path->pathdata.Count].X = x + fromfixedpoint(ph->pfxStart.x); + path->pathdata.Points[path->pathdata.Count++].Y = y + bb_end - fromfixedpoint(ph->pfxStart.y); + TRACE("Starting at count %i with pos %f, %f)\n", path->pathdata.Count, x, y); + ofs += sizeof(*ph); + while (ofs - ofs_start < ph->cb) + { + TTPOLYCURVE *curve = (TTPOLYCURVE*)&start[ofs]; + int j; + ofs += sizeof(TTPOLYCURVE) + (curve->cpfx - 1) * sizeof(POINTFX); + + switch (curve->wType) + { + case TT_PRIM_LINE: + for (j = 0; j < curve->cpfx; ++j) + { + path->pathdata.Types[path->pathdata.Count] = PathPointTypeLine; + path->pathdata.Points[path->pathdata.Count].X = x + fromfixedpoint(curve->apfx[j].x); + path->pathdata.Points[path->pathdata.Count++].Y = y + bb_end - fromfixedpoint(curve->apfx[j].y); + } + break; + case TT_PRIM_CSPLINE: + for (j = 0; j < curve->cpfx; ++j) + { + path->pathdata.Types[path->pathdata.Count] = PathPointTypeBezier; + path->pathdata.Points[path->pathdata.Count].X = x + fromfixedpoint(curve->apfx[j].x); + path->pathdata.Points[path->pathdata.Count++].Y = y + bb_end - fromfixedpoint(curve->apfx[j].y); + } + break; + default: + ERR("Unhandled type: %u\n", curve->wType); + status = GenericError; + } + } + path->pathdata.Types[path->pathdata.Count - 1] |= PathPointTypeCloseSubpath; + } + path->newfigure = TRUE; + x += gm.gmCellIncX; + y += gm.gmCellIncY; + + GdipFree(ph); + if (status != Ok) + break; + } + + return status; +} + GpStatus WINGDIPAPI GdipAddPathString(GpPath* path, GDIPCONST WCHAR* string, INT length, GDIPCONST GpFontFamily* family, INT style, REAL emSize, GDIPCONST RectF* layoutRect, GDIPCONST GpStringFormat* format) { - FIXME("(%p, %p, %d, %p, %d, %f, %p, %p): stub\n", path, string, length, family, style, emSize, layoutRect, format); - return NotImplemented; + GpFont *font; + GpStatus status; + HANDLE hfont; + HDC dc; + GpPath *backup; + struct format_string_args args; + int i; + + FIXME("(%p, %s, %d, %p, %d, %f, %p, %p): stub\n", path, debugstr_w(string), length, family, style, emSize, layoutRect, format); + if (!path || !string || !family || !emSize || !layoutRect || !format) + return InvalidParameter; + + status = GdipCreateFont(family, emSize, style, UnitPixel, &font); + if (status != Ok) + return status; + + hfont = CreateFontIndirectW(&font->lfw); + if (!hfont) + { + WARN("Failed to create font\n"); + return GenericError; + } + + if ((status = GdipClonePath(path, &backup)) != Ok) + { + DeleteObject(hfont); + return status; + } + + dc = CreateCompatibleDC(0); + SelectObject(dc, hfont); + + args.path = path; + args.maxY = 0; + status = gdip_format_string(dc, string, length, NULL, layoutRect, format, format_string_callback, &args); + + DeleteDC(dc); + DeleteObject(hfont); + + if (status != Ok) /* free backup */ + { + GdipFree(path->pathdata.Points); + GdipFree(path->pathdata.Types); + *path = *backup; + GdipFree(backup); + return status; + } + if (format && format->vertalign == StringAlignmentCenter && layoutRect->Y + args.maxY < layoutRect->Height) + { + float inc = layoutRect->Height - args.maxY - layoutRect->Y; + inc /= 2; + for (i = backup->pathdata.Count; i < path->pathdata.Count; ++i) + path->pathdata.Points[i].Y += inc; + } else if (format && format->vertalign == StringAlignmentFar) { + float inc = layoutRect->Height - args.maxY - layoutRect->Y; + for (i = backup->pathdata.Count; i < path->pathdata.Count; ++i) + path->pathdata.Points[i].Y += inc; + } + GdipDeletePath(backup); + return status; } GpStatus WINGDIPAPI GdipAddPathStringI(GpPath* path, GDIPCONST WCHAR* string, INT length, GDIPCONST GpFontFamily* family, INT style, REAL emSize, GDIPCONST Rect* layoutRect, GDIPCONST GpStringFormat* format) { - FIXME("(%p, %p, %d, %p, %d, %f, %p, %p): stub\n", path, string, length, family, style, emSize, layoutRect, format); - return NotImplemented; + if (layoutRect) + { + RectF layoutRectF = { + (REAL)layoutRect->X, + (REAL)layoutRect->Y, + (REAL)layoutRect->Width, + (REAL)layoutRect->Height + }; + return GdipAddPathString(path, string, length, family, style, emSize, &layoutRectF, format); + } + return InvalidParameter; } GpStatus WINGDIPAPI GdipClonePath(GpPath* path, GpPath **clone) @@ -1507,7 +1677,7 @@ GpStatus WINGDIPAPI GdipAddPathRectangle(GpPath *path, REAL x, REAL y, TRACE("(%p, %.2f, %.2f, %.2f, %.2f)\n", path, x, y, width, height); - if(!path || width < 0.0 || height < 0.0) + if(!path) return InvalidParameter; /* make a backup copy of path data */ @@ -1536,9 +1706,10 @@ GpStatus WINGDIPAPI GdipAddPathRectangle(GpPath *path, REAL x, REAL y, fail: /* reverting */ - GdipDeletePath(path); - GdipClonePath(backup, &path); - GdipDeletePath(backup); + GdipFree(path->pathdata.Points); + GdipFree(path->pathdata.Types); + memcpy(path, backup, sizeof(*path)); + GdipFree(backup); return retstat; } @@ -1581,9 +1752,10 @@ GpStatus WINGDIPAPI GdipAddPathRectangles(GpPath *path, GDIPCONST GpRectF *rects fail: /* reverting */ - GdipDeletePath(path); - GdipClonePath(backup, &path); - GdipDeletePath(backup); + GdipFree(path->pathdata.Points); + GdipFree(path->pathdata.Types); + memcpy(path, backup, sizeof(*path)); + GdipFree(backup); return retstat; } diff --git a/reactos/dll/win32/gdiplus/image.c b/reactos/dll/win32/gdiplus/image.c index 69f58659a28..aba83669196 100644 --- a/reactos/dll/win32/gdiplus/image.c +++ b/reactos/dll/win32/gdiplus/image.c @@ -296,6 +296,53 @@ GpStatus WINGDIPAPI GdipBitmapGetPixel(GpBitmap* bitmap, INT x, INT y, return Ok; } +static inline UINT get_palette_index(BYTE r, BYTE g, BYTE b, BYTE a, GpBitmap* bitmap) { + BYTE index = 0; + int best_distance = 0x7fff; + int distance; + int i; + /* This algorithm scans entire palette, + computes difference from desired color (all color components have equal weight) + and returns the index of color with least difference. + + Note: Maybe it could be replaced with a better algorithm for better image quality + and performance, though better algorithm would probably need some pre-built lookup + tables and thus may actually be slower if this method is called only few times per + every image. + */ + for(i=0;iimage.palette_size;i++) { + ARGB color=bitmap->image.palette_entries[i]; + distance=abs(b-(color & 0xff)) + abs(g-(color>>8 & 0xff)) + abs(r-(color>>16 & 0xff)) + abs(a-(color>>24 & 0xff)); + if (distanceformat); return NotImplemented; @@ -442,11 +498,11 @@ GpStatus WINGDIPAPI GdipBitmapSetPixel(GpBitmap* bitmap, INT x, INT y, return Ok; } -GpStatus convert_pixels(UINT width, UINT height, +GpStatus convert_pixels(INT width, INT height, INT dst_stride, BYTE *dst_bits, PixelFormat dst_format, INT src_stride, const BYTE *src_bits, PixelFormat src_format, ARGB *src_palette) { - UINT x, y; + INT x, y; if (src_format == dst_format || (dst_format == PixelFormat32bppRGB && PIXELFORMATBPP(src_format) == 32)) @@ -857,9 +913,7 @@ GpStatus convert_pixels(UINT width, UINT height, GpStatus WINGDIPAPI GdipBitmapLockBits(GpBitmap* bitmap, GDIPCONST GpRect* rect, UINT flags, PixelFormat format, BitmapData* lockeddata) { - INT stride, bitspp = PIXELFORMATBPP(format); - BYTE *buff = NULL; - UINT abs_height; + INT bitspp = PIXELFORMATBPP(format); GpRect act_rect; /* actual rect to be used */ GpStatus stat; @@ -881,20 +935,13 @@ GpStatus WINGDIPAPI GdipBitmapLockBits(GpBitmap* bitmap, GDIPCONST GpRect* rect, act_rect.Height = bitmap->height; } - if(flags & ImageLockModeUserInputBuf) - { - static int fixme=0; - if (!fixme++) FIXME("ImageLockModeUserInputBuf not implemented\n"); - return NotImplemented; - } - if(bitmap->lockmode) { WARN("bitmap is already locked and cannot be locked again\n"); return WrongState; } - if (bitmap->bits && bitmap->format == format) + if (bitmap->bits && bitmap->format == format && !(flags & ImageLockModeUserInputBuf)) { /* no conversion is necessary; just use the bits directly */ lockeddata->Width = act_rect.Width; @@ -912,11 +959,14 @@ GpStatus WINGDIPAPI GdipBitmapLockBits(GpBitmap* bitmap, GDIPCONST GpRect* rect, } /* Make sure we can convert to the requested format. */ - stat = convert_pixels(0, 0, 0, NULL, format, 0, NULL, bitmap->format, NULL); - if (stat == NotImplemented) + if (flags & ImageLockModeRead) { - FIXME("cannot read bitmap from %x to %x\n", bitmap->format, format); - return NotImplemented; + stat = convert_pixels(0, 0, 0, NULL, format, 0, NULL, bitmap->format, NULL); + if (stat == NotImplemented) + { + FIXME("cannot read bitmap from %x to %x\n", bitmap->format, format); + return NotImplemented; + } } /* If we're opening for writing, make sure we'll be able to write back in @@ -931,34 +981,50 @@ GpStatus WINGDIPAPI GdipBitmapLockBits(GpBitmap* bitmap, GDIPCONST GpRect* rect, } } - abs_height = bitmap->height; - stride = (bitmap->width * bitspp + 7) / 8; - stride = (stride + 3) & ~3; - - buff = GdipAlloc(stride * abs_height); - - if (!buff) return OutOfMemory; - - stat = convert_pixels(bitmap->width, bitmap->height, - stride, buff, format, - bitmap->stride, bitmap->bits, bitmap->format, bitmap->image.palette_entries); - - if (stat != Ok) - { - GdipFree(buff); - return stat; - } - lockeddata->Width = act_rect.Width; lockeddata->Height = act_rect.Height; lockeddata->PixelFormat = format; lockeddata->Reserved = flags; - lockeddata->Stride = stride; - lockeddata->Scan0 = buff + (bitspp / 8) * act_rect.X + stride * act_rect.Y; + + if(!(flags & ImageLockModeUserInputBuf)) + { + lockeddata->Stride = (((act_rect.Width * bitspp + 7) / 8) + 3) & ~3; + + bitmap->bitmapbits = GdipAlloc(lockeddata->Stride * act_rect.Height); + + if (!bitmap->bitmapbits) return OutOfMemory; + + lockeddata->Scan0 = bitmap->bitmapbits; + } + + if (flags & ImageLockModeRead) + { + static int fixme=0; + + if (!fixme && (PIXELFORMATBPP(bitmap->format) * act_rect.X) % 8 != 0) + { + FIXME("Cannot copy rows that don't start at a whole byte.\n"); + fixme = 1; + } + + stat = convert_pixels(act_rect.Width, act_rect.Height, + lockeddata->Stride, lockeddata->Scan0, format, + bitmap->stride, + bitmap->bits + bitmap->stride * act_rect.Y + PIXELFORMATBPP(bitmap->format) * act_rect.X / 8, + bitmap->format, bitmap->image.palette_entries); + + if (stat != Ok) + { + GdipFree(bitmap->bitmapbits); + bitmap->bitmapbits = NULL; + return stat; + } + } bitmap->lockmode = flags; bitmap->numlocks++; - bitmap->bitmapbits = buff; + bitmap->lockx = act_rect.X; + bitmap->locky = act_rect.Y; return Ok; } @@ -980,6 +1046,7 @@ GpStatus WINGDIPAPI GdipBitmapUnlockBits(GpBitmap* bitmap, BitmapData* lockeddata) { GpStatus stat; + static int fixme=0; TRACE("(%p,%p)\n", bitmap, lockeddata); @@ -989,10 +1056,7 @@ GpStatus WINGDIPAPI GdipBitmapUnlockBits(GpBitmap* bitmap, if(!bitmap->lockmode) return WrongState; - if(lockeddata->Reserved & ImageLockModeUserInputBuf) - return NotImplemented; - - if(lockeddata->Reserved & ImageLockModeRead){ + if(!(lockeddata->Reserved & ImageLockModeWrite)){ if(!(--bitmap->numlocks)) bitmap->lockmode = 0; @@ -1001,7 +1065,7 @@ GpStatus WINGDIPAPI GdipBitmapUnlockBits(GpBitmap* bitmap, return Ok; } - if (!bitmap->bitmapbits) + if (!bitmap->bitmapbits && !(lockeddata->Reserved & ImageLockModeUserInputBuf)) { /* we passed a direct reference; no need to do anything */ bitmap->lockmode = 0; @@ -1009,9 +1073,17 @@ GpStatus WINGDIPAPI GdipBitmapUnlockBits(GpBitmap* bitmap, return Ok; } - stat = convert_pixels(bitmap->width, bitmap->height, - bitmap->stride, bitmap->bits, bitmap->format, - lockeddata->Stride, bitmap->bitmapbits, lockeddata->PixelFormat, NULL); + if (!fixme && (PIXELFORMATBPP(bitmap->format) * bitmap->lockx) % 8 != 0) + { + FIXME("Cannot copy rows that don't start at a whole byte.\n"); + fixme = 1; + } + + stat = convert_pixels(lockeddata->Width, lockeddata->Height, + bitmap->stride, + bitmap->bits + bitmap->stride * bitmap->locky + PIXELFORMATBPP(bitmap->format) * bitmap->lockx / 8, + bitmap->format, + lockeddata->Stride, lockeddata->Scan0, lockeddata->PixelFormat, NULL); if (stat != Ok) { @@ -1298,12 +1370,12 @@ GpStatus WINGDIPAPI GdipCreateHBITMAPFromBitmap(GpBitmap* bitmap, HBITMAP* hbmReturn, ARGB background) { GpStatus stat; - HBITMAP result, oldbitmap; + HBITMAP result; UINT width, height; HDC hdc; - GpGraphics *graphics; BITMAPINFOHEADER bih; - void *bits; + LPBYTE bits; + BitmapData lockeddata; TRACE("(%p,%p,%x)\n", bitmap, hbmReturn, background); if (!bitmap || !hbmReturn) return InvalidParameter; @@ -1326,25 +1398,19 @@ GpStatus WINGDIPAPI GdipCreateHBITMAPFromBitmap(GpBitmap* bitmap, hdc = CreateCompatibleDC(NULL); if (!hdc) return GenericError; - result = CreateDIBSection(hdc, (BITMAPINFO*)&bih, DIB_RGB_COLORS, &bits, + result = CreateDIBSection(hdc, (BITMAPINFO*)&bih, DIB_RGB_COLORS, (void**)&bits, NULL, 0); if (result) { - oldbitmap = SelectObject(hdc, result); + lockeddata.Stride = -width * 4; + lockeddata.Scan0 = bits + (width * 4 * (height - 1)); + + stat = GdipBitmapLockBits(bitmap, NULL, ImageLockModeRead|ImageLockModeUserInputBuf, + PixelFormat32bppPARGB, &lockeddata); - stat = GdipCreateFromHDC(hdc, &graphics); if (stat == Ok) - { - stat = GdipGraphicsClear(graphics, background); - - if (stat == Ok) - stat = GdipDrawImage(graphics, (GpImage*)bitmap, 0, 0); - - GdipDeleteGraphics(graphics); - } - - SelectObject(hdc, oldbitmap); + stat = GdipBitmapUnlockBits(bitmap, &lockeddata); } else stat = GenericError; @@ -1955,7 +2021,21 @@ GpStatus WINGDIPAPI GdipDisposeImage(GpImage *image) DeleteDC(((GpBitmap*)image)->hdc); DeleteObject(((GpBitmap*)image)->hbitmap); } - else if (image->type != ImageTypeMetafile) + else if (image->type == ImageTypeMetafile) + { + GpMetafile *metafile = (GpMetafile*)image; + GdipFree(metafile->comment_data); + DeleteEnhMetaFile(CloseEnhMetaFile(metafile->record_dc)); + DeleteEnhMetaFile(metafile->hemf); + if (metafile->record_graphics) + { + WARN("metafile closed while recording\n"); + /* not sure what to do here; for now just prevent the graphics from functioning or using this object */ + metafile->record_graphics->image = NULL; + metafile->record_graphics->busy = TRUE; + } + } + else { WARN("invalid image: %p\n", image); return ObjectBusy; @@ -2071,12 +2151,7 @@ GpStatus WINGDIPAPI GdipGetImageGraphicsContext(GpImage *image, if(!image || !graphics) return InvalidParameter; - if(image->type != ImageTypeBitmap){ - FIXME("not implemented for image type %d\n", image->type); - return NotImplemented; - } - - if (((GpBitmap*)image)->hbitmap) + if (image->type == ImageTypeBitmap && ((GpBitmap*)image)->hbitmap) { hdc = ((GpBitmap*)image)->hdc; @@ -2091,6 +2166,8 @@ GpStatus WINGDIPAPI GdipGetImageGraphicsContext(GpImage *image, if (stat == Ok) (*graphics)->image = image; } + else if (image->type == ImageTypeMetafile) + stat = METAFILE_GetGraphicsContext((GpMetafile*)image, graphics); else stat = graphics_from_image(image, graphics); @@ -2322,7 +2399,8 @@ GpStatus WINGDIPAPI GdipGetPropertyCount(GpImage *image, UINT* num) if(!(calls++)) FIXME("not implemented\n"); - return InvalidParameter; + *num = 0; + return Ok; } GpStatus WINGDIPAPI GdipGetPropertyIdList(GpImage *image, UINT num, PROPID* list) @@ -2384,7 +2462,7 @@ struct image_format_dimension const GUID *dimension; }; -struct image_format_dimension image_format_dimensions[] = +static struct image_format_dimension image_format_dimensions[] = { {&ImageFormatGIF, &FrameDimensionTime}, {&ImageFormatIcon, &FrameDimensionResolution}, @@ -3013,6 +3091,12 @@ static GpStatus encode_image_BMP(GpImage *image, IStream* stream, return encode_image_WIC(image, stream, &CLSID_WICBmpEncoder, params); } +static GpStatus encode_image_tiff(GpImage *image, IStream* stream, + GDIPCONST CLSID* clsid, GDIPCONST EncoderParameters* params) +{ + return encode_image_WIC(image, stream, &CLSID_WICTiffEncoder, params); +} + static GpStatus encode_image_png(GpImage *image, IStream* stream, GDIPCONST CLSID* clsid, GDIPCONST EncoderParameters* params) { @@ -3231,14 +3315,14 @@ static const struct image_codec codecs[NUM_CODECS] = { /* FormatDescription */ tiff_format, /* FilenameExtension */ tiff_extension, /* MimeType */ tiff_mimetype, - /* Flags */ ImageCodecFlagsDecoder | ImageCodecFlagsSupportBitmap | ImageCodecFlagsBuiltin, + /* Flags */ ImageCodecFlagsDecoder | ImageCodecFlagsEncoder | ImageCodecFlagsSupportBitmap | ImageCodecFlagsBuiltin, /* Version */ 1, /* SigCount */ 2, /* SigSize */ 4, /* SigPattern */ tiff_sig_pattern, /* SigMask */ tiff_sig_mask, }, - NULL, + encode_image_tiff, decode_image_tiff }, { @@ -3442,6 +3526,7 @@ GpStatus WINGDIPAPI GdipGetEncoderParameterListSize(GpImage *image, GpStatus WINGDIPAPI GdipCreateBitmapFromHBITMAP(HBITMAP hbm, HPALETTE hpal, GpBitmap** bitmap) { BITMAP bm; + DIBSECTION dib; GpStatus retval; PixelFormat format; BitmapData lockeddata; @@ -3452,12 +3537,6 @@ GpStatus WINGDIPAPI GdipCreateBitmapFromHBITMAP(HBITMAP hbm, HPALETTE hpal, GpBi if(!hbm || !bitmap) return InvalidParameter; - /* TODO: Support for device-dependent bitmaps */ - if(hpal){ - FIXME("no support for device-dependent bitmaps\n"); - return NotImplemented; - } - if (GetObjectA(hbm, sizeof(bm), &bm) != sizeof(bm)) return InvalidParameter; @@ -3472,6 +3551,36 @@ GpStatus WINGDIPAPI GdipCreateBitmapFromHBITMAP(HBITMAP hbm, HPALETTE hpal, GpBi case 8: format = PixelFormat8bppIndexed; break; + case 16: + { + if (GetObjectA(hbm, sizeof(dib), &dib) == sizeof(dib)) + { + if (dib.dsBitfields[0] == 0x7c00 && + dib.dsBitfields[1] == 0x3e0 && + dib.dsBitfields[2] == 0x1f) + { + format = PixelFormat16bppRGB555; + } + else if (dib.dsBitfields[0] == 0xf800 && + dib.dsBitfields[1] == 0x7e0 && + dib.dsBitfields[2] == 0x1f) + { + format = PixelFormat16bppRGB565; + } + else + { + FIXME("unrecognized bitfields %x,%x,%x\n", dib.dsBitfields[0], + dib.dsBitfields[1], dib.dsBitfields[2]); + return InvalidParameter; + } + } + else + { + FIXME("unimplemented for 16-bit ddb\n"); + return InvalidParameter; + } + break; + } case 24: format = PixelFormat24bppRGB; break; @@ -3554,6 +3663,56 @@ GpStatus WINGDIPAPI GdipCreateBitmapFromHBITMAP(HBITMAP hbm, HPALETTE hpal, GpBi GdipBitmapUnlockBits(*bitmap, &lockeddata); } + + if (retval == Ok && hpal) + { + WORD num_palette_entries; + PALETTEENTRY *palette_entries=NULL; + ColorPalette *palette=NULL; + int i; + + if (!GetObjectW(hpal, sizeof(num_palette_entries), &num_palette_entries)) + retval = GenericError; + + if (retval == Ok) + { + palette_entries = GdipAlloc(sizeof(PALETTEENTRY) * num_palette_entries); + palette = GdipAlloc(sizeof(ColorPalette) + sizeof(ARGB) * (num_palette_entries-1)); + + if (!palette_entries || !palette) + retval = OutOfMemory; + } + + if (retval == Ok) + { + if (!GetPaletteEntries(hpal, 0, num_palette_entries, palette_entries)) + retval = GenericError; + } + + if (retval == Ok) + { + palette->Flags = 0; + palette->Count = num_palette_entries; + + for (i=0; iEntries[i] = 0xff000000 | entry->peRed << 16 | + entry->peGreen << 8 | entry->peBlue; + } + + retval = GdipSetImagePalette((GpImage*)*bitmap, palette); + } + + GdipFree(palette_entries); + GdipFree(palette); + } + + if (retval != Ok) + { + GdipDisposeImage((GpImage*)*bitmap); + *bitmap = NULL; + } } return retval; diff --git a/reactos/dll/win32/gdiplus/matrix.c b/reactos/dll/win32/gdiplus/matrix.c index a6724d31304..acfe98946e4 100644 --- a/reactos/dll/win32/gdiplus/matrix.c +++ b/reactos/dll/win32/gdiplus/matrix.c @@ -85,27 +85,28 @@ GpStatus WINGDIPAPI GdipCreateMatrix2(REAL m11, REAL m12, REAL m21, REAL m22, GpStatus WINGDIPAPI GdipCreateMatrix3(GDIPCONST GpRectF *rect, GDIPCONST GpPointF *pt, GpMatrix **matrix) { + REAL m11, m12, m21, m22, dx, dy; TRACE("(%p, %p, %p)\n", rect, pt, matrix); if(!matrix || !pt) return InvalidParameter; - *matrix = GdipAlloc(sizeof(GpMatrix)); - if(!*matrix) return OutOfMemory; + m11 = (pt[1].X - pt[0].X) / rect->Width; + m21 = (pt[2].X - pt[0].X) / rect->Height; + dx = pt[0].X - m11 * rect->X - m21 * rect->Y; + m12 = (pt[1].Y - pt[0].Y) / rect->Width; + m22 = (pt[2].Y - pt[0].Y) / rect->Height; + dy = pt[0].Y - m12 * rect->X - m22 * rect->Y; - memcpy((*matrix)->matrix, rect, 4 * sizeof(REAL)); - - (*matrix)->matrix[4] = pt->X; - (*matrix)->matrix[5] = pt->Y; - - return Ok; + return GdipCreateMatrix2(m11, m12, m21, m22, dx, dy, matrix); } GpStatus WINGDIPAPI GdipCreateMatrix3I(GDIPCONST GpRect *rect, GDIPCONST GpPoint *pt, GpMatrix **matrix) { GpRectF rectF; - GpPointF ptF; + GpPointF ptF[3]; + int i; TRACE("(%p, %p, %p)\n", rect, pt, matrix); @@ -114,10 +115,11 @@ GpStatus WINGDIPAPI GdipCreateMatrix3I(GDIPCONST GpRect *rect, GDIPCONST GpPoint rectF.Width = (REAL)rect->Width; rectF.Height = (REAL)rect->Height; - ptF.X = (REAL)pt->X; - ptF.Y = (REAL)pt->Y; - - return GdipCreateMatrix3(&rectF, &ptF, matrix); + for (i = 0; i < 3; i++) { + ptF[i].X = (REAL)pt[i].X; + ptF[i].Y = (REAL)pt[i].Y; + } + return GdipCreateMatrix3(&rectF, ptF, matrix); } GpStatus WINGDIPAPI GdipCloneMatrix(GpMatrix *matrix, GpMatrix **clone) @@ -231,8 +233,10 @@ GpStatus WINGDIPAPI GdipMultiplyMatrix(GpMatrix *matrix, GDIPCONST GpMatrix* mat if(order == MatrixOrderAppend) matrix_multiply(matrix->matrix, matrix2->matrix, matrix->matrix); - else + else if (order == MatrixOrderPrepend) matrix_multiply(matrix2->matrix, matrix->matrix, matrix->matrix); + else + return InvalidParameter; return Ok; } @@ -260,8 +264,10 @@ GpStatus WINGDIPAPI GdipRotateMatrix(GpMatrix *matrix, REAL angle, if(order == MatrixOrderAppend) matrix_multiply(matrix->matrix, rotate, matrix->matrix); - else + else if (order == MatrixOrderPrepend) matrix_multiply(rotate, matrix->matrix, matrix->matrix); + else + return InvalidParameter; return Ok; } @@ -285,8 +291,10 @@ GpStatus WINGDIPAPI GdipScaleMatrix(GpMatrix *matrix, REAL scaleX, REAL scaleY, if(order == MatrixOrderAppend) matrix_multiply(matrix->matrix, scale, matrix->matrix); - else + else if (order == MatrixOrderPrepend) matrix_multiply(scale, matrix->matrix, matrix->matrix); + else + return InvalidParameter; return Ok; } @@ -330,8 +338,10 @@ GpStatus WINGDIPAPI GdipShearMatrix(GpMatrix *matrix, REAL shearX, REAL shearY, if(order == MatrixOrderAppend) matrix_multiply(matrix->matrix, shear, matrix->matrix); - else + else if (order == MatrixOrderPrepend) matrix_multiply(shear, matrix->matrix, matrix->matrix); + else + return InvalidParameter; return Ok; } @@ -410,8 +420,10 @@ GpStatus WINGDIPAPI GdipTranslateMatrix(GpMatrix *matrix, REAL offsetX, if(order == MatrixOrderAppend) matrix_multiply(matrix->matrix, translate, matrix->matrix); - else + else if (order == MatrixOrderPrepend) matrix_multiply(translate, matrix->matrix, matrix->matrix); + else + return InvalidParameter; return Ok; } diff --git a/reactos/dll/win32/gdiplus/metafile.c b/reactos/dll/win32/gdiplus/metafile.c new file mode 100644 index 00000000000..38923a091aa --- /dev/null +++ b/reactos/dll/win32/gdiplus/metafile.c @@ -0,0 +1,553 @@ +/* + * Copyright (C) 2011 Vincent Povirk for CodeWeavers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#include +#include + +#include "windef.h" +#include "winbase.h" +#include "wingdi.h" +#include "wine/unicode.h" + +#define COBJMACROS +#include "objbase.h" +#include "ocidl.h" +#include "olectl.h" +#include "ole2.h" + +#include "winreg.h" +#include "shlwapi.h" + +#include "gdiplus.h" +#include "gdiplus_private.h" +#include "wine/debug.h" +#include "wine/list.h" + +WINE_DEFAULT_DEBUG_CHANNEL(gdiplus); + +typedef struct EmfPlusRecordHeader +{ + WORD Type; + WORD Flags; + DWORD Size; + DWORD DataSize; +} EmfPlusRecordHeader; + +typedef struct EmfPlusHeader +{ + EmfPlusRecordHeader Header; + DWORD Version; + DWORD EmfPlusFlags; + DWORD LogicalDpiX; + DWORD LogicalDpiY; +} EmfPlusHeader; + +static GpStatus METAFILE_AllocateRecord(GpMetafile *metafile, DWORD size, void **result) +{ + DWORD size_needed; + EmfPlusRecordHeader *record; + + if (!metafile->comment_data_size) + { + DWORD data_size = max(256, size * 2 + 4); + metafile->comment_data = GdipAlloc(data_size); + + if (!metafile->comment_data) + return OutOfMemory; + + memcpy(metafile->comment_data, "EMF+", 4); + + metafile->comment_data_size = data_size; + metafile->comment_data_length = 4; + } + + size_needed = size + metafile->comment_data_length; + + if (size_needed > metafile->comment_data_size) + { + DWORD data_size = size_needed * 2; + BYTE *new_data = GdipAlloc(data_size); + + if (!new_data) + return OutOfMemory; + + memcpy(new_data, metafile->comment_data, metafile->comment_data_length); + + metafile->comment_data_size = data_size; + GdipFree(metafile->comment_data); + metafile->comment_data = new_data; + } + + *result = metafile->comment_data + metafile->comment_data_length; + metafile->comment_data_length += size; + + record = (EmfPlusRecordHeader*)*result; + record->Size = size; + record->DataSize = size - sizeof(EmfPlusRecordHeader); + + return Ok; +} + +static void METAFILE_WriteRecords(GpMetafile *metafile) +{ + if (metafile->comment_data_length > 4) + { + GdiComment(metafile->record_dc, metafile->comment_data_length, metafile->comment_data); + metafile->comment_data_length = 4; + } +} + +static GpStatus METAFILE_WriteHeader(GpMetafile *metafile, HDC hdc) +{ + GpStatus stat; + + if (metafile->metafile_type == MetafileTypeEmfPlusOnly || metafile->metafile_type == MetafileTypeEmfPlusDual) + { + EmfPlusHeader *header; + + stat = METAFILE_AllocateRecord(metafile, sizeof(EmfPlusHeader), (void**)&header); + if (stat != Ok) + return stat; + + header->Header.Type = EmfPlusRecordTypeHeader; + + if (metafile->metafile_type == MetafileTypeEmfPlusDual) + header->Header.Flags = 1; + else + header->Header.Flags = 0; + + header->Version = 0xDBC01002; + + if (GetDeviceCaps(hdc, TECHNOLOGY) == DT_RASDISPLAY) + header->EmfPlusFlags = 1; + else + header->EmfPlusFlags = 0; + + header->LogicalDpiX = GetDeviceCaps(hdc, LOGPIXELSX); + header->LogicalDpiY = GetDeviceCaps(hdc, LOGPIXELSY); + + METAFILE_WriteRecords(metafile); + } + + return Ok; +} + +static GpStatus METAFILE_WriteEndOfFile(GpMetafile *metafile) +{ + GpStatus stat; + + if (metafile->metafile_type == MetafileTypeEmfPlusOnly || metafile->metafile_type == MetafileTypeEmfPlusDual) + { + EmfPlusRecordHeader *record; + + stat = METAFILE_AllocateRecord(metafile, sizeof(EmfPlusRecordHeader), (void**)&record); + if (stat != Ok) + return stat; + + record->Type = EmfPlusRecordTypeEndOfFile; + record->Flags = 0; + + METAFILE_WriteRecords(metafile); + } + + return Ok; +} + +GpStatus WINGDIPAPI GdipRecordMetafile(HDC hdc, EmfType type, GDIPCONST GpRectF *frameRect, + MetafileFrameUnit frameUnit, GDIPCONST WCHAR *desc, GpMetafile **metafile) +{ + HDC record_dc; + REAL framerect_factor_x, framerect_factor_y; + RECT rc; + GpStatus stat; + + TRACE("(%p %d %p %d %p %p)\n", hdc, type, frameRect, frameUnit, desc, metafile); + + if (!hdc || type < EmfTypeEmfOnly || type > EmfTypeEmfPlusDual || !metafile) + return InvalidParameter; + + if (!frameRect) + { + FIXME("not implemented for NULL rect\n"); + return NotImplemented; + } + + switch (frameUnit) + { + case MetafileFrameUnitPixel: + framerect_factor_x = 2540.0 / GetDeviceCaps(hdc, LOGPIXELSX); + framerect_factor_y = 2540.0 / GetDeviceCaps(hdc, LOGPIXELSY); + break; + case MetafileFrameUnitPoint: + framerect_factor_x = framerect_factor_y = 2540.0 / 72.0; + break; + case MetafileFrameUnitInch: + framerect_factor_x = framerect_factor_y = 2540.0; + break; + case MetafileFrameUnitDocument: + framerect_factor_x = framerect_factor_y = 2540.0 / 300.0; + break; + case MetafileFrameUnitMillimeter: + framerect_factor_x = framerect_factor_y = 100.0; + break; + case MetafileFrameUnitGdi: + framerect_factor_x = framerect_factor_y = 1.0; + break; + default: + return InvalidParameter; + } + + rc.left = framerect_factor_x * frameRect->X; + rc.top = framerect_factor_y * frameRect->Y; + rc.right = rc.left + framerect_factor_x * frameRect->Width; + rc.bottom = rc.top + framerect_factor_y * frameRect->Height; + + record_dc = CreateEnhMetaFileW(hdc, NULL, &rc, desc); + + if (!record_dc) + return GenericError; + + *metafile = GdipAlloc(sizeof(GpMetafile)); + if(!*metafile) + { + DeleteEnhMetaFile(CloseEnhMetaFile(record_dc)); + return OutOfMemory; + } + + (*metafile)->image.type = ImageTypeMetafile; + (*metafile)->image.picture = NULL; + (*metafile)->image.flags = ImageFlagsNone; + (*metafile)->image.palette_flags = 0; + (*metafile)->image.palette_count = 0; + (*metafile)->image.palette_size = 0; + (*metafile)->image.palette_entries = NULL; + (*metafile)->bounds = *frameRect; + (*metafile)->unit = frameUnit; + (*metafile)->metafile_type = type; + (*metafile)->record_dc = record_dc; + (*metafile)->comment_data = NULL; + (*metafile)->comment_data_size = 0; + (*metafile)->comment_data_length = 0; + (*metafile)->hemf = NULL; + + stat = METAFILE_WriteHeader(*metafile, hdc); + + if (stat != Ok) + { + DeleteEnhMetaFile(CloseEnhMetaFile(record_dc)); + GdipFree(*metafile); + *metafile = NULL; + return OutOfMemory; + } + + return stat; +} + +/***************************************************************************** + * GdipRecordMetafileI [GDIPLUS.@] + */ +GpStatus WINGDIPAPI GdipRecordMetafileI(HDC hdc, EmfType type, GDIPCONST GpRect *frameRect, + MetafileFrameUnit frameUnit, GDIPCONST WCHAR *desc, GpMetafile **metafile) +{ + GpRectF frameRectF, *pFrameRectF; + + TRACE("(%p %d %p %d %p %p)\n", hdc, type, frameRect, frameUnit, desc, metafile); + + if (frameRect) + { + frameRectF.X = frameRect->X; + frameRectF.Y = frameRect->Y; + frameRectF.Width = frameRect->Width; + frameRectF.Height = frameRect->Height; + pFrameRectF = &frameRectF; + } + else + pFrameRectF = NULL; + + return GdipRecordMetafile(hdc, type, pFrameRectF, frameUnit, desc, metafile); +} + +GpStatus METAFILE_GetGraphicsContext(GpMetafile* metafile, GpGraphics **result) +{ + GpStatus stat; + + if (!metafile->record_dc || metafile->record_graphics) + return InvalidParameter; + + stat = graphics_from_image((GpImage*)metafile, &metafile->record_graphics); + + if (stat == Ok) + *result = metafile->record_graphics; + + return stat; +} + +GpStatus METAFILE_GetDC(GpMetafile* metafile, HDC *hdc) +{ + if (metafile->metafile_type == MetafileTypeEmfPlusOnly || metafile->metafile_type == MetafileTypeEmfPlusDual) + { + EmfPlusRecordHeader *record; + GpStatus stat; + + stat = METAFILE_AllocateRecord(metafile, sizeof(EmfPlusRecordHeader), (void**)&record); + if (stat != Ok) + return stat; + + record->Type = EmfPlusRecordTypeGetDC; + record->Flags = 0; + + METAFILE_WriteRecords(metafile); + } + + *hdc = metafile->record_dc; + + return Ok; +} + +GpStatus METAFILE_ReleaseDC(GpMetafile* metafile, HDC hdc) +{ + if (hdc != metafile->record_dc) + return InvalidParameter; + + return Ok; +} + +GpStatus METAFILE_GraphicsDeleted(GpMetafile* metafile) +{ + GpStatus stat; + + stat = METAFILE_WriteEndOfFile(metafile); + metafile->record_graphics = NULL; + + metafile->hemf = CloseEnhMetaFile(metafile->record_dc); + metafile->record_dc = NULL; + + GdipFree(metafile->comment_data); + metafile->comment_data = NULL; + metafile->comment_data_size = 0; + + return stat; +} + +GpStatus WINGDIPAPI GdipGetHemfFromMetafile(GpMetafile *metafile, HENHMETAFILE *hEmf) +{ + TRACE("(%p,%p)\n", metafile, hEmf); + + if (!metafile || !hEmf || !metafile->hemf) + return InvalidParameter; + + *hEmf = metafile->hemf; + metafile->hemf = NULL; + + return Ok; +} + +static GpStatus METAFILE_PlaybackGetDC(GpMetafile *metafile) +{ + GpStatus stat = Ok; + + stat = GdipGetDC(metafile->playback_graphics, &metafile->playback_dc); + + if (stat == Ok) + { + /* The result of GdipGetDC always expects device co-ordinates, but the + * device co-ordinates of the source metafile do not correspond to + * device co-ordinates of the destination. Therefore, we set up the DC + * so that the metafile's bounds map to the destination points where we + * are drawing this metafile. */ + SetMapMode(metafile->playback_dc, MM_ANISOTROPIC); + + SetWindowOrgEx(metafile->playback_dc, metafile->bounds.X, metafile->bounds.Y, NULL); + SetWindowExtEx(metafile->playback_dc, metafile->bounds.Width, metafile->bounds.Height, NULL); + + SetViewportOrgEx(metafile->playback_dc, metafile->playback_points[0].X, metafile->playback_points[0].Y, NULL); + SetViewportExtEx(metafile->playback_dc, + metafile->playback_points[1].X - metafile->playback_points[0].X, + metafile->playback_points[2].Y - metafile->playback_points[0].Y, NULL); + } + + return stat; +} + +static void METAFILE_PlaybackReleaseDC(GpMetafile *metafile) +{ + if (metafile->playback_dc) + { + GdipReleaseDC(metafile->playback_graphics, metafile->playback_dc); + metafile->playback_dc = NULL; + } +} + +GpStatus WINGDIPAPI GdipPlayMetafileRecord(GDIPCONST GpMetafile *metafile, + EmfPlusRecordType recordType, UINT flags, UINT dataSize, GDIPCONST BYTE *data) +{ + TRACE("(%p,%x,%x,%d,%p)\n", metafile, recordType, flags, dataSize, data); + + if (!metafile || (dataSize && !data) || !metafile->playback_graphics) + return InvalidParameter; + + if (recordType >= 1 && recordType <= 0x7a) + { + /* regular EMF record */ + if (metafile->playback_dc) + { + ENHMETARECORD *record; + + record = GdipAlloc(dataSize + 8); + + if (record) + { + record->iType = recordType; + record->nSize = dataSize; + memcpy(record->dParm, data, dataSize); + + PlayEnhMetaFileRecord(metafile->playback_dc, metafile->handle_table, + record, metafile->handle_count); + + GdipFree(record); + } + else + return OutOfMemory; + } + } + else + { + METAFILE_PlaybackReleaseDC((GpMetafile*)metafile); + + switch(recordType) + { + case EmfPlusRecordTypeHeader: + case EmfPlusRecordTypeEndOfFile: + break; + case EmfPlusRecordTypeGetDC: + METAFILE_PlaybackGetDC((GpMetafile*)metafile); + break; + default: + FIXME("Not implemented for record type %x\n", recordType); + return NotImplemented; + } + } + + return Ok; +} + +struct enum_metafile_data +{ + EnumerateMetafileProc callback; + void *callback_data; + GpMetafile *metafile; +}; + +static int CALLBACK enum_metafile_proc(HDC hDC, HANDLETABLE *lpHTable, const ENHMETARECORD *lpEMFR, + int nObj, LPARAM lpData) +{ + BOOL ret; + struct enum_metafile_data *data = (struct enum_metafile_data*)lpData; + const BYTE* pStr; + + data->metafile->handle_table = lpHTable; + data->metafile->handle_count = nObj; + + /* First check for an EMF+ record. */ + if (lpEMFR->iType == EMR_GDICOMMENT) + { + const EMRGDICOMMENT *comment = (const EMRGDICOMMENT*)lpEMFR; + + if (comment->cbData >= 4 && memcmp(comment->Data, "EMF+", 4) == 0) + { + int offset = 4; + + while (offset + sizeof(EmfPlusRecordHeader) <= comment->cbData) + { + const EmfPlusRecordHeader *record = (const EmfPlusRecordHeader*)&comment->Data[offset]; + + if (record->DataSize) + pStr = (const BYTE*)(record+1); + else + pStr = NULL; + + ret = data->callback(record->Type, record->Flags, record->DataSize, + pStr, data->callback_data); + + if (!ret) + return 0; + + offset += record->Size; + } + + return 1; + } + } + + if (lpEMFR->nSize != 8) + pStr = (const BYTE*)lpEMFR->dParm; + else + pStr = NULL; + + return data->callback(lpEMFR->iType, 0, lpEMFR->nSize-8, + pStr, data->callback_data); +} + +GpStatus WINGDIPAPI GdipEnumerateMetafileSrcRectDestPoints(GpGraphics *graphics, + GDIPCONST GpMetafile *metafile, GDIPCONST GpPointF *destPoints, INT count, + GDIPCONST GpRectF *srcRect, Unit srcUnit, EnumerateMetafileProc callback, + VOID *callbackData, GDIPCONST GpImageAttributes *imageAttributes) +{ + struct enum_metafile_data data; + GpStatus stat; + GpMetafile *real_metafile = (GpMetafile*)metafile; /* whoever made this const was joking */ + + TRACE("(%p,%p,%p,%i,%p,%i,%p,%p,%p)\n", graphics, metafile, + destPoints, count, srcRect, srcUnit, callback, callbackData, + imageAttributes); + + if (!graphics || !metafile || !destPoints || count != 3 || !srcRect) + return InvalidParameter; + + if (!metafile->hemf) + return InvalidParameter; + + if (metafile->playback_graphics) + return ObjectBusy; + + TRACE("%s %i -> %s %s %s\n", debugstr_rectf(srcRect), srcUnit, + debugstr_pointf(&destPoints[0]), debugstr_pointf(&destPoints[1]), + debugstr_pointf(&destPoints[2])); + + data.callback = callback; + data.callback_data = callbackData; + data.metafile = real_metafile; + + real_metafile->playback_graphics = graphics; + real_metafile->playback_dc = NULL; + + memcpy(real_metafile->playback_points, destPoints, sizeof(PointF) * 3); + stat = GdipTransformPoints(graphics, CoordinateSpaceDevice, CoordinateSpaceWorld, real_metafile->playback_points, 3); + + if (stat == Ok && metafile->metafile_type == MetafileTypeEmf) + stat = METAFILE_PlaybackGetDC((GpMetafile*)metafile); + + if (stat == Ok) + EnumEnhMetaFile(0, metafile->hemf, enum_metafile_proc, &data, NULL); + + METAFILE_PlaybackReleaseDC((GpMetafile*)metafile); + + real_metafile->playback_graphics = NULL; + + return stat; +} diff --git a/reactos/dll/win32/gdiplus/region.c b/reactos/dll/win32/gdiplus/region.c index f11f3ca3669..485c3a3e165 100644 --- a/reactos/dll/win32/gdiplus/region.c +++ b/reactos/dll/win32/gdiplus/region.c @@ -683,17 +683,18 @@ GpStatus WINGDIPAPI GdipGetRegionBounds(GpRegion *region, GpGraphics *graphics, return Ok; } - if(!GetRgnBox(hrgn, &r)){ - DeleteObject(hrgn); - return GenericError; + if(GetRgnBox(hrgn, &r)){ + rect->X = r.left; + rect->Y = r.top; + rect->Width = r.right - r.left; + rect->Height = r.bottom - r.top; } + else + status = GenericError; - rect->X = r.left; - rect->Y = r.top; - rect->Width = r.right - r.left; - rect->Height = r.bottom - r.top; + DeleteObject(hrgn); - return Ok; + return status; } /***************************************************************************** @@ -1419,7 +1420,7 @@ static GpStatus get_region_scans_data(GpRegion *region, GpMatrix *matrix, LPRGND (*data)->rdh.rcBound.left = (*data)->rdh.rcBound.top = -0x400000; (*data)->rdh.rcBound.right = (*data)->rdh.rcBound.bottom = 0x400000; - memcpy(&(*data)->Buffer, &(*data)->rdh.rcBound, sizeof(RECT)); + memcpy((*data)->Buffer, &(*data)->rdh.rcBound, sizeof(RECT)); } else stat = OutOfMemory; @@ -1468,7 +1469,7 @@ GpStatus WINGDIPAPI GdipGetRegionScansI(GpRegion *region, GpRect *scans, INT *co if (stat == Ok) { *count = data->rdh.nCount; - rects = (RECT*)&data->Buffer; + rects = (RECT*)data->Buffer; if (scans) { @@ -1502,7 +1503,7 @@ GpStatus WINGDIPAPI GdipGetRegionScans(GpRegion *region, GpRectF *scans, INT *co if (stat == Ok) { *count = data->rdh.nCount; - rects = (RECT*)&data->Buffer; + rects = (RECT*)data->Buffer; if (scans) { diff --git a/reactos/include/psdk/gdiplus.h b/reactos/include/psdk/gdiplus.h index c8385dbd4e2..f063b3e2a84 100644 --- a/reactos/include/psdk/gdiplus.h +++ b/reactos/include/psdk/gdiplus.h @@ -28,8 +28,8 @@ namespace Gdiplus #include "gdiplusmem.h" }; -#include "gdiplustypes.h" #include "gdiplusenums.h" +#include "gdiplustypes.h" #include "gdiplusinit.h" #include "gdipluspixelformats.h" #include "gdiplusmetaheader.h" @@ -48,8 +48,8 @@ namespace Gdiplus #include "gdiplusmem.h" -#include "gdiplustypes.h" #include "gdiplusenums.h" +#include "gdiplustypes.h" #include "gdiplusinit.h" #include "gdipluspixelformats.h" #include "gdiplusmetaheader.h" diff --git a/reactos/include/psdk/gdiplusenums.h b/reactos/include/psdk/gdiplusenums.h index d472fd83810..69c81540ffc 100644 --- a/reactos/include/psdk/gdiplusenums.h +++ b/reactos/include/psdk/gdiplusenums.h @@ -42,6 +42,14 @@ enum BrushType BrushTypeLinearGradient = 4 }; +enum DriverStringOptions +{ + DriverStringOptionsCmapLookup = 1, + DriverStringOptionsVertical = 2, + DriverStringOptionsRealizedAdvance = 4, + DriverStringOptionsLimitSubpixel = 4 +}; + enum FillMode { FillModeAlternate = 0, @@ -430,10 +438,284 @@ enum HatchStyle HatchStyleMax = HatchStyleTotal - 1 }; +#define GDIP_EMFPLUS_RECORD_BASE 0x00004000 +#define GDIP_WMF_RECORD_BASE 0x00010000 +#define GDIP_WMF_RECORD_TO_EMFPLUS(x) ((x)|GDIP_WMF_RECORD_BASE) + +enum EmfPlusRecordType { + WmfRecordTypeSetBkColor = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETBKCOLOR), + WmfRecordTypeSetBkMode = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETBKMODE), + WmfRecordTypeSetMapMode = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETMAPMODE), + WmfRecordTypeSetROP2 = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETROP2), + WmfRecordTypeSetRelAbs = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETRELABS), + WmfRecordTypeSetPolyFillMode = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETPOLYFILLMODE), + WmfRecordTypeSetStretchBltMode = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETSTRETCHBLTMODE), + WmfRecordTypeSetTextCharExtra = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETTEXTCHAREXTRA), + WmfRecordTypeSetTextColor = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETTEXTCOLOR), + WmfRecordTypeSetTextJustification = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETTEXTJUSTIFICATION), + WmfRecordTypeSetWindowOrg = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETWINDOWORG), + WmfRecordTypeSetWindowExt = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETWINDOWEXT), + WmfRecordTypeSetViewportOrg = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETVIEWPORTORG), + WmfRecordTypeSetViewportExt = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETVIEWPORTEXT), + WmfRecordTypeOffsetWindowOrg = GDIP_WMF_RECORD_TO_EMFPLUS(META_OFFSETWINDOWORG), + WmfRecordTypeScaleWindowExt = GDIP_WMF_RECORD_TO_EMFPLUS(META_SCALEWINDOWEXT), + WmfRecordTypeOffsetViewportOrg = GDIP_WMF_RECORD_TO_EMFPLUS(META_OFFSETVIEWPORTORG), + WmfRecordTypeScaleViewportExt = GDIP_WMF_RECORD_TO_EMFPLUS(META_SCALEVIEWPORTEXT), + WmfRecordTypeLineTo = GDIP_WMF_RECORD_TO_EMFPLUS(META_LINETO), + WmfRecordTypeMoveTo = GDIP_WMF_RECORD_TO_EMFPLUS(META_MOVETO), + WmfRecordTypeExcludeClipRect = GDIP_WMF_RECORD_TO_EMFPLUS(META_EXCLUDECLIPRECT), + WmfRecordTypeIntersectClipRect = GDIP_WMF_RECORD_TO_EMFPLUS(META_INTERSECTCLIPRECT), + WmfRecordTypeArc = GDIP_WMF_RECORD_TO_EMFPLUS(META_ARC), + WmfRecordTypeEllipse = GDIP_WMF_RECORD_TO_EMFPLUS(META_ELLIPSE), + WmfRecordTypeFloodFill = GDIP_WMF_RECORD_TO_EMFPLUS(META_FLOODFILL), + WmfRecordTypePie = GDIP_WMF_RECORD_TO_EMFPLUS(META_PIE), + WmfRecordTypeRectangle = GDIP_WMF_RECORD_TO_EMFPLUS(META_RECTANGLE), + WmfRecordTypeRoundRect = GDIP_WMF_RECORD_TO_EMFPLUS(META_ROUNDRECT), + WmfRecordTypePatBlt = GDIP_WMF_RECORD_TO_EMFPLUS(META_PATBLT), + WmfRecordTypeSaveDC = GDIP_WMF_RECORD_TO_EMFPLUS(META_SAVEDC), + WmfRecordTypeSetPixel = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETPIXEL), + WmfRecordTypeOffsetClipRgn = GDIP_WMF_RECORD_TO_EMFPLUS(META_OFFSETCLIPRGN), + WmfRecordTypeTextOut = GDIP_WMF_RECORD_TO_EMFPLUS(META_TEXTOUT), + WmfRecordTypeBitBlt = GDIP_WMF_RECORD_TO_EMFPLUS(META_BITBLT), + WmfRecordTypeStretchBlt = GDIP_WMF_RECORD_TO_EMFPLUS(META_STRETCHBLT), + WmfRecordTypePolygon = GDIP_WMF_RECORD_TO_EMFPLUS(META_POLYGON), + WmfRecordTypePolyline = GDIP_WMF_RECORD_TO_EMFPLUS(META_POLYLINE), + WmfRecordTypeEscape = GDIP_WMF_RECORD_TO_EMFPLUS(META_ESCAPE), + WmfRecordTypeRestoreDC = GDIP_WMF_RECORD_TO_EMFPLUS(META_RESTOREDC), + WmfRecordTypeFillRegion = GDIP_WMF_RECORD_TO_EMFPLUS(META_FILLREGION), + WmfRecordTypeFrameRegion = GDIP_WMF_RECORD_TO_EMFPLUS(META_FRAMEREGION), + WmfRecordTypeInvertRegion = GDIP_WMF_RECORD_TO_EMFPLUS(META_INVERTREGION), + WmfRecordTypePaintRegion = GDIP_WMF_RECORD_TO_EMFPLUS(META_PAINTREGION), + WmfRecordTypeSelectClipRegion = GDIP_WMF_RECORD_TO_EMFPLUS(META_SELECTCLIPREGION), + WmfRecordTypeSelectObject = GDIP_WMF_RECORD_TO_EMFPLUS(META_SELECTOBJECT), + WmfRecordTypeSetTextAlign = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETTEXTALIGN), + WmfRecordTypeDrawText = GDIP_WMF_RECORD_TO_EMFPLUS(0x062F), + WmfRecordTypeChord = GDIP_WMF_RECORD_TO_EMFPLUS(META_CHORD), + WmfRecordTypeSetMapperFlags = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETMAPPERFLAGS), + WmfRecordTypeExtTextOut = GDIP_WMF_RECORD_TO_EMFPLUS(META_EXTTEXTOUT), + WmfRecordTypeSetDIBToDev = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETDIBTODEV), + WmfRecordTypeSelectPalette = GDIP_WMF_RECORD_TO_EMFPLUS(META_SELECTPALETTE), + WmfRecordTypeRealizePalette = GDIP_WMF_RECORD_TO_EMFPLUS(META_REALIZEPALETTE), + WmfRecordTypeAnimatePalette = GDIP_WMF_RECORD_TO_EMFPLUS(META_ANIMATEPALETTE), + WmfRecordTypeSetPalEntries = GDIP_WMF_RECORD_TO_EMFPLUS(META_SETPALENTRIES), + WmfRecordTypePolyPolygon = GDIP_WMF_RECORD_TO_EMFPLUS(META_POLYPOLYGON), + WmfRecordTypeResizePalette = GDIP_WMF_RECORD_TO_EMFPLUS(META_RESIZEPALETTE), + WmfRecordTypeDIBBitBlt = GDIP_WMF_RECORD_TO_EMFPLUS(META_DIBBITBLT), + WmfRecordTypeDIBStretchBlt = GDIP_WMF_RECORD_TO_EMFPLUS(META_DIBSTRETCHBLT), + WmfRecordTypeDIBCreatePatternBrush = GDIP_WMF_RECORD_TO_EMFPLUS(META_DIBCREATEPATTERNBRUSH), + WmfRecordTypeStretchDIB = GDIP_WMF_RECORD_TO_EMFPLUS(META_STRETCHDIB), + WmfRecordTypeExtFloodFill = GDIP_WMF_RECORD_TO_EMFPLUS(META_EXTFLOODFILL), + WmfRecordTypeSetLayout = GDIP_WMF_RECORD_TO_EMFPLUS(0x0149), + WmfRecordTypeResetDC = GDIP_WMF_RECORD_TO_EMFPLUS(0x014C), + WmfRecordTypeStartDoc = GDIP_WMF_RECORD_TO_EMFPLUS(0x014D), + WmfRecordTypeStartPage = GDIP_WMF_RECORD_TO_EMFPLUS(0x004F), + WmfRecordTypeEndPage = GDIP_WMF_RECORD_TO_EMFPLUS(0x0050), + WmfRecordTypeAbortDoc = GDIP_WMF_RECORD_TO_EMFPLUS(0x0052), + WmfRecordTypeEndDoc = GDIP_WMF_RECORD_TO_EMFPLUS(0x005E), + WmfRecordTypeDeleteObject = GDIP_WMF_RECORD_TO_EMFPLUS(META_DELETEOBJECT), + WmfRecordTypeCreatePalette = GDIP_WMF_RECORD_TO_EMFPLUS(META_CREATEPALETTE), + WmfRecordTypeCreateBrush = GDIP_WMF_RECORD_TO_EMFPLUS(0x00F8), + WmfRecordTypeCreatePatternBrush = GDIP_WMF_RECORD_TO_EMFPLUS(META_CREATEPATTERNBRUSH), + WmfRecordTypeCreatePenIndirect = GDIP_WMF_RECORD_TO_EMFPLUS(META_CREATEPENINDIRECT), + WmfRecordTypeCreateFontIndirect = GDIP_WMF_RECORD_TO_EMFPLUS(META_CREATEFONTINDIRECT), + WmfRecordTypeCreateBrushIndirect = GDIP_WMF_RECORD_TO_EMFPLUS(META_CREATEBRUSHINDIRECT), + WmfRecordTypeCreateBitmapIndirect = GDIP_WMF_RECORD_TO_EMFPLUS(0x02FD), + WmfRecordTypeCreateBitmap = GDIP_WMF_RECORD_TO_EMFPLUS(0x06FE), + WmfRecordTypeCreateRegion = GDIP_WMF_RECORD_TO_EMFPLUS(META_CREATEREGION), + EmfRecordTypeHeader = EMR_HEADER, + EmfRecordTypePolyBezier = EMR_POLYBEZIER, + EmfRecordTypePolygon = EMR_POLYGON, + EmfRecordTypePolyline = EMR_POLYLINE, + EmfRecordTypePolyBezierTo = EMR_POLYBEZIERTO, + EmfRecordTypePolyLineTo = EMR_POLYLINETO, + EmfRecordTypePolyPolyline = EMR_POLYPOLYLINE, + EmfRecordTypePolyPolygon = EMR_POLYPOLYGON, + EmfRecordTypeSetWindowExtEx = EMR_SETWINDOWEXTEX, + EmfRecordTypeSetWindowOrgEx = EMR_SETWINDOWORGEX, + EmfRecordTypeSetViewportExtEx = EMR_SETVIEWPORTEXTEX, + EmfRecordTypeSetViewportOrgEx = EMR_SETVIEWPORTORGEX, + EmfRecordTypeSetBrushOrgEx = EMR_SETBRUSHORGEX, + EmfRecordTypeEOF = EMR_EOF, + EmfRecordTypeSetPixelV = EMR_SETPIXELV, + EmfRecordTypeSetMapperFlags = EMR_SETMAPPERFLAGS, + EmfRecordTypeSetMapMode = EMR_SETMAPMODE, + EmfRecordTypeSetBkMode = EMR_SETBKMODE, + EmfRecordTypeSetPolyFillMode = EMR_SETPOLYFILLMODE, + EmfRecordTypeSetROP2 = EMR_SETROP2, + EmfRecordTypeSetStretchBltMode = EMR_SETSTRETCHBLTMODE, + EmfRecordTypeSetTextAlign = EMR_SETTEXTALIGN, + EmfRecordTypeSetColorAdjustment = EMR_SETCOLORADJUSTMENT, + EmfRecordTypeSetTextColor = EMR_SETTEXTCOLOR, + EmfRecordTypeSetBkColor = EMR_SETBKCOLOR, + EmfRecordTypeOffsetClipRgn = EMR_OFFSETCLIPRGN, + EmfRecordTypeMoveToEx = EMR_MOVETOEX, + EmfRecordTypeSetMetaRgn = EMR_SETMETARGN, + EmfRecordTypeExcludeClipRect = EMR_EXCLUDECLIPRECT, + EmfRecordTypeIntersectClipRect = EMR_INTERSECTCLIPRECT, + EmfRecordTypeScaleViewportExtEx = EMR_SCALEVIEWPORTEXTEX, + EmfRecordTypeScaleWindowExtEx = EMR_SCALEWINDOWEXTEX, + EmfRecordTypeSaveDC = EMR_SAVEDC, + EmfRecordTypeRestoreDC = EMR_RESTOREDC, + EmfRecordTypeSetWorldTransform = EMR_SETWORLDTRANSFORM, + EmfRecordTypeModifyWorldTransform = EMR_MODIFYWORLDTRANSFORM, + EmfRecordTypeSelectObject = EMR_SELECTOBJECT, + EmfRecordTypeCreatePen = EMR_CREATEPEN, + EmfRecordTypeCreateBrushIndirect = EMR_CREATEBRUSHINDIRECT, + EmfRecordTypeDeleteObject = EMR_DELETEOBJECT, + EmfRecordTypeAngleArc = EMR_ANGLEARC, + EmfRecordTypeEllipse = EMR_ELLIPSE, + EmfRecordTypeRectangle = EMR_RECTANGLE, + EmfRecordTypeRoundRect = EMR_ROUNDRECT, + EmfRecordTypeArc = EMR_ARC, + EmfRecordTypeChord = EMR_CHORD, + EmfRecordTypePie = EMR_PIE, + EmfRecordTypeSelectPalette = EMR_SELECTPALETTE, + EmfRecordTypeCreatePalette = EMR_CREATEPALETTE, + EmfRecordTypeSetPaletteEntries = EMR_SETPALETTEENTRIES, + EmfRecordTypeResizePalette = EMR_RESIZEPALETTE, + EmfRecordTypeRealizePalette = EMR_REALIZEPALETTE, + EmfRecordTypeExtFloodFill = EMR_EXTFLOODFILL, + EmfRecordTypeLineTo = EMR_LINETO, + EmfRecordTypeArcTo = EMR_ARCTO, + EmfRecordTypePolyDraw = EMR_POLYDRAW, + EmfRecordTypeSetArcDirection = EMR_SETARCDIRECTION, + EmfRecordTypeSetMiterLimit = EMR_SETMITERLIMIT, + EmfRecordTypeBeginPath = EMR_BEGINPATH, + EmfRecordTypeEndPath = EMR_ENDPATH, + EmfRecordTypeCloseFigure = EMR_CLOSEFIGURE, + EmfRecordTypeFillPath = EMR_FILLPATH, + EmfRecordTypeStrokeAndFillPath = EMR_STROKEANDFILLPATH, + EmfRecordTypeStrokePath = EMR_STROKEPATH, + EmfRecordTypeFlattenPath = EMR_FLATTENPATH, + EmfRecordTypeWidenPath = EMR_WIDENPATH, + EmfRecordTypeSelectClipPath = EMR_SELECTCLIPPATH, + EmfRecordTypeAbortPath = EMR_ABORTPATH, + EmfRecordTypeReserved_069 = 69, + EmfRecordTypeGdiComment = EMR_GDICOMMENT, + EmfRecordTypeFillRgn = EMR_FILLRGN, + EmfRecordTypeFrameRgn = EMR_FRAMERGN, + EmfRecordTypeInvertRgn = EMR_INVERTRGN, + EmfRecordTypePaintRgn = EMR_PAINTRGN, + EmfRecordTypeExtSelectClipRgn = EMR_EXTSELECTCLIPRGN, + EmfRecordTypeBitBlt = EMR_BITBLT, + EmfRecordTypeStretchBlt = EMR_STRETCHBLT, + EmfRecordTypeMaskBlt = EMR_MASKBLT, + EmfRecordTypePlgBlt = EMR_PLGBLT, + EmfRecordTypeSetDIBitsToDevice = 80, + EmfRecordTypeStretchDIBits = EMR_STRETCHDIBITS, + EmfRecordTypeExtCreateFontIndirect = EMR_EXTCREATEFONTINDIRECTW, + EmfRecordTypeExtTextOutA = EMR_EXTTEXTOUTA, + EmfRecordTypeExtTextOutW = EMR_EXTTEXTOUTW, + EmfRecordTypePolyBezier16 = EMR_POLYBEZIER16, + EmfRecordTypePolygon16 = EMR_POLYGON16, + EmfRecordTypePolyline16 = EMR_POLYLINE16, + EmfRecordTypePolyBezierTo16 = EMR_POLYBEZIERTO16, + EmfRecordTypePolylineTo16 = EMR_POLYLINETO16, + EmfRecordTypePolyPolyline16 = EMR_POLYPOLYLINE16, + EmfRecordTypePolyPolygon16 = EMR_POLYPOLYGON16, + EmfRecordTypePolyDraw16 = EMR_POLYDRAW16, + EmfRecordTypeCreateMonoBrush = EMR_CREATEMONOBRUSH, + EmfRecordTypeCreateDIBPatternBrushPt = EMR_CREATEDIBPATTERNBRUSHPT, + EmfRecordTypeExtCreatePen = EMR_EXTCREATEPEN, + EmfRecordTypePolyTextOutA = EMR_POLYTEXTOUTA, + EmfRecordTypePolyTextOutW = EMR_POLYTEXTOUTW, + EmfRecordTypeSetICMMode = 98, + EmfRecordTypeCreateColorSpace = 99, + EmfRecordTypeSetColorSpace = 100, + EmfRecordTypeDeleteColorSpace = 101, + EmfRecordTypeGLSRecord = 102, + EmfRecordTypeGLSBoundedRecord = 103, + EmfRecordTypePixelFormat = 104, + EmfRecordTypeDrawEscape = 105, + EmfRecordTypeExtEscape = 106, + EmfRecordTypeStartDoc = 107, + EmfRecordTypeSmallTextOut = 108, + EmfRecordTypeForceUFIMapping = 109, + EmfRecordTypeNamedEscape = 110, + EmfRecordTypeColorCorrectPalette = 111, + EmfRecordTypeSetICMProfileA = 112, + EmfRecordTypeSetICMProfileW = 113, + EmfRecordTypeAlphaBlend = 114, + EmfRecordTypeSetLayout = 115, + EmfRecordTypeTransparentBlt = 116, + EmfRecordTypeReserved_117 = 117, + EmfRecordTypeGradientFill = 118, + EmfRecordTypeSetLinkedUFIs = 119, + EmfRecordTypeSetTextJustification = 120, + EmfRecordTypeColorMatchToTargetW = 121, + EmfRecordTypeCreateColorSpaceW = 122, + EmfRecordTypeMax = 122, + EmfRecordTypeMin = 1, + EmfPlusRecordTypeInvalid = GDIP_EMFPLUS_RECORD_BASE, + EmfPlusRecordTypeHeader, + EmfPlusRecordTypeEndOfFile, + EmfPlusRecordTypeComment, + EmfPlusRecordTypeGetDC, + EmfPlusRecordTypeMultiFormatStart, + EmfPlusRecordTypeMultiFormatSection, + EmfPlusRecordTypeMultiFormatEnd, + EmfPlusRecordTypeObject, + EmfPlusRecordTypeClear, + EmfPlusRecordTypeFillRects, + EmfPlusRecordTypeDrawRects, + EmfPlusRecordTypeFillPolygon, + EmfPlusRecordTypeDrawLines, + EmfPlusRecordTypeFillEllipse, + EmfPlusRecordTypeDrawEllipse, + EmfPlusRecordTypeFillPie, + EmfPlusRecordTypeDrawPie, + EmfPlusRecordTypeDrawArc, + EmfPlusRecordTypeFillRegion, + EmfPlusRecordTypeFillPath, + EmfPlusRecordTypeDrawPath, + EmfPlusRecordTypeFillClosedCurve, + EmfPlusRecordTypeDrawClosedCurve, + EmfPlusRecordTypeDrawCurve, + EmfPlusRecordTypeDrawBeziers, + EmfPlusRecordTypeDrawImage, + EmfPlusRecordTypeDrawImagePoints, + EmfPlusRecordTypeDrawString, + EmfPlusRecordTypeSetRenderingOrigin, + EmfPlusRecordTypeSetAntiAliasMode, + EmfPlusRecordTypeSetTextRenderingHint, + EmfPlusRecordTypeSetTextContrast, + EmfPlusRecordTypeSetGammaValue, + EmfPlusRecordTypeSetInterpolationMode, + EmfPlusRecordTypeSetPixelOffsetMode, + EmfPlusRecordTypeSetCompositingMode, + EmfPlusRecordTypeSetCompositingQuality, + EmfPlusRecordTypeSave, + EmfPlusRecordTypeRestore, + EmfPlusRecordTypeBeginContainer, + EmfPlusRecordTypeBeginContainerNoParams, + EmfPlusRecordTypeEndContainer, + EmfPlusRecordTypeSetWorldTransform, + EmfPlusRecordTypeResetWorldTransform, + EmfPlusRecordTypeMultiplyWorldTransform, + EmfPlusRecordTypeTranslateWorldTransform, + EmfPlusRecordTypeScaleWorldTransform, + EmfPlusRecordTypeRotateWorldTransform, + EmfPlusRecordTypeSetPageTransform, + EmfPlusRecordTypeResetClip, + EmfPlusRecordTypeSetClipRect, + EmfPlusRecordTypeSetClipPath, + EmfPlusRecordTypeSetClipRegion, + EmfPlusRecordTypeOffsetClip, + EmfPlusRecordTypeDrawDriverString, + EmfPlusRecordTypeStrokeFillPath, + EmfPlusRecordTypeSerializableObject, + EmfPlusRecordTypeSetTSGraphics, + EmfPlusRecordTypeSetTSClip, + EmfPlusRecordTotal, + EmfPlusRecordTypeMax = EmfPlusRecordTotal-1, + EmfPlusRecordTypeMin = EmfPlusRecordTypeHeader +}; + #ifndef __cplusplus typedef enum Unit Unit; typedef enum BrushType BrushType; +typedef enum DriverStringOptions DriverStringOptions; typedef enum FillMode FillMode; typedef enum LineCap LineCap; typedef enum PathPointType PathPointType; @@ -461,7 +743,7 @@ typedef enum StringTrimming StringTrimming; typedef enum FontStyle FontStyle; typedef enum StringFormatFlags StringFormatFlags; typedef enum HotkeyPrefix HotkeyPrefix; -typedef enum PenAlignment GpPenAlignment; +typedef enum PenAlignment PenAlignment; typedef enum PaletteFlags PaletteFlags; typedef enum ImageCodecFlags ImageCodecFlags; typedef enum CombineMode CombineMode; @@ -471,7 +753,11 @@ typedef enum GpTestControlEnum GpTestControlEnum; typedef enum MetafileFrameUnit MetafileFrameUnit; typedef enum PenType PenType; typedef enum HatchStyle HatchStyle; +typedef enum EmfPlusRecordType EmfPlusRecordType; #endif /* end of c typedefs */ +#undef GDIP_WMF_RECORD_TO_EMFPLUS +#define GDIP_WMF_RECORD_TO_EMFPLUS(x) ((EmfPlusRecordType)((x)|GDIP_WMF_RECORD_BASE)) + #endif diff --git a/reactos/include/psdk/gdiplusflat.h b/reactos/include/psdk/gdiplusflat.h index 8312e16490a..67920042937 100644 --- a/reactos/include/psdk/gdiplusflat.h +++ b/reactos/include/psdk/gdiplusflat.h @@ -206,10 +206,15 @@ GpStatus WINGDIPAPI GdipDrawRectanglesI(GpGraphics*,GpPen*,GDIPCONST GpRect*,INT GpStatus WINGDIPAPI GdipDrawString(GpGraphics*,GDIPCONST WCHAR*,INT, GDIPCONST GpFont*,GDIPCONST RectF*, GDIPCONST GpStringFormat*, GDIPCONST GpBrush*); +GpStatus WINGDIPAPI GdipEnumerateMetafileSrcRectDestPoints(GpGraphics*, + GDIPCONST GpMetafile*,GDIPCONST GpPointF*,INT,GDIPCONST GpRectF*,Unit, + EnumerateMetafileProc,VOID*,GDIPCONST GpImageAttributes*); GpStatus WINGDIPAPI GdipFillClosedCurve2(GpGraphics*,GpBrush*,GDIPCONST GpPointF*,INT, REAL,GpFillMode); GpStatus WINGDIPAPI GdipFillClosedCurve2I(GpGraphics*,GpBrush*,GDIPCONST GpPoint*,INT, REAL,GpFillMode); +GpStatus WINGDIPAPI GdipFillClosedCurve(GpGraphics*,GpBrush*,GDIPCONST GpPointF*,INT); +GpStatus WINGDIPAPI GdipFillClosedCurveI(GpGraphics*,GpBrush*,GDIPCONST GpPoint*,INT); GpStatus WINGDIPAPI GdipFillEllipse(GpGraphics*,GpBrush*,REAL,REAL,REAL,REAL); GpStatus WINGDIPAPI GdipFillEllipseI(GpGraphics*,GpBrush*,INT,INT,INT,INT); GpStatus WINGDIPAPI GdipFillPath(GpGraphics*,GpBrush*,GpPath*); @@ -472,6 +477,7 @@ GpStatus WINGDIPAPI GdipSetLinePresetBlend(GpLineGradient*,GDIPCONST ARGB*, GDIPCONST REAL*,INT); GpStatus WINGDIPAPI GdipGetLinePresetBlend(GpLineGradient*,ARGB*,REAL*,INT); GpStatus WINGDIPAPI GdipGetLinePresetBlendCount(GpLineGradient*,INT*); +GpStatus WINGDIPAPI GdipGetLineTransform(GpLineGradient*,GpMatrix*); GpStatus WINGDIPAPI GdipResetLineTransform(GpLineGradient*); GpStatus WINGDIPAPI GdipRotateLineTransform(GpLineGradient*,REAL,GpMatrixOrder); GpStatus WINGDIPAPI GdipScaleLineTransform(GpLineGradient*,REAL,REAL, @@ -520,7 +526,10 @@ GpStatus WINGDIPAPI GdipCreateMetafileFromWmfFile(GDIPCONST WCHAR*, GDIPCONST Wm GpMetafile**); GpStatus WINGDIPAPI GdipCreateMetafileFromFile(GDIPCONST WCHAR*,GpMetafile**); GpStatus WINGDIPAPI GdipCreateMetafileFromStream(IStream*,GpMetafile**); +GpStatus WINGDIPAPI GdipGetHemfFromMetafile(GpMetafile*,HENHMETAFILE*); +GpStatus WINGDIPAPI GdipPlayMetafileRecord(GDIPCONST GpMetafile*,EmfPlusRecordType,UINT,UINT,GDIPCONST BYTE*); GpStatus WINGDIPAPI GdipSetMetafileDownLevelRasterizationLimit(GpMetafile*,UINT); +GpStatus WINGDIPAPI GdipRecordMetafile(HDC,EmfType,GDIPCONST GpRectF*,MetafileFrameUnit,GDIPCONST WCHAR*,GpMetafile**); /* MetafileHeader */ GpStatus WINGDIPAPI GdipGetMetafileHeaderFromEmf(HENHMETAFILE,MetafileHeader*); @@ -641,6 +650,9 @@ GpStatus WINGDIPAPI GdipGetRegionBoundsI(GpRegion *, GpGraphics *, GpRect *); GpStatus WINGDIPAPI GdipGetRegionData(GpRegion *, BYTE *, UINT, UINT *); GpStatus WINGDIPAPI GdipGetRegionDataSize(GpRegion *, UINT *); GpStatus WINGDIPAPI GdipGetRegionHRgn(GpRegion *, GpGraphics *, HRGN *); +GpStatus WINGDIPAPI GdipGetRegionScans(GpRegion *, GpRectF *, INT *, GpMatrix *); +GpStatus WINGDIPAPI GdipGetRegionScansI(GpRegion *, GpRect *, INT *, GpMatrix *); +GpStatus WINGDIPAPI GdipGetRegionScansCount(GpRegion *, UINT *, GpMatrix *); GpStatus WINGDIPAPI GdipIsEmptyRegion(GpRegion *, GpGraphics *, BOOL *); GpStatus WINGDIPAPI GdipIsEqualRegion(GpRegion *, GpRegion *, GpGraphics *, BOOL *); GpStatus WINGDIPAPI GdipIsInfiniteRegion(GpRegion *, GpGraphics *, BOOL *); diff --git a/reactos/include/psdk/gdiplusgpstubs.h b/reactos/include/psdk/gdiplusgpstubs.h index 3edc1f4b7b4..5a65cd83e96 100644 --- a/reactos/include/psdk/gdiplusgpstubs.h +++ b/reactos/include/psdk/gdiplusgpstubs.h @@ -22,6 +22,7 @@ #ifdef __cplusplus class GpGraphics {}; +class GpPen {}; class GpBrush {}; class GpHatch : public GpBrush {}; class GpSolidFill : public GpBrush {}; @@ -92,6 +93,7 @@ typedef WrapMode GpWrapMode; typedef Color GpColor; typedef FlushIntention GpFlushIntention; typedef CoordinateSpace GpCoordinateSpace; +typedef PenAlignment GpPenAlignment; typedef PenType GpPenType; #endif diff --git a/reactos/include/psdk/gdiplusimaging.h b/reactos/include/psdk/gdiplusimaging.h index 42a00cbef4e..7c199c3d5bd 100644 --- a/reactos/include/psdk/gdiplusimaging.h +++ b/reactos/include/psdk/gdiplusimaging.h @@ -110,7 +110,7 @@ public: UINT Width; UINT Height; INT Stride; - PixelFormat PixelFormat; + Gdiplus::PixelFormat PixelFormat; VOID* Scan0; UINT_PTR Reserved; }; diff --git a/reactos/include/psdk/gdiplustypes.h b/reactos/include/psdk/gdiplustypes.h index 4f97432bc64..2e46bb4aecd 100644 --- a/reactos/include/psdk/gdiplustypes.h +++ b/reactos/include/psdk/gdiplustypes.h @@ -55,6 +55,8 @@ typedef BOOL (CALLBACK * ImageAbort)(VOID *); typedef ImageAbort DrawImageAbort; typedef ImageAbort GetThumbnailImageAbort; +typedef BOOL (CALLBACK * EnumerateMetafileProc)(EmfPlusRecordType,UINT,UINT,const BYTE*,VOID*); + #ifdef __cplusplus } #endif @@ -199,6 +201,31 @@ public: INT Height; }; +class CharacterRange +{ +public: + CharacterRange() + { + First = Length = 0; + } + + CharacterRange(INT first, INT length) + { + First = first; + Length = length; + } + + CharacterRange& operator=(const CharacterRange& rhs) + { + First = rhs.First; + Length = rhs.Length; + return *this; + } +public: + INT First; + INT Length; +}; + #else /* end of c++ typedefs */ typedef struct Point diff --git a/reactos/media/doc/README.WINE b/reactos/media/doc/README.WINE index 4d92699d5d3..b567757e873 100644 --- a/reactos/media/doc/README.WINE +++ b/reactos/media/doc/README.WINE @@ -49,7 +49,7 @@ reactos/dll/win32/cabinet # Synced to Wine-1.3.37 reactos/dll/win32/clusapi # Synced to Wine-1.3.37 reactos/dll/win32/comcat # Synced to Wine-1.3.37 reactos/dll/win32/comctl32 # Synced to Wine 1.3.37 -reactos/dll/win32/comdlg32 # Autosync +reactos/dll/win32/comdlg32 # Synced to Wine 1.3.37 reactos/dll/win32/compstui # Synced to Wine-1.3.37 reactos/dll/win32/credui # Synced to Wine-1.3.37 reactos/dll/win32/crypt32 # Synced to Wine-1.3.37 @@ -61,7 +61,7 @@ reactos/dll/win32/dbghelp # Autosync reactos/dll/win32/dciman32 # Autosync reactos/dll/win32/dwmapi # Synced to Wine-1.3.37 reactos/dll/win32/fusion # Synced to Wine-1.3.37 -reactos/dll/win32/gdiplus # Autosync +reactos/dll/win32/gdiplus # Synced to Wine-1.3.37 reactos/dll/win32/hhctrl.ocx # Autosync reactos/dll/win32/hlink # Synced to Wine-1.3.37 reactos/dll/win32/hnetcfg # Synced to Wine-1.3.37