Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Лекция_5(слайды)_2012.doc
Скачиваний:
1
Добавлен:
21.08.2019
Размер:
496.13 Кб
Скачать

Лекция №5. Работа с функция GDI. Захват изображения.

Альтернативный метод сохранения изображений представлен в виде метафайлов (metafile). Метафайл в строгом смысле рисунка не хранит, он сохраняет только последовательность команд (вызовов функций GDI) формирующих изображение.

Общие операции над метафайлами можно разделить на операции по созданию метафайла, то есть его записи и операции по воспроизведению метафайла на нужном контексте устройства.

Контекст для метафайла

Контекст для метафайла позволяет записывать команды GDI в файл, а затем проиграть такой файл на физическом устройстве вывода. Файл может находиться в памяти или на диске.

1) Для создания контекста метафайла используется функция CreateMetaFile:

HDC WINAPI CreateMetaFile(LPCSTR lpszFileName);

Параметр lpszFileName указывает на строку, содержащую путь к имени файла, в который будут записаны команды GDI, или NULL. Если параметр равен NULL, то создается метафайл в оперативной памяти.

2) После выполнения рисования в контексте метафайла следует закрыть метафайл, вызвав функцию CloseMetaFile :

HMETAFILE WINAPI CloseMetaFile(HDC hdc);

Функция закрывает метафайл для контекста hdc и возвращает идентификатор метафайла.

3) Если имеется идентификатор метафайла, то метафайл можно скопировать в обычный дисковый файл, с помощью функции CopyMetaFile :

HMETAFILE WINAPI CopyMetaFile(HMETAFILE hmf,

LPCSTR lpszFileName);

Параметр hmf определяет метафайл, параметр lpszFileName содержит путь к имени файла, в который будет записан метафайл .

4) Можно проиграть метафайл в контексте отображения или контексте устройства, вызвав функцию PlayMetaFile:

BOOL WINAPI PlayMetaFile(HDC hdc, HMETAFILE hmf);

5) При помощи функции DeleteMetaFile можно удалить метафайл:

BOOL WINAPI DeleteMetaFile(HMETAFILE hmf);

При удалении метафайла освобождается оперативная память, занятая метафайлом. Если метафайл был создан как дисковый файл, функция DeleteMetaFile не удаляет его с диска.

6) Для того чтобы воспользоваться метафайлом, хранящимся в виде дискового файла, его нужно загрузить функцией GetMetaFile, указав в качестве параметра путь к соответствующему файлу:

HMETAFILE WINAPI GetMetaFile(LPCSTR lpszFileName);

Для хранения метафайлов требуется значительно меньше места, чем для хранения растровых изображений. В то же время для отображения метафайлов требуется обычно больше времени, чем для вывода растровых изображений.

Использование сообщения WM_PAINT

Сообщение WM_PAINT система посылает окну во всех случаях, требующих перерисовки клиентской области окна, например при наступлении следующих событий:

  1. Изменились размеры или местоположение окна;

  2. Клиентская область была полностью или частично закрыта другим окном или выпадающим меню, а теперь закрывающий объект исчез;

  3. Приложение вызвало одну из функций работы с полосами прокрутки.

Кроме того, приложение может само инициировать посылку сообщения WM_PAINT посредством вызова одной из функций InvalidateRect, InvalidateRgn или UpdateWindow.

Функция UpdateWindow посылает сообщение WM_PAINT непосредственно в оконную процедуру, минуя очередь сообщений приложения.

Операции передачи образов

Операции по обмену блоками бит (bit block transfer, BLT) или тернарные растровые операции (ternary raster operation) – механизм, осуществляющий передачу растровых изображений между различными контекстами устройств.

Основная идея растровых операций заключается в организации обмена данными между двумя контекстами устройств. В Windows-приложении можно осуществить передачу изображения:

  1. между битмапом, выбранным в совместимый контекст устройства и реальным устройством на котором необходимо изображение показать;

2) между двумя битмапами;

  1. с реального устройства в битмап;

  2. с реального устройства на другое устройство.

GDI содержит 3 функции, осуществляющих такую передачу изображений — PatBlt, BitBlt и StretchBlt:

BOOL PatBlt(hDC, nX, nY, nWidth, nHeight, dwROP);

BOOL BitBlt(hDestDC, nDestX, nDestY, nDestWidth, nDestHeight, hSrcDC, nSrcX, nSrcY, dwROP);

BOOL StretchBlt(hDestDC, nDestX, nDestY, nDestWidth, nDestHeight, hSrcDC, nSrcX, nSrcY, nSrcWidth, nSrcHeight, dwROP);

Все три функции строят результирующее изображение на контексте–приемнике, используя в качестве исходных данных:

1. изображение, создаваемое на приемнике при закраске фона текущей кистью, выбранной в контекст–приемник (это называется образцом, pattern).

2. изображение, существующее на контексте–источнике (исходное изображение, source).

3. изображение, существующее в данный момент на контексте–приемнике (имеющееся изображение, destination).

В процессе выполнения растровой операции три исходных изображения (битовых последовательности p, d, s) комбинируются и получается результирующее изображение. Код выполняемой операции задается параметром dwROP — индексом тернарной растровой операции.

Предположим, что биты, определяющие битмап совместимого контекста обозначают буквой S (source – источник, ресурс), биты заливки – буквой Р (pattern - образец), а биты, на которых будет прорисовываться изображение – буквой D (destination – назначение, место назначения). Операции, которые выполняются с битами S, P, D: а – побитовое И, n – побитовое НЕТ, о – побитовое ИЛИ, х – побитовое исключающее ИЛИ.

Х1 Х2 И Х1 НЕТ Х1 Х2 ИЛИ Х1 Х2 Исключающее ИЛИ

0 0 0 0 1 0 0 0 0 0 0

0 1 0 1 0 0 1 1 0 1 1

1 0 0 1 0 1 1 0 1

1 1 1 1 1 1 1 1 0

Обозначив знак операции как Ор, то действия с битами можно записать таким образом: PSОр. То есть необходимо взять пиксель паттерны и прорисовываемого битмапа и произвести над ними операцию (бинарная растровая операция). Если в операции участвует три операнда, то получим DPSОр1Ор2 (тернарная растровая операция).

Определить индекс операции PSx и DPSxx.

P 1 1 1 1 0 0 0 0

S 1 1 0 0 1 1 0 0

D 1 0 1 0 1 0 1 0

PSx 0 0 1 1 1 1 0 0 = 0x3c ????

DPSxx 1 0 0 1 0 1 1 0 = 0x96 ????

DPx 0 1 0 1 1 0 1 0 = 5A ????

В документации по SDK имеется таблица, перечисляющая индексы 256 возможных растровых операций, их имена и короткое пояснение к каждой операции. Имена присвоены только 15 наиболее употребляемым операциям. Таблица, представленная в документации имеет следующий вид:

Number

Hex ROP

Boolean function

Common Name

0

00000042

0

BLACKNESS

...

0D

000D0B25

PDSnaon

...

Поле «Hex ROP» – индекс тернарной растровой операции (используется в качестве параметра dwROP).

Поле «Boolean function» содержит пояснение к выполняемой операции;

Поле «Common name» — имя растровой операции, если оно назначено.

Основные коды растровых операций приведены в таблице.

Функция StretchBlt

Скопировать bitmap с совместимого на основной контекст с масштабированием можно с помощью функции StretchBlt(). Эта функция описана следующим образом:

StretchBlt(HDC, int, int, int, int, HDC, int, int, int, int, DWORD);

Устройством приёмником должно быть окно, в которое необходимо вывести изображение и которое представляется своим контекстом. В качестве устройства источника (псевдоустройства) необходимо создать в памяти область, которая по своим возможностям должна быть совместима с экраном и в которую сначала необходимо поместить изображение, а затем скопировать это изображение в окно приёмник. Поэтому функция StretchBlt() должна получать через свои параметры дескрипторы обоих контекстов.

Первый и шестой аргументы функции – хэндлы окна (hDC) и совместимого контекста (hCompatibleDC) соответственно. Одиннадцатый аргумент функции StretchBlt() – это код растровой операции.

Первые пять аргументов описывают тот прямоугольник на экране, в который будет вписан битмап. Ту часть битмапа, которая будет вписана в прямоугольник на экране, описывают следующие пят аргументов.

При масштабировании, используя функцию StretchBlt возможно два случая:

– изображение увеличивается, то некоторые строки (столбцы) будут дублироваться;

– изображение уменьшается, то некоторые строки (столбцы) будут комбинироваться в одну строку (столбец).

Объединение строк (столбцов) при сжатии может осуществляться различными способами, которые выбираются с помощью функции:

UINT SetStretchBltMode(hDC, nMode);

параметр nMode задает режим объединения строк:

BLACKONWHITE

выполняется операция И (AND). В результате получается, что черный цвет имеет "приоритет" над белым — сочетание черного с белым рассматривается как черный

WHITEONBLACK

выполняется операция ИЛИ (OR). При этом "приоритет" принадлежит белому над черным — сочетание черного с белым дает белый

COLORONCOLOR

при этом происходит простое исключение строк (столбцов).

HALFTONE 1

только в Win32 API; происходит усреднение цвета объединяемых точек.

Функция BitBlt

BOOL BitBlt(hDestDC, nDestX, nDestY, nDestWidth, nDestHeight, hSrcDC, nSrcX, nSrcY, dwROP);

Функция осуществляет передачу изображений между двумя контекстами устройств, при этом передается прямоугольный фрагмент, который на контексте-приемнике и на контексте-источнике имеет одинаковые размеры. Для задания координат и размеров используется логическая система координат, и логический размер изображения в обеих системах может быть различным.

Отдельно надо рассмотреть случай, когда один из контекстов является цветным, а другой черно–белым — при этом особым образом осуществляется преобразование цветов:

– при переходе от монохромного к цветному цвет, закодированный 1, соответствует цвету фона (задаваемому функцией SetBkColor), а цвет 0 — цвету текста (функция SetTextColor).

– при переходе от цветного к монохромному считается, что если цвет точки совпадает с цветом фона, то эта точка кодируется цветом 1, иначе 0.

Функция PatBlt не может рисовать битовые изображения, но используется для закраски прямоугольных областей экрана. Эта функция имеет имя PatBlt :

BOOL WINAPI PatBlt(

HDC hdc, // контекст для рисования

int nX, // x-координата верхнего левого угла закрашиваемой области

int nY, // y-координата верхнего левого угла закрашиваемой области

int nWidth, // ширина области

int nHeight, // высота области

DWORD dwRop); // код растровой операции

При использовании этой функции можно закрашивать области экрана с использованием следующих кодов растровых операций: PATCOPY, PATINVERT, PATPAINT, DSTINVERT, BLACKNESS, WHITENESS.

Возвращаемое функцией PatBlt значение равно TRUE при успешном завершении или FALSE при ошибке.

Битовые изображения

В операционной системе Windows используются два формата битовых изображений - аппаратно-зависимый DDB (device-dependent bitmap ) и аппаратно-независимый DIB (device-independent bitmap).

Битовое изображение DDB есть набор бит в оперативной памяти, который может быть отображен на устройстве вывода (например, выведен на экран видеомонитора или распечатан на принтере). Внутренняя структура изображения DDB жестко привязана к аппаратным особенностям устройства вывода. Поэтому представление изображения DDB в оперативной памяти полностью зависит от устройства вывода.

Иногда битовые изображения называют растровыми изображениями, подчеркивая тот факт, что его можно рассматривать как совокупность строк растра (горизонтальных линий развертки).

Аппаратно-независимое битовое изображение DIB содержит описание цвета пикселов изображения, которое не зависит от особенностей устройства отображения. Операционная система Windows после соответствующего преобразования может отобразить такое изображение на любом устройстве вывода.

Первые версии операционной системы Windows могли работать только с аппаратно-зависимыми изображениями DDB.

Кроме битовых изображений используются так называемые векторные изображения.

Чтобы использовать формат DDB в контексте устройства, он должен иметь организацию цвета этого контекста устройства. Поэтому, аппаратно-зависимый растровый формат (DDB) часто называется совместимым точечным рисунком (compatible bitmap) и обычно имеет производительность в GDI выше, чем аппаратно-независимый растровый формат (DIB).

Совместимые точечные рисунки используются, чтобы захватывать изображения и создавать точечные рисунки во время выполнения программы для меню.

При работе с DDB изображениями цвет конкретной точки определяется непосредственно настройками аппаратуры и остается независим от самого растрового изображения. То есть попытка отобразить одно и то же изображение при различных настройках (допустим, при различных используемых палитрах), приводит к искажению цветов исходного изображения. Помимо этого при попытке отобразить одно и тоже изображение на разных устройствах требуется преобразовывать информацию о кодировании цветов.

Часто для представления в памяти используются именно формат DDB, так как его отображение выполняется быстрее и он как правило занимает меньше ресурсов.

  • Получение битмапа; Для получения хендла битмапа можно либо создать новый объект и получить его хендл, либо загрузить уже имеющееся изображение. Так как во всех современных версиях Windows битмапы реально хранятся в виде независимых от устройства, то для загрузки изображения в виде DDB надо осуществить преобразование независимого битмапа в зависимый. Это делается либо автоматически — при загрузке битмапа из ресурсов приложения, либо это надо осуществить непосредственно в вашем приложении.

  • Формирование или коррекция битмапа; Для рисования на битмапе создается контекст устройства, ассоциированный с данным битмапом, после чего все функции GDI, применяемые к этому контексту, реально взаимодействуют с битмапом и формируют его изображение. Для выполнения этой задачи предназначен совместимый контекст устройства (compatible DC, memory DC), который предназначен именно для этого.

  • Отображение битмапа на контексте устройства; GDI не содержит специальных функций для отображения DDB. Вместо этого необходимо ассоциировать битмап с контекстом устройства (как и для рисования), а затем осуществить передачу изображения с одного контекста на другой — для этого в GDI содержится специальный набор функций, называемых функциями передачи растровых изображений или, дословно, функциями для передачи блоков бит (Bit Block Transfer, BLT — произносится «блит»)

Одним из объектов, с которым работает GDI, является битовая карта или растр, дескриптор которого имеет тип HBITMAP. Битовая карта может быть создана несколькими способами, например посредством вызова функции:

HBITMAP CreateCompatibleBitmap (HDC hdc, int nWidth, int nHeight);

Аргументы функции описывают контекст устройства, с которым будет совместим растр, и размеры создаваемого растра. Полученный подобным образом растр является аппаратно-зависимым и не подходит для обмена информацией между различными устройствами. Для решения этой проблемы в системе Windows была введена поддержка аппаратно-независимых растров (DIB - Device Independent Bitmap). Главным образом аппаратно-независимый растр используется для хранения графических данных на внешнем носителе в виде BMP-файлов.

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]