лабораторные на Pasca (Кудрявцев)l
.pdfУправление цветами и шаблонами заливки (заполнения) |
213 |
|
|
Ее параметры имеют такое же назначение, как и в процедуре DrawPoly. Отличие только в том, что координаты первой и послед- ней вершин многоугольникамогут не совпадать. Все равно они бу- дут соединены линией, и внутренность фигуры будетзалита.
Пример.
Uses Graph;
{$I initgraph.pas } Const
our_figure: Array [1..4] of PointType =
(( x : 319 ; y : 40 ), |
{задание координат} |
( x : 398 ; y : 146 ), |
{концов отрезков } |
( x : 240 ; y : 146 ), |
|
( x : 400 ; y : 40 )); |
|
Begin |
|
GrInit; |
{задание шаблона} |
SetFillStyle (InterLeaveFill, Red); |
|
FillPoly (SizeOf (our_figure) div SizeOf (PointType), |
{рисование фигуры} |
Our_figure); |
|
Readln; |
|
CloseGraph |
|
End. |
|
Универсальная процедура
FloodFill (X,Y: Integer; Border: Word)
заливает всю область вокруг точки (X,Y), ограниченную линиями цвета Border. Например, если точка (X,Y) находится внутри области, ограниченной окружностью, то вся область будет залита по шабло- ну и цветом, установленными процедурами SetFillPattern или SetFillStyle. Если же точка будет находится вне этой области, то за- литым будетвесь экран, за исключением этой области.
Опрос и установка цветов пера и фона. Различные адаптеры под-
держивают разное количество цветов, выводимых одновременно на экран в графическом режиме. Но для всех BGI–драйверов оно огра- ничено диапазоном 0..15. Нумерация и названия цветов таковы:
Black = 0 |
Черный |
Blue = 1 |
Синий |
Green = 2 |
Зеленый |
Cyan = 3 |
Голубой |
Red = 4 |
Красный |
Magenta = 5 |
Фиолетовый |
Управление цветами и шаблонами заливки (заполнения) |
215 |
|
|
Стандартная палитра режима 320×200 адаптера CGA (палитра C0) состоит всего лишь из четырех цветов:
0–черный; 2–малиновый; 1–синий; 3–белый.
А для того же адаптера CGA в режиме CGAHi (640×200) палитра со- стоит из двух цветов: черного (0) и белого (1).
Числа от 0 до 15, которые используются для обозначения цветов, определяют цветовые атрибуты или “программные” цвета. Каждо- му “программному” цвету присваивается “аппаратный” цвет из так называемой палитры. Например, для адаптера EGA, выводящего одновременно до 16 цветов, программные цвета выбираются из полной палитры в 64 цвета, имеющейся в этом адаптере. А в адап- тере VGA аппаратная палитра содержит 256 цветов. Для адаптера CGA полная палитра составляет 16 аппаратных цветов, но на экране может одновременно появиться лишь 4 цвета одной из четырех программных палитр (C0 ... C3).
Для управления соответствием между программными и аппарат- ными цветами в модуле Graph предусмотрен ряд процедур, охваты- вающих практически все возможные операции с палитрой.
В модулеGraph определен тип для описания палитры:
Const
MaxColors = 15; {максимальный программный номер цвета}
Type
PaletteType = Record
Size: Byte;
Colors: Array [0..MaxColors] of ShortInt; End;
Поле Size содержит количество цветов в палитре, а поле Colors со- держит действующие цвета в первых Size элементах массива.
Процедуры GetPalette и GetDefaultPalette возвращают в фактических параметрах значение PaletteType:
GetDefaultPalette (Var Palette: PaletteType);
GetPalette (Var Palette: PaletteType).
Первая возвращает набор цветов, который устанавливается при инициализации графического режима, т.е. по умолчанию, а вторая процедура возвращает текущий набор цветов.
Функция
GetPaletteSize: Word
Управление цветами и шаблонами заливки (заполнения) |
217 |
|
|
пущенных за день одним предприятием. Решить данную задачу ис- пользуя процедуру Bar3D с наложением столбцов один на другой.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 день |
2 день |
n–1 день |
n–2 день |
Рис. 1
1.n = 5; заполнение типа /// и === ;
2.n = 5; заполнение типа /// (тонкими линиями) и крупный горошек;
3.n = 6; заполнение типа === и косой клеткой;
4.n = 6; заполнение типа /// (тонкими линиями) и мелкий горошек;
5.n = 7; заполнение типа /// (тонкими линиями) и клеткой;
6.n = 5; заполнение типа === и косой клеткой;
7.n = 5; заполнение типа \\\\\ (тонкими линиями) и клеткой;
8.n = 6; заполнение типа //// (тонкими линиями) и частой клеткой.
II. Написать программу построения диаграммы с элементами, имеющими вид, показанный на рис. 2. Высота столбцов и шаблон заполнения зада- ются случайным образом. Представить эти же данные секторной диа- граммой (секторы пропорциональны заданным числам).
Pис. 2
218
Лабораторная работа № 19
БИТОВЫЕ ГРАФИЧЕСКИЕОПЕРАЦИИ
Turbo Pascal позволяет организовать прямой доступ к каждому пик- селу экрана. Делается это функцией
GetPixel (X, Y: Integer),
которая возвращает значение типа Word – номер цвета пиксела с координатами (X,Y). Поскольку обычно номер цвета лежит в диапа- зоне 0..15 или меньше, значащим является только младший байт.
Управление пикселами заключается в возможности назначить цвет любому пикселу экрана. Процедура
PutPixel (X, Y: Integer; Color: Word)
«зажигает» на экране в точке с координатами (X,Y) пиксел цвета Color. На применении этой процедуры построен следующий при- мер.
Uses Graph, Crt;
{ $I initgraph.pas } Const
minx = 290; miny = 70; |
{левый верхний угол области} |
maxx = 350; maxy = 130; |
{правый нижний угол области} |
Nx = Succ(maxx – minx); |
{ширина области в пикселах} |
Ny = Succ(maxy – miny); |
{высота области в пикселах } |
Npixels = Nx * Ny; |
{число пикселов в области } |
Var |
{счетчик точек и их цвет} |
countpixels, Color: Word; |
|
X, Y: Integer; |
{координаты текущей точки} |
Begin |
{инициализация графики} |
GrInit; |
|
Color:= GetMaxColor; |
{цвет выводимых точек} |
countpixels:= 0; |
{обнуление счетчика точек} |
Repeat |
{случайные координаты} |
x:= minx + Random(Nx); |
|
y:= miny + Random(Ny); |
{точки в прямоугольнике } |
if GetPixel(X,Y) = Black then |
{если в точке (X,Y) } |
begin |
{ничего нет, то } |
PutPixel(X,Y,Color); |
{подсветить ее и } |
Inc(countpixels) |
{увеличить счетчик } |
end; |
|
Битовые графические операции |
219 |
|
|
until countpixels = Npixels; |
{пауза до нажатия клавиши } |
Repeat Until KeyPressed; |
|
Repeat |
{случайные координаты} |
x:= minx + Random(Nx); |
|
y:= miny + Random(Ny); |
{точки в прямоугольнике} |
if GetPixel(X,Y) = Color then |
{если точка (X,Y) } |
begin |
|
PutPixel(X,Y,Black); |
{светится, то “потушить” } |
Dec(countpixels) |
{ее и уменьшить счетчик } |
end; |
|
Until countpixels = 0; |
|
CloseGraph |
|
End. |
|
Работа с фрагментами изображения. Для запоминания в буфере и восстановления из него прямоугольныхфрагментов графического изображения используют процедуры
GetImage(X1,Y1,X2,Y2: Integer; Var BitMap)
и
PutImage(X1,Y1: Integer; Var BitMap; Mode: Word),
где (X1,Y1), (X2,Y2) – координаты левого верхнего и правого нижне- го углов области, а вместо бестипового параметра BitMap должна подставляться переменная – буфер, занимающая область памяти размера, необходимого для полного сохранения изображения. Для
определения этого размера используется функция
ImageSize(X1,Y1,X2,Y2: Integer): Word;
которая возвращает размер памяти в байтах, необходимый для со- хранения прямоугольной области экрана. Максимальный размер сохраняемого изображения не должен превышать 64 К.
Обратите внимание, что у процедуры PutImage, которая восстанав- ливает изображение из буфера BitMap в прямоугольник, указывает- ся всего одна точка (X1,Y1). Объясняется это тем, что в структуре BitMap первые два слова (четыре байта) содержат ширину и высоту в пикселах запомненного изображения.
В этой процедуре имеется возможность определять режим вывода изображения: можно суммировать изображение на экране и изо- бражение в буфере, можно уничтожать изображение, находящееся в определяемой области, можно инвертировать изображение, со-
Битовые графические операции |
221 |
|
|
repeat |
{ начало движения шарика} |
PutImage(Sx, Sy, P^, XORPut); |
{ вывод шарика } |
Delay(120); |
{ пауза} |
PutImage(Sx, Sy, P^, XORPut); |
{ стирание шарика } |
|
{ограничения на движения шарика |
if (Sx < 50) or (Sx > maxx – 50 – |
в пределах поля фона } |
|
|
2 * r) then Sxmove:= – Sxmove; |
|
if (Sy < 50) or (Sy > maxy – 50 – |
|
2 * r) then Symove:= – Symove; |
{следующая точка появления } |
Inc(Sx, Sxmove); |
|
Inc(Sy, Symove); |
{шарика на экране } |
until KeyPressed; |
{... пока не нажата клавиша} |
FreeMem(P, Size); |
{освобождение памяти буфера} |
CloseGraph |
{закрытие режима графики} |
End. |
|
В примере продемонстрирован алгоритм мультипликации. Ско-
рость движения картинки сильно зависит от разрешения экрана и количества цветов.
Обращаем внимание на стандартную связку:
Size:= ImageSize(X1, Y1, X2, Y2); |
{фрагмент в байтах } |
GetMem(P, Size); |
{размещение буфера} |
GetImage(X1, Y1, X2, Y2, P^); |
{фрагмент è в буфер} |
. . . . . . . . . . |
{вывод фрагмента(ов)} |
PutImage (X, Y, P^, ***Put); |
|
FreeMem(P,Size); |
{освобождение буфера} |
организующую хранение динамического фрагмента через перемен-
ную P типа Pointer.
КОНТРОЛЬНЫЕ ЗАДАНИЯ
I. Составить программу, моделирующую абсолютно упругий центральный удар двух шаров с массами m1 и m2 движущихся со скоростями v1 и v2.
a)m1 = m2 , v1 = 2v2 , шары движутся навстречу друг другу;
b)m1 = m2 , v1 = v2 , шары движутся навстречу друг другу;
c)m1 = 2m2 , v1 = 2v2 , шары движутся навстречу друг другу;
d)m1 = 0.5m2 , v1 = v2 , шары движутся навстречу друг другу;
e)m1 = 2m2 , v1 = 2v2 , один шар догоняет другой;
f)m1 = m2 , v1 = 0.5v2 , один шар догоняет другой;
g)m1 = 0.5m2 , v1 = 2v2 , один шар догоняет другой;