Вход/Регистрация
Графика DirectX в Delphi
вернуться

Краснов Михаил

Шрифт:

var

desc : TDDSURFACEDESC2;

i, j : Integer;

hRet : HRESULT; begin

ZeroMemory (@desc, SizeOf(desc));

desc.dwSize := SizeOf (desc);

hRet := FDDSZoom.Lock (nil, desc, DDLOCK_WAIT, 0); if Failed (hRet) then begin Result := hRet;

Exit;

end;

for i := 0 to 99 do // Цикл по всем точкам поверхности

for j := 0 to 99 do

// Выделяем точки, располагающиеся за пределами круга "лупы"

if sqr (i - 50} + sqr (j - 50) > 50 * 50 then // Заполняем черным

PWord (Integer(desc.IpSurface) + j * desc.lPitch + i * 2)^ := 0;

Result := FDDSZoom.Unlock (nil);

end;

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

// Квадрат, задающий степень увеличения

SetRect (wrkRect, mouseX + 25, mouseY + 25, mouseX + 75, mouseY + 75);

// Растягиваем участок фона

FDDSZoom.Bit (nil, FDDSBackGround, SwrkRect, DDBLT_WAIT, nil);

Circle; // Заполняем черным часть квадрата

// Выводим с цветовым ключом

FDDSBack.BltFast (mouseX, mouseY, FDDSZoom, nil,

DDBLTFAST_WAIT or DDBLTFAST_SRCCOLORKEY);

Выглядит просто и эффектно, но в решении содержится проблема: оно подходит только для черного цвета. Если в качестве ключа использовать любой другой цвет, то на точки, заполненные цветом ключа "вручную", прозрачность распространяться не будет: прозрачными окажутся только участки этого же цвета, но окрашенные вызовом метода поверхности. Разрешить означенную проблему мне не удалось, поскольку плохо понятно, как DirectDraw удается различать такие участки.

Черный цвет для использования его в качестве ключа подходит для этого фона, но пример будет некрасиво работать с фоном, подобным рис. 3.11, где присутствует масса участков именно черного цвета.

В проекте каталога Ех22 приведено другое решение задачи, менее элегантное, но работающее с любыми цветовыми ключами.

Здесь, помимо поверхности FDDSZoom, введена поверхность FDDSDouble. Для первой из них в качестве ключа взят чистый зеленый цвет, как отсутствующий на фоне. Вторая поверхность создается путем загрузки изображения-шаблона - зеленый квадрат с черным кругом посередине. Ключом для нее установлен черный цвет.

Теперь на поверхность лупы последовательно помещаем растянутый участок фона, затем ограничивающий шаблон:

SetRect (wrkRect, mouseX + 25, mouseY + 25, mouseX + 75, mouseY +- 75);

// Растягиваем участок фона

FDDSZoom.Blt (nil, FDDSBackGround, @wrkRect, DDBLT_WAIT, nil);

// Вместо черных участков шаблона останется увеличенный фрагмент

FDDSZoom.BltFast (О, О, FDDSDouble, nil,

DDBLTFASTJMAIT or DDBLTFAST^SRCCOLORKEY);

// Зеленая канва не воспроизведется FDDSBack.BltFast (mouseX, mouseY, FDDSZoom, nil,

DDBLTFAST_WAIT or DDBLTFAST_SRCCOLORKEY);

Позже мы вернемся к задаче с лупой и получим искаженное изображение в ее круге.

Палитры

Для хранения отдельного набора цветовых составляющих палитры используется переменная типа TPaietteEntry. Переменная типа iDirectDrawPaiette, как мы знаем из предыдущих примеров, служит для установления определенной палитры 8-битной поверхности. Обычно такая палитра загружается из растра.

В любой момент времени мы можем получить набор палитры и модифицировать его, как это делается в следующем нашем примере (проект каталога Ех23). За основу взят проект с перемещающимся драконом, но здесь с течением времени экран становится тусклым, имитируется суточная смена освещенности. Дойдя до некоторой фазы, восстанавливается первоначальная яркость. Такой эффект постепенного угасания называется fade (затухание). Разберем, как он создается.

Для хранения первоначальной палитры предназначен массив:

DefPal : Array[0..255] of TPaietteEntry;

Массив заполняется после загрузки палитры из растра, для чего вызывается

Метод Палитры GetEntries:

hRet := FDDpal.GetEntries(0, 0, 256, @DefPal);

if Failed (hRet) then ErrorOut(hRet, 'Palette GetEntries');

При каждом перемещении образа во всех составляющих текущей палитры убавляются веса цветов, используется локальный массив palEntries:

// Получаем составляющие текущей палитры экрана FDDpal.GetEntries(О, О, 256, @PalEntries) ;

for i := 0 to 255 do begin // Цикл по всем элементам палитры

if PalEntries[i].peRed > Step then PalEntries[i].peRed :=

PalEntries[i].peRed - Step;

if PalEntries[i].peGreen > Step then PalEntries[i].peGreen :=

PalEntries [i] .peGreen - Step

if PalEntries[i].peBlue > Step then PalEntries[i].peBlue :=

PalEntries[i].peBlue - Step;

end;

  • Читать дальше
  • 1
  • ...
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • ...

Ебукер (ebooker) – онлайн-библиотека на русском языке. Книги доступны онлайн, без утомительной регистрации. Огромный выбор и удобный дизайн, позволяющий читать без проблем. Добавляйте сайт в закладки! Все произведения загружаются пользователями: если считаете, что ваши авторские права нарушены – используйте форму обратной связи.

Полезные ссылки

  • Моя полка

Контакты

  • chitat.ebooker@gmail.com

Подпишитесь на рассылку: