Некоторые функции содержат не только массив параметров, но и структуры с данными. Например, запись, описывающая функцию BitBlt использует сохраненное растровое изображениев формате Device Dependent Bitmap (DDB). Структура записи BitBlt в метафайлах Windows 2.x выглядит следующим образом:
Массив bitmap состоит из структур RGBTRIPLE:
typedef struct _RGBTriple
{
BYTE Red;
BYTE Green;
BYTE Blue;
} RGBTRIPLE;
DDB формат поддерживается Windows 2.x но не совместим с Windows 3.0 и старше. Windows 3.0 описывает функцию DibBitBlt и Device Independent Bitmap (DIB):
typedef struct _DibBitBltRecord
{
DWORD Size; /* Размер записи в словах */
WORD Function; /* Номер функции (0x0922) */
WORD RasterOp; /* старшее слово растровой операции */
WORD YSrcOrigin; /* Y-координата источника */
WORD XSrcOrigin; /* X-координата источника */
WORD YDest; /* ширина отображения */
WORD XDest; /* высота отображения */
WORD YDestOrigin; /* Y-координата отображения */
WORD XDestOrigin; /* X-координата отображения */
/* DIB Bitmap */
DWORD Width; /* ширина растра в пикселях */
DWORD Height; /* высота растра в строках */
DWORD BytesPerLine; /* разрешение */
WORD NumColorPlanes; /* количество цветов в палитре */
WORD BitsPerPixel; /* количество бит на пиксель */
DWORD Compression; /* Формат сжатия */
DWORD SizeImage; /* Размер растра в байтах */
LONG XPelsPerMeter; /* расрешение по горизонтали */
LONG YPelsPerMeter; /* разрешение по вертикали */
DWORD ClrUsed; /* Количетсво используемых цветов */
DWORD ClrImportant; /* Количество важных цветов */
RGBQUAD Bitmap[]; /* растр */
} DIBBITBLTRECORD;
Массив bitmapсостоит из структур RGBQUAD:
typedef struct _RGBQuad
{
BYTE Red;
BYTE Green;
BYTE Blue;
BYTE Reserved;
} RGBQUAD;
Другая специфическая запись метафайлов, заслуживающая внимание это Escape (0x0626). API Windows 3.x поддерживает 64 escape-последовательностей, которые могут содержаться в метафайле. Но на практике каждая escape-последовательность работает по разному, в зависимости от типа принтера.
Ниже приведен список GDI функций, поддержка которых в метафайлах была изменена с Microsoft Windows 3.0:
AnimatePalette
BitBlt
CreatePalette
CreatePatternBrush
DeleteObject
DibBitBlt
DibCreatePatternBrush
DibStretchBlt
RealizePalette
ResizePalette
StretchBlt
Не все GDI функции могут быть использованы в метафайлах, а только те, которые используют заголовок устройства отображения в качестве первого параметра.
Структура записей Enhanced метафайлов
Enhanced метафайлы имеют свою собственную структуру, которая похожа на структуру записей стандартных метафайолв, но является полностью 32-разрядной:
typedef struct _EnhancedMetaRecord
{
DWORD Function; /* Номер функции (определено в WINGDI.H) */
DWORD Size; /* Общий размер записи в байтах */
DWORD Parameters[]; /* параметры */
} EMFRECORD;
Фунции, поддерживаемые EMFописаны в WINDOWS.H и начинаются с преффикса EMR_*.
Size общий размер записи в байтах, включая поля Size и Function. Минимальное значение равно 8.
Parameters массив параметров, используемых GDI функцией. Параметры следуют в обратном порядке, чем в вызове функции. Например, два параметра для LineTo(X, Y) будут следовать, как Y и X.
EMF метафайл может состоять из любых из 97 типов записей, но 2 типа должны присутствовать обязательно. Это заголовочная запись (1) и Заглушка (14).
Запись |
Номер |
Запись |
Номер |
EMR_ABORTPATH |
68 |
EMR_POLYLINE |
4 |
EMR_ANGLEARC |
41 |
EMR_POLYLINE16 |
87 |
EMR_ARC |
45 |
EMR_POLYLINETO |
6 |
EMR_ARCTO |
55 |
EMR_POLYLINETO16 |
89 |
EMR_BEGINPATH |
59 |
EMR_POLYPOLYGON |
8 |
EMR_BITBLT |
76 |
EMR_POLYPOLYGON16 |
91 |
EMR_CHORD |
46 |
EMR_POLYPOLYLINE |
7 |
EMR_CLOSEFIGURE |
61 |
EMR_POLYPOLYLINE16 |
90 |
EMR_CREATEBRUSHINDIRECT |
39 |
EMR_POLYTEXTOUTA |
96 |
EMR_CREATEDIBPATTERNBRUSHPT |
94 |
EMR_POLYTEXTOUTW |
97 |
EMR_CREATEMONOBRUSH |
93 |
EMR_REALIZEPALETTE |
52 |
EMR_CREATEPALETTE |
49 |
EMR_RECTANGLE |
43 |
EMR_CREATEPEN |
38 |
EMR_RESIZEPALETTE |
51 |
EMR_DELETEOBJECT |
40 |
EMR_RESTOREDC |
34 |
EMR_ELLIPSE |
42 |
EMR_ROUNDRECT |
44 |
EMR_ENDPATH |
60 |
EMR_SAVEDC |
33 |
EMR_EOF |
14 |
EMR_SCALEVIEWPORTEXTEX |
31 |
EMR_EXCLUDECLIPRECT |
29 |
EMR_SCALEWINDOWEXTEX |
32 |
EMR_EXTCREATEFONTINDIRECTW |
82 |
EMR_SELECTCLIPPATH |
67 |
EMR_EXTCREATEPEN |
95 |
EMR_SELECTOBJECT |
37 |
EMR_EXTFLOODFILL |
53 |
EMR_SELECTPALETTE |
48 |
EMR_EXTSELECTCLIPRGN |
75 |
EMR_SETARCDIRECTION |
57 |
EMR_EXTTEXTOUTA |
83 |
EMR_SETBKCOLOR |
25 |
EMR_EXTTEXTOUTW |
84 |
EMR_SETBKMODE |
18 |
EMR_FILLPATH |
62 |
EMR_SETBRUSHORGEX |
13 |
EMR_FILLRGN |
71 |
EMR_SETCOLORADJUSTMENT |
23 |
EMR_FLATTENPATH |
65 |
EMR_SETDIBITSTODEVICE |
80 |
EMR_FRAMERGN |
72 |
EMR_SETMAPMODE |
17 |
EMR_GDICOMMENT |
70 |
EMR_SETMAPPERFLAGS |
16 |
EMR_HEADER |
1 |
EMR_SETMETARGN |
28 |
EMR_INTERSECTCLIPRECT |
30 |
EMR_SETMITERLIMIT |
58 |
EMR_INVERTRGN |
73 |
EMR_SETPALETTEENTRIES |
50 |
EMR_LINETO |
54 |
EMR_SETPIXELV |
15 |
EMR_MASKBLT |
78 |
EMR_SETPOLYFILLMODE |
19 |
EMR_MODIFYWORLDTRANSFORM |
36 |
EMR_SETROP2 |
20 |
EMR_MOVETOEX |
27 |
EMR_SETSTRETCHBLTMODE |
21 |
EMR_OFFSETCLIPRGN |
26 |
EMR_SETTEXTALIGN |
22 |
EMR_PAINTRGN |
74 |
EMR_SETTEXTCOLOR |
24 |
EMR_PIE |
47 |
EMR_SETVIEWPORTEXTEX |
11 |
EMR_PLGBLT |
79 |
EMR_SETVIEWPORTORGEX |
12 |
EMR_POLYBEZIER |
2 |
EMR_SETWINDOWEXTEX |
9 |
EMR_POLYBEZIER16 |
85 |
EMR_SETWINDOWORGEX |
10 |
EMR_POLYBEZIERTO |
5 |
EMR_SETWORLDTRANSFORM |
35 |
EMR_POLYBEZIERTO16 |
88 |
EMR_STRETCHBLT |
77 |
EMR_POLYDRAW |
56 |
EMR_STRETCHDIBITS |
81 |
EMR_POLYDRAW16 |
92 |
EMR_STROKEANDFILLPATH |
63 |
EMR_POLYGON |
3 |
EMR_STROKEPATH |
64 |
EMR_POLYGON16 |
86 |
EMR_WIDENPATH |
66 |
Таблица цветов
EMF файл также может содержать таблицу цветов, используемую при отображении изображения. По умолчанию, файл не содержит таблицу цветов и использует системную палитру.
Поле NumPalEntries заголовка EMF файла указывает на количество цветов в таблице и равно 0 если таблица отсутствует. Если таблица присутствует, то она находится в конечной записи-заглушке:
typedef struct _EndOfRecord
{
DWORD Function; /* Номер функции (14) */
DWORD Size; /* Размер записи в байтах */
DWORD NumPalEntries; /* ККоличество цветов палитре */
DWORD OffPalEntries; /* Смещение первого цвета */
PALENT Palette[]; /* Палитра */
DWORD OffToEOF; /* Смещение о тначала записи */
} ENDOFRECORD;
Function Номер функции. Для заглушки всегда равен 14.
Size общий размер записи в байтах. Для записи не содержаещй палитры равен 20.
NumPalEntries количество цветов в палитре. Значение переписывается из поля NumPalEntries заголовка.
OffPalEntries указывает позицию первого значения палитры от начала записи.
Palette массив стурктур PALENT. Поле отсутвует, если палитры нет.
OffToEOF смещение от начала записи. Равно значению поля Size.
Структура PALENT:
typedef struct _PaletteEntry
{
BYTE Red; /* */
BYTE Green; /* */
BYTE Blue; /* */
BYTE Flags; /* */
} PALENT;
Red, Green, и Blue содержат цветовые компоненты определения цвета.
Flags может принимать значения:
0x01 |
цвет используется для анимации |
0x02 |
|
0x04 |
Цвет не соответствует системной палитре |
GDI Comment
Одной из важных особенностей EMF формата является возможность использования скрытых данных в файле. В отличие от escape-последовательностей WMF, комментарий GDI может содержать любой тип данных, полностью независящий от внешних устройств
GDICOMMENT запись имеет формат:
typedef struct _GdiCommentRecord
{
DWORD Function; /* Номер функции (70) */
DWORD Size; /* Размер записи в байтах */
DWORD SizeOfData; /* Размер данных в байтах */
BYTE Data[]; /* Комментарий */
} GDICOMMENTRECORD;
Function номер функции. Для GDI комментария всегда равен 70.
Size Общий размер записи в байтах. Для пустой записи комментария равен 12
SizeOfData Размер записи Data в байтах.
Data сам комментарий.
GDI комментарии могут содержать несколько определенных типов комментариев:
Тип комментария |
Содержимое |
Public |
Содержит метафайл |
BeginGroup/EndGroup |
Содержит коллекцию метафайлов и строк описания |
Multiformats |
Содержит метафайл и Encapsulated PostScript данные |
Заголовок Public комментария выглядит следующим образом:
typedef struct _GdiCommentMetafile
{
DWORD Identifier; /* ID комментария(0x43494447) */
DWORD Comment; /* ID типа комментария (0x80000001) */
DWORD Version; /* Версия метафайла */
DWORD Checksum; /* Контрольная сумма метафайла */
DWORD Flags; /* Флаг (0) */
DWORD Size; /* Размер данных в байтах */
} GDICOMMENTMETAFILE;
Identifier содержит значение 0x43494447 идентифицирующее комментарий.
Comment содержит значение 0x80000001 идентифицирующее структуру Public комментария
Version содержит значение версии метафайла. Обычно это 0x00000001.
Checksum контрольная сумма данных метафайла.
Flags всегда содержит 0.
Size Размер данных метафайла в байтах.
BeginGroup / EndGroup комментарии содержат один или несколько EMF объектов. BeginGroup указывает начало списка, EMF записей, и заканчивается EndGroup структурой. Такие группы могут быть вложенными.
typedef struct _GdiCommentBeginGroup
{
DWORD Identifier; /* ID комментария(0x43494447) */
DWORD Comment; /* BeginGroup ID (0x00000002) */
LONG BoundsLeft; /* Левая точка прямоугольника */
LONG BoundsRight; /* Правая точка прямоугольника */
LONG BoundsTop; /* Верхняя точка прямоугольника */
LONG BoundsBottom; /* Нижняя точка прямоугольника */
DWORD SizeOfDescrip; /* Количество символов в описании */
} GDICOMMENTBEGINGROUP;
Identifier содержит значение 0x43494447 идентифицирующее комментарий
Comment содержит значение 0x00000002 идентифицирующее структуру BeginGroup комментария.
BoundsLeft, BoundsRight, BoundsTop, и BoundsBottom определяют область вывода изображения.
SizeOfDescrip количество Unicode символов строки описания. Строка,если она присутствует, должна следовать сразу за заголовком. Поле равно 0, если строки нет.
EndGroup содержит только идентификационный заголовок без данных:
typedef struct _GdiCommentEndGroup
{
DWORD Identifier; /* комментария ID (0x43494447) */
DWORD Comment; /* EndGroup ID (0x00000003) */
} GDICOMMENTENDGROUP;
Identifier содержит значение 0x43494447 идентифицирующее комментарий.
Comment содержит значение 0x00000003 идентифицирующее структуру EndGroup комментария.
Multiformats комментарий используется для хранения метафайлов и Encapsulated PostScript (EPS) данных. Этот комментарий начинается с заголовка, затем идет одно или последовательност изображений:
typedef struct _GdiCommentMultiFormats
{
DWORD Identifier; /* ID комментария(0x43494447) */
DWORD Comment; /* Multiformats ID (0x40000004) */
LONG BoundsLeft; /* Левая точка прямоугольника */
LONG BoundsRight; /* Правая точка прямоугольника */
LONG BoundsTop; /* Верхняя точка прямоугольника */
LONG BoundsBottom; /* Нижняя точка прямоугольника */
DWORD NumFormats; /* Количество объектов в структуре */
EMRFORMAT Data[]; /* Массим объектов */
} GDICOMMENTMULTIFORMATS
Identifier содержит значение 0x43494447 идентифицирующее комментарий.
Comment содержит значение 0x40000004 идентифицирующее структуру Multiformats комментария.
BoundsLeft, BoundsRight, BoundsTop, и BoundsBottom определяют область вывода изображения.
NumFormats кличество структур EMRFORMAT.
Data сами структуры EMRFORMAT.
typedef struct _EmrFormat
{
DWORD Signature; /* Идентификатор формата */
DWORD Version; /* Версия формата */
DWORD Data; /* Размер данных в байтах */
DWORD OffsetToData; /* Смещение в байтах */
} EMRFORMAT;
Signature содержит значение 0x464D4520 идентифицирующее структуру метафайла, и значение 0x46535045 идентифицирующее Encapsulated PostScript файл.
Version версия данных. Для EPS содержит версию EPS файла. Для EMF обычно равно 0x00000001.
Data размер содержащейся структуры в байтах.
OffsetToData содержит смещение данных относительно начала структуры GDICOMMENTMULTIFORMATS.
Copyright © 1996, 1994 O'Reilly & Associates, Inc. All Rights Reserved.