Практическое освоение типовых приемов построения движущихся графических образов на примере создания программ управления движением набора простых графических объектов.
· Изучение графических процедур и функций языка Турбо Паскаль;
· Исследование различных методов построения графических движущихся объектов;
· Разработка программ, имитирующих движение простых графических объектов.
Наиболее простой метод имитации сложного движения образа - рисование фигуры как контура на наборе узловых точек с вызовом процедур преобразования координат узловых точек контура. При этом как рисование самой фигуры, так и преобразования координат узловых точек выполняется по простым и быстро работающим алгоритмам, и процесс перерисовки происходит почти незаметно для глаз даже на не слишком мощных ПК.
Вложение | Размер |
---|---|
modelirovanie_dvizheniya-shulepov.docx | 328.01 КБ |
Муниципальное общеобразовательное учреждение
гимназия № 56
Моделирование графических образов средствами движущихся графических объектов
Выполнил: Шулепов Владимир 11 а класс
Руководитель Колесниченко Е.В.
Г. Ижевск
Оглавление
Моделирование графических образов средствами
движущихся графических объектов
Шулепов Владимир 11 класс, МАОУ «Гимназия № 56»
Руководитель Колесниченко Елена Владимировна, учитель информатики
Цель работы
Практическое освоение типовых приемов построения движущихся графических образов на примере создания программ управления движением набора простых графических объектов.
Наиболее простой метод имитации сложного движения образа - рисование фигуры как контура на наборе узловых точек с вызовом процедур преобразования координат узловых точек контура. При этом как рисование самой фигуры, так и преобразования координат узловых точек выполняется по простым и быстро работающим алгоритмам, и процесс перерисовки происходит почти незаметно для глаз даже на не слишком мощных ПК.
Синтез динамических эффектов на экране монитора проводится чередованием набора образов, в той или иной степени моделирующим моменты какого-либо реального физического процесса. При этом для достижения приемлемых результатов следует учитывать психофизические особенности восприятия глазом быстрой смены образов, а также принципы и особенности формирования образов на экране монитора.
При прорисовке различных составляющих модели важно корректно и полно определить набор свойств составляющих модель объекта.
В работе представлены алгоритмы, позволяющие рисовать движущиеся объекты, использующие элементы окружностей, прямых линий и замкнутых фигур.
Начало машинной системы координат, направление осей, а также максимальные значения координат монитора показаны на рисунке
На рисунке приведена также машинная (xm, ym) и физическая (x,y) системы координат. Для изображения на экране точки с физическими координатами (x,y) необходимо определить ее машинные координаты (xm, ym).
xm=x0+x*Mx ,
ym=y0-y*My,
где Mx, My-масштабы соответственно по осям x и y, которые показывают число пикселей в одной физической единице,
x, y- физические координаты точки,
xm, ym- машинные координаты точки,
x0, y0- машинные координаты начала физической системы координат.
Для начала, нужно нарисовать фон. Просто делим плоскость линией - горизонтом и заливаем небо и снег. После чего создаем небо: луну и звезды, если присмотреться, то можно увидеть созвездие «Большая Медведица». Создавая его, я просто примерно подбирал координаты на бумаге, а потом подгонял на компьютере. Далее рисуем елку. Пенек – закрашенным прямоугольником, а треугольники – циклом, параллельно закрашивая. Далее – снеговик. Сначала, я рисовал снеговика, а после создавал его движение. Снеговик состоит из простых фигур – окружностей и линий, а на лице - использовались эллипсы и дуги.
Движение моего снеговика заключается в том, что координаты частей просто смещаются вправо, в связи с чем, рисуется снеговик еще раз, смещенный вбок на какое-то число, а слева – столько же закрашивается. Некоторые рисуют движение: закрашивают исходную фигуру и рисуют смещенную, а я, например, у тела снеговика, - перерисовал смещенного снеговика, а потом слева зарисовал полуокружностью. Такой метод сложен тем, когда объект движется не по однородному фону, нужно закрашивать частями, как я делал с правой рукой снеговика, часть которой на белом фоне, а часть – на голубом. Ведро – просто из двух дуг, соединенных линиями.
Uses Graph, crt;
Var
x,y,z,r,a,b,n,l,i,j: longint;
D,M : integer;
ch:char;
Begin
d:=detect;
InitGraph (d, m, '');
SetColor(177); {небо}
line(0,250,GetMaxX,300);
SetFillStyle(1,177);
FloodFill(0,0,177);
SetFillStyle(1,100); {земля}
FloodFill(60,500,177);
SetColor(68);
ellipse(GetMaxX-100,100,90,270,70,70); {луна}
ellipse(GetMaxX-100,100,90,270,50,70);
SetFillStyle(1,68);
FloodFill(GetMaxX-160,100,68);
putpixel(100,50,68); {звезды}
putpixel(300,15,68);
putpixel(450,50,68);
putpixel(650,90,68);
putpixel(680,190,68);
putpixel(830,200,68);
putpixel(860,100,68);
putpixel(297,12,68);
putpixel(350,200,68);
putpixel(1201,251,68);
putpixel(1200,250,68);
putpixel(1201,250,68);
putpixel(1200,251,68);
setcolor(6); {ель}
setfillstyle(1,6);
Bar(1050,800,1150,850);
r:=400;
SetColor(10);
SetFillStyle(1,red);
while r>=0 do
begin
LIne(1100,300+r,1250,400+r);
LIne(1100,300+r,950,400+r);
LIne(1250,400+r,950,400+r);
setfillstyle(1,10);
floodFill(1100,310+r,10);
r:=r-100;
end;
a:=400;
x:=500;
b:=100;
y:=x div 6;
z:=x div 3;
n:=x div 2;
SetColor(White);
Circle (b,(y div 2)+a,y div 2); {Снеговик}
Circle (b,y+(z div 2)+a,z div 2);
Circle (b,x-(n div 2)+a,n div 2);
SetFillStyle (1, white);
FloodFill (b,(y div 2)+a,white); {Заливка снеговика}
FloodFill (b,y+( z div 2)+a,white);
FloodFill (b,x-(n div 2)+a,white);
SetColor(Black);
PieSlice(b,(y div 2)+a-10,0,360,5); {Глаза}
PieSlice(b+20,(y div 2)+a-10,0,360,5);
ellipse(b+10,(y div 2)+a+10,210,330,15,5); {рот}
line(b+82,y+(z div 2)+a+20,b+100,y+(z div 2)+a+100); {руки}
line(b-53,y+(z div 2)+a,b-70,y+(z div 2)+a+100);
setcolor(42);
PieSlice(b+20,(y div 2)+a,150,210,10); {нос}
SetColor(Black);
SetFillStyle (1, black);
SetFillStyle (1, white);
While b<=800 do {Движение снеговика}
begin
SetColor(White);
Circle (b,(y div 2)+a,y div 2);
Circle (b,y+(z div 2)+a,z div 2);
Circle (b,x-(n div 2)+a,n div 2);
setcolor(42);
PieSlice(b+20,(y div 2)+a,150,210,10);
SetColor(Black);
PieSlice(b,(y div 2)+a-10,0,360,5);
PieSlice(b+20,(y div 2)+a-10,0,360,5);
ellipse(b+10,(y div 2)+a+10,210,330,15,5);
line(b+82,y+(z div 2)+a+20,b+100,y+(z div 2)+a+100);
line(b-53,y+(z div 2)+a,b-70,y+(z div 2)+a+100);
setColor(100);
line(b+80,y+(z div 2)+a+25,b+100,y+(z div 2)+a+100);
line(b-64,y+(z div 2)+a+51,b-71,y+(z div 2)+a+101);
ellipse (b-1,(y div 2)+a,90,270,y div 2,y div 2);
ellipse (b-1,y+(z div 2)+a,90,270,z div 2,z div 2);
ellipse (b-1,x-(n div 2)+a,90,270,n div 2,n div 2);
SetColor(White);
ellipse (b-1,(y div 2)+a-10,90,270,5,5);
ellipse (b+19,(y div 2)+a-10,90,270,5,5);
ellipse (b+9,(y div 2)+a+11,180,270,15,5);
ellipse (b+9,(y div 2)+a+9,270,330,15,5);
ellipse (b+19,(y div 2)+a,150,210,10,10);
line (b-56,y+(z div 2)+a,b-63,y+(z div 2)+a+50);
b:=b+1;
end;
setColor(30);
setfillstyle(1,28);
line (b-35,(y div 2)+a-25,b-20,(y div 2)+a-80); {ведро}
line (b+35,(y div 2)+a-25,b+20,(y div 2)+a-80);
fillellipse(b,(y div 2)+a-80,20,3);
ellipse(b,(y div 2)+a-25,180,360,35,7);
floodfill(b-1,(y div 2)+a-25,30);
ellipse(b+7,(y div 2)+a,160,323,25,50);
readln;
closeGraph;
end.
Для начала, так же, рисуем фон, то есть – линию горизонта и заливаем небо, после – закрашенные прямоугольники в цикле. Сначала я просто рисовал автомобили, а потом создавал их движение. В данном случае я рисовал их с использованием режима «Xor», что позволяет на много проще создавать движущиеся объекты на разноцветном фоне. Данный режим заключается в том, что если нарисовать линию любого цвета, а потом еще раз на том же месте, то изображение на заднем плане будет таким же, каким и было до линии. Автомобили я рисовал просто, сначала на листочке нарисовал, а потом примерно поставил координаты, после чего подгонял на компьютере. Потом нарисовал второй автомобиль, отразив его. Просто каждую координату менял по «x», вычитая из длины автомобиля координату. Допустим координата была (100;40), а длина автомобиля равна 250, то получаем координату (250-100;40) = (150;40).
Единственный минус функции «Xor» - это то, что она работает только с линиями, незакрашенными прямоугольниками и незакрашенными многоугольниками. Поэтому колеса пришлось рисовать так же, как в предыдущей программе, то есть закрашиваем данную окружность и рисуем смещенную.
Uses Graph, crt;
Var
x,y,k,e,q,n,w,r,a,b: longint;
D,M : integer;
ch:char;
Begin
d:=detect;
InitGraph (d, m, '');
SetWriteMode(1); {Включение режима Xor}
SetColor(177);
line(0,500,GetMaxX,450); {небо}
setFillStyle(1,177);
Floodfill(0,0,177);
q:=0;
k:=80;
n:=300;
while q<=5 do {здания}
begin
setFillStyle(1,random(6)+4);
Bar (k,n,k+180,n+500);
if q mod 2=0 then begin k:=k+200; n:=200; end
else begin k:=k+200; n:=300; end;
q:=q+1;
end;
Randomize;
Setfillstyle(1,yellow);
q:=0;
k:=80;
n:=300;
e:=10;
r:=10;
x:=-300; {автомобиль}
y:=822;
A:=1200;
B:=900;
while x<1300 do
Begin
SetColor(White);
circle(x+50,y,20);
Circle(x+200,y,20);
line(x,y,x+30,y);
line(x+70,y,x+180,y);
line(x+220,y,x+250,y);
line(x,y,x+5,y-25);
line(x+5,y-25,x+55,y-25);
line(x+55,y-25,x+67,y-50);
line(x+67,y-50,x+170,y-50);
line(x+170,y-50,x+200,y-25);
line(x+200,y-25,x+225,y-25);
line(x+225,y-25,x+250,y);
line(x+85,y-5,x+60,y-25);
line(x+85,y-5,x+115,y-5);
line(x+70,y-45,x+60,y-25);
line(x+70,y-45,x+115,y-45);
line(x+115,y-5,x+115,y-45);
line(x+120,y-5,x+120,y-45);
line(x+120,y-5,x+175,y-5);
line(x+175,y-5,x+190,y-25);
line(x+190,y-25,x+170,y-45);
line(x+170,y-45,x+120,y-45);
line(x+60,y-25,x+115,y-25);
line(x+190,y-25,x+120,y-25);
Circle(a+50,b,20); {второй автомобиль}
circle(a+200,b,20);
line(a,b,a+30,b);
line(a+70,b,a+180,b);
line(a+220,b,a+250,b);
line(a,b,a+25,b-25);
line(a+25,b-25,a+50,b-25);
line(a+50,b-25,a+80,b-50);
line(a+80,b-50,a+183,b-50);
line(a+183,b-50,a+195,b-25);
line(a+195,b-25,a+245,b-25);
line(a+245,b-25,a+250,b);
line(a+165,b-5,a+190,b-25);
line(a+165,b-5,a+135,b-5);
line(a+180,b-45,a+190,b-25);
line(a+180,b-45,a+135,b-45);
line(a+135,b-5,a+135,b-45);
line(a+130,b-5,a+130,b-45);
line(a+130,b-5,a+75,b-5);
line(a+75,b-5,a+60,b-25);
line(a+60,b-25,a+80,b-45);
line(a+80,b-45,a+130,b-45);
line(a+60,b-25,a+135,b-25);
line(a+190,b-25,a+130,b-25);
delay(70);
line(x,y,x+30,y);
line(x+70,y,x+180,y);
line(x+220,y,x+250,y);
line(x,y,x+5,y-25);
line(x+5,y-25,x+55,y-25);
line(x+55,y-25,x+67,y-50);
line(x+67,y-50,x+170,y-50);
line(x+170,y-50,x+200,y-25);
line(x+200,y-25,x+225,y-25);
line(x+225,y-25,x+250,y);
line(x+85,y-5,x+60,y-25);
line(x+85,y-5,x+115,y-5);
line(x+70,y-45,x+60,y-25);
line(x+70,y-45,x+115,y-45);
line(x+115,y-5,x+115,y-45);
line(x+120,y-5,x+120,y-45);
line(x+120,y-5,x+175,y-5);
line(x+175,y-5,x+190,y-25);
line(x+190,y-25,x+170,y-45);
line(x+170,y-45,x+120,y-45);
line(x+60,y-25,x+115,y-25);
line(x+190,y-25,x+120,y-25);
line(a,b,a+30,b);
line(a+70,b,a+180,b);
line(a+220,b,a+250,b);
line(a,b,a+25,b-25);
line(a+25,b-25,a+50,b-25);
line(a+50,b-25,a+80,b-50);
line(a+80,b-50,a+183,b-50);
line(a+183,b-50,a+195,b-25);
line(a+195,b-25,a+245,b-25);
line(a+245,b-25,a+250,b);
line(a+165,b-5,a+190,b-25);
line(a+165,b-5,a+135,b-5);
line(a+180,b-45,a+190,b-25);
line(a+180,b-45,a+135,b-45);
line(a+135,b-5,a+135,b-45);
line(a+130,b-5,a+130,b-45);
line(a+130,b-5,a+75,b-5);
line(a+75,b-5,a+60,b-25);
line(a+60,b-25,a+80,b-45);
line(a+80,b-45,a+130,b-45);
line(a+60,b-25,a+135,b-25);
line(a+190,b-25,a+130,b-25);
SetColor(black);
circle(x+50,y,20);
Circle(x+200,y,20);
Circle(a+50,b,20);
circle(a+200,b,20);
x:=x+5;
a:=a-5;
end;
readln;
end.
Движение Головы осуществляется за счет стирания данной окружности и рисования смещенной, движение остальных частей тела происходит с использованием режима «Xor». Движение тела – просто смещение координаты по оси «OX». Движение рук и головы – с использованием логической операции «If», то есть, когда координата тела по оси «OX» четна, то одно положение рук и ног, а ,когда координата – нечетна, то другое положение рук и ног.
Uses Graph, crt;
Var
x,y: longint;
D,M : integer;
ch:char;
Begin
d:=detect;
InitGraph (d, m, '');
setwritemode(1); {Включение режима Xor}
setcolor(white);
x:=0;
y:=200;
while x<=getmaxX do {Цикл, осуществляющий движение человека}
begin
setcolor(white);
circle(x,y,50); {Голова}
line(x,y+50,x,y+250); {Туловище}
if x mod 2 = 0 then {Логическая операция, осуществляющая различное положении рук и ног}
begin
line(x,y+60,x-60,y+100);
line(x,y+60,x+60,y+100);
line(x-60,y+100,x-40,y+140);
line(x+60,y+100,x+100,y+60);
line(x,y+250,x-60,y+300);
line(x,y+250,x+60,y+300);
line(x-60,y+300,x-120,y+250);
line(x+60,y+300,x+60,y+370);
end
else
begin
line(x,y+250,x,y+390);
end;
delay(100);
line(x,y+50,x,y+250);
if x mod 2 = 0 then
begin
line(x,y+60,x-60,y+100);
line(x,y+60,x+60,y+100);
line(x-60,y+100,x-40,y+140);
line(x+60,y+100,x+100,y+60);
line(x,y+250,x-60,y+300);
line(x,y+250,x+60,y+300);
line(x-60,y+300,x-120,y+250);
line(x+60,y+300,x+60,y+370);
end
else
begin
line(x,y+250,x,y+390);
end;
setcolor(black);
circle(x,y,50);
x:=x+13;
end;
closegraph;
readln;
end.
1. Дж. Корриган. Компьютерная графика: Секреты и решения. - М.: Диалог - МИФИ, 1995.
2. Фаронов В.В. Турбо Паскаль ( в 3-х книгах ). Практика программирования. - М.: УНЦ ”МВТУ ФЕСТО ДИДАКТИК”, 1993.
3.Шикин Е.В., Боресков А.В. Компьютерная графика. Динамика, реалистические изображения. - М.: Диалог - МИФИ, 1995.
4. Шикин Е.В., Боресков А.В., Зайцев А.А. Начала компьютерной графики. - М.: Диалог- МИФИ, 1993.
5. Колесниченко Е.В. Пособие Турбо Паскаль, 2002 г. Изд. Дом Удмуртский Университет.
Типовые графические функции BGI
При реализации приведенных в пособии типовых алгоритмов графики использованы следующие типовые графические процедуры и функции Borland Graphics Interface:
InitGraph(Gd, Gm, 'way') - переход к графическому режиму
(инициализация графики),
где Gd - имя графического драйвера,
Gm - номер графического режима монитора ,
'way' - дорожка DOS к файлам с графическими драйверами (*.bgi).
Обычно драйверы подключаются в режиме автоопределения используемого монитора ПК. Для этого перед инициализацией графики задается Gd:= Detect (или Gd:= 0). В этом случае по умолчанию устанавливается режим с наибольшим числом точек на экране, а значение параметра "Gm" игнорируется.
Номер наибольшего режима для текущего драйвера возвращает функция GetMaxMode. Изменить режим можно процедурой SetGraphMode( Gm). Экран при этом очищается.
Разрешающую способность для текущего графического режима можно определить функциями, возвращающими максимальные значения координат экрана
GetMaxX - по оси Х; GetMaxY - по оси Y.
Для возврата из графического режима в текстовый можно использовать операторы:
CloseGraph - полное прекращение работы графической системы;
RestoreCrtMode - переключение в текстовый режим с возможностью
возврата к текущим установкам графического режима (оператором SetGraphMode).
Очистить графический экран можно процедурой ClearDevice (без изменения установленных параметров) либо GraphDefaults ( устанавливаются параметры, принятые по умолчанию).
Процедуры рисования:
SetBkColor( N) - установить цвет N для пикселов фона;
SetColor( N) - установить цвет N для выводимых линий;
PutPixel( X, Y, N) - высветить цветом N пиксель с координатами X,Y;
GetPixel( X, Y) - определить цвет пиксела с координатами X, Y;
Circle( X, Y, R) - окружность с центром X, Y радиуса R;
Arc( X,Y, A1,A2, R) - дуга окружности;
Ellipse( X,Y, A1,A2, RX,RY) - сектор эллипса с полуосями RX,RY;
A1, A2 - начальный и конечный углы (в градусах),
отсчитываемые против часовой стрелки относительно оси Х;
Line( X1,Y1, X2,Y2) - отрезок прямой от точки с координатами
X1,Y1 к точке с координатами X2,Y2;
LineTo( X, Y) - отрезок прямой от текущего положения курсора
до точки X,Y;
LineRel( dX, dY) - отрезок прямой от текущего положения курсора
до точки, смещенной на расстояние dX,dY.
В отличие от процедуры Line процедуры LineTo и LineRel при своем исполнении перемещают текущий указатель. Перемещать курсор без рисования можно процедурами MoveTo(X, Y) и MoveRel(dX,dY).
В графическом режиме курсор невидим, а его положение можно определить функциями, возвращающими значения координат
GetX - по оси Х, GetY - по оси Y.
Rectangle( X1,Y1, X2,Y2) - прямоугольник с левым верхним углом в
точке X1,Y1 и правым нижним углом в точке X2,Y2 (стороны параллельны краям экрана ).
Для заполняемых фигур граница рисуется текущим цветом для линий. Цвет N и стиль заполнения P (орнамент) можно устанавливать из стандартного набора BGI или определять самим процедурой SetFillStyle( P, N).
Bar( X1,Y1, X2,Y2) - заполненный прямоугольник;
Bar3d( X1,Y1, X2,Y2, d, t) - параллелепипед с заполненной передней
гранью (координаты углов грани X1,Y1, X2,Y2), глубиной d. Переменная t типа boolean задает вывод верхней грани. При t=TopOn (true) верхняя грань показывается, при t=TopOff (false) - нет.
FillEllipse( X,Y, RX,RY) - заполненный эллипс;
Sector( X,Y, A1,A2, RX,RY) - заполненный сектор эллипса;
PieSlice( X,Y, A1,A2, R) - заполненный сектор круга.
«Течет река Волга»
Шум и человек
Хрюк на ёлке
Любили тебя без особых причин...
Заяц, косач, медведь и весна