ЗАДАНИЕ XXI

Тема: Изучение работы с функциями
Цель: Знакомство с функциями автоматического создания и удаления имиджей

Введение

Классы и объекты
Объектно-ориентированный подход разработки в среде подразумевает наличие базовых понятий в виде объектов и классов. Гради Буч дает следующее определение: “Объект обладает состоянием, поведением и индивидуальностью; структура и поведение схожих объектов определяют общий для них класс. Термины “экземпляр класса” и “объект” взаимозаменяемы”. Термин "имидж" соответствует классу, а экземпляр имиджа - объекту. Для работы с классами и объектами существует ряд специальных функций.

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

Задание 1. Построение схемы

    Создадим новый проект. Построим пример эволюционной модели.

Создайте два имиджа которые позволят нам ограничить некоторое пространство на схеме - Вертикальная и Горизонтальная стенки. Нарисуйте соответствующий им внешний вид. Модель этих имиджей очень простая:

FLOAT F

Переменная F служит идентификатором типа стенки. Для горизонтальной стенки установите значение 1, для вертикальной 2. В дальнейшем это даст нам возможность автоматически определять тип стенки из другого имиджа.

Постройте из них замкнутую фигуру, например:

lab21_1.gif (14555 bytes)

Теперь создадим имидж Ball (не забудьте установить ему именно такое имя!). Модель имиджа:

HANDLE _HObject,HSpace // дескриптор имиджа
FLOAT OrgX,OrgY // начальные координаты имиджа
FLOAT f // тип объекта (установить число 3)
FLOAT r // радиус шарика (установить)
FLOAT x,y,vx,vy // текущие координаты и скорость

if (Init == 0) // инициализация переменных
HSpace := GetWindowSpace("@Scheme@Root")
if (not(~_HObject))
exit()
endif
vx := Rnd(4) - 2
vy := Rnd(4) - 2
x := OrgX+r
y := OrgY+r
Init := 1
endif

xx := ~x + r*Sgn(~vx) // расчет новых координат
yy := ~y + r*Sgn(~vy)

hfobj := GetObjectFromPoint2d(~HSpace,~xx,~yy)
if (~hfobj != #0) // если есть препятствие обрабатываем
k := GetVarF("..\#"+string(float(~hfobj)),"f")
if (~k == 1) // горизонтальная стена
vy := -1*~vy
endif
if (~k == 2) // вертикальная стена
vx := -1*~vx
endif
if (~k == 3) // другой шар
vy := -1*~vy
vx := -1*~vx
endif
if (rnd(1)<0.5) // с вероятностью 50% создаем новый шар
if (c > 5)
h := CreateObject("Root","Ball","",x-r,y-r)
c := 0
else
c := c + 1
endif
endif
endif

x := ~x + ~vx // перемещаем шар в новые координаты
y := ~y + ~vy
ret := SetObjectOrg2d(~HSpace,~_HObject,~x-r,~y-r)

Нарисуйте для него соответствующее изображение и установите радиус в переменную r, и число 3 в переменную f.

Для того чтобы правильно обрабатывалась функция GetWindowSpace (7-я строчка), задайте имя корневого имиджа проекта - Root. Для этого выполните команду Вид-Иерархия проекта. Найдите корневой имидж (самый верхний), и в его свойствах (дважды щелкните на нем мышкой) введите имя Root.

Поместите имидж внутри стен и проверьте работоспособность схемы. Шар должен перемещаться, отражаться от стен и других шаров и при соударении с вероятностью 50% создавать себе подобного.

Проверьте работоспособность схемы.

Задание 2. Усложнение схемы

Добавим другой тип шара, который будет при столкновении с другими уничтожать их. Для этого создайте имидж Ball2:

HANDLE _HObject,HSpace // дескриптор имиджа
FLOAT OrgX,OrgY // начальные координаты имиджа
FLOAT f // тип объекта (установить число 3)
FLOAT r // радиус шарика (установить)
FLOAT x,y,vx,vy // текущие координаты и скорость

if (Init == 0) // инициализация переменных
HSpace := GetWindowSpace("@Scheme@Root")
if (not(~_HObject))
exit()
endif
vx := 1 + Rnd(4) - 2
vy := 1 + Rnd(4) - 2
x := OrgX+r
y := OrgY+r
Init := 1
endif

xx := ~x + r*Sgn(~vx) // расчет новых координат
yy := ~y + r*Sgn(~vy)

hfobj := GetObjectFromPoint2d(~HSpace,~xx,~yy)
if (~hfobj != #0) // если есть препятствие обрабатываем
k := GetVarF("..\#"+string(float(~hfobj)),"f")
if (~k == 1) // горизонтальная стена
vy := -1*~vy
endif
if (~k == 2) // вертикальная стена
vx := -1*~vx
endif
if (~k == 3) // другой шар
ret := DeleteObject("Root",~hfobj,0) // удаляем его
endif
if (rnd(1)<0.5) // с вероятностью 50% создаем новый шар
if (c > 5)
h := CreateObject("Root","Ball","",x-r,y-r)
c := 0
else
c := c + 1
endif
endif
endif

x := ~x + ~vx // перемещаем шар в новые координаты
y := ~y + ~vy
ret := SetObjectOrg2d(~HSpace,~_HObject,~x-r,~y-r)

Аналогично предыдущему имиджу, установите переменные r и f.
Проверьте работоспособность схемы. Правильно работающая схема может выглядеть так:

lab21_2.gif (16313 bytes)

Примечание. При тестрировании схемы, у Вас может возникнуть ситуация, когда имиджи "разлетятся" по всей схеме. Для того чтобы удалить лишние удобно использовать команду Правка-Поиск. Осуществите поиск по названию Ball и укажите поиск в Имени классов и Создавать группу.