Пятница, 29.03.2024, 05:11

Delphi

Приветствую Вас Гость

Поиск
Друзья сайта
Статистика

Онлайн всего: 1
Гостей: 1
Пользователей: 0

Сегодня были:
Самые активные пользователи

Меню сайта
Категории каталога
Звук и музыка [1]
Графика и игры [6]
Базы данных [1]
Стандартные компоненты [0]
3D графика [4]
Исходники [10]
DirectX и OpenGL [5]
Разное [1]
Интернет и сети [7]
Наш опрос
Чему уделять больше внимания?
Всего ответов: 64
Главная » Статьи » Delphi » 3D графика

Создаем "Крестики-нолики" в GLScene
Без лишних разглагольствований, приступим к делу. Для начала создадим простенькую игру, такую как «Крестики-нолики». Работать она будет только в оконном режиме, но мы применим технологию Cell-shading, чтобы создать эффект «мультяшности».
Запускаем Дельфи, добавляем на форму следующие компоненты: GLScene, GLMaterialLibrary и GLSceneViewer. Если вы уже работали с этим движком, то вам должно быть известно о назначении каждого из этих компонентов, если нет, то вот краткое пояснение: GLScene – это контейнер, в котором хранятся все объекты движка и их свойства, без него нам ничего не удастся изобразить; GLMaterialLibrary – это список материалов (которые в свою очередь тоже являются списками свойств поверхностей трехмерных объектов); GLSceneViewer – это компонент, отвечающий за отображение всех 3д объектов.
Теперь можно перейти к подготовке сцены. Для начала создадим объект TGLDummyCube, к нему будут наследоваться все объекты нашей игры. Назовем его, например, Desk, потому что игра будет происходить на столе, но можете назвать его и как-нибудь еще. Добавляется он очень просто: дважды щелкаем на компонент GLScene и в появившемся окне щелкаем сначала на объект к которому будет наследоваться наш куб а потом на правую кнопку мыши и в появившемся меню в подменю Add Object выбираем DummyCube. Чтобы изменить его название, измените свойство Name этого объекта. Теперь добавим крестики и нолики. Для этого добавим к DummyCube’у два объекта GLSpaceText назовем их О1 для ноликов и Х1 для крестиков. Теперь изменим их свойство Text на О и Х соответственно для О1 и Х1. Свойству Extrusion обоих объектов придадим значение 0,3. С объектами разобрались, теперь перейдем к материалам. Дважды щелкаем по GLMaterialLibrary. Теперь добавляем новый материал нажатием на кнопку Add New в левом верхнем углу. Назовем этот материал XMat, как видно из названия, будет использоваться для крестиков, добавим еще один и назовем его OMat, который будет использоваться для ноликов, создадим третий материал с названием DeskMat, использующийся для игрового поля. Чтобы крестики с ноликами как-то различались изменим их цвета. Для этого выбираем материал и в инспекторе объектов раскрываем свойство Material и его подсвойство FrontProperties(оно отвечает за свойтво той стороны объекта, которая находится в поле зрения камеры, чуть выше есть также свойство BackProperties, но оно нам не нужно, т.к отвечает за ту сторону объекта, которая не видна камере), теперь изменяем свойство Diffuse на понравившийся нам цвет и все, материал практически готов, осталось только добавить эффект «мультяшности», но это чуть попозже. Проделываем вышеописанные действия и с оставшимися материалами. Вот практически все приготовления завершены и можно начинать писать код, однако ни один из игровых объектов не предстал нашим глазам. Дело в том, что мы не создали камеру, которая бы показывала нам, что сейчас творится в игре. Для того, чтобы создать камеру, щелкаем правой кнопкой мыши на пункте Cameras в редакторе сцены и выбираем Add camera. Камеру мы добавили, теперь настроим ее параметры в раскрывающемся списке выбираем Desk, именно на него будет направлена наша камера, в свойства свойстве Position, в полях X, Y, Z вписываем число 3. Теперь щелкаем на GLSceneViewer’е и в списке Camera выбираем только что созданную камеру. Добавляем свет, чтобы не приходилось играть в полной темноте, для этого щелкаем правой кнопкой мыши в редакторе сцены и выбираем Add -> LightSource. Теперь делаем его дочерним объектом камеры(если вы забыли, то просто перетаскиваем его на камеру в редакторе сцены), это нужно для того, чтобы поле освещалось со стороны игрока. Ну вот, теперь можно переходить непосредственно к написанию кода.
Первым делом нам нужно создать игровое поле. Его мы сделаем из 9 кубиков. Хочу заметить, что писать мы будем немного не так, как раньше, если вы не новичок в Дельфи, то можете не читать это предложение до конца, а если да, то внимайте: мы будем описывать программы не в обработчике какого-либо события компонента, как, например, TForm1.FormCreate, а создадим отдельную процедуру для выполнения нужных нам действий, а в обработчике события будем просто вызывать ее, это уменьшит вероятность того, что мы запутаемся в коде, ведь в обработчике хоть того же TForm1.FormCreate может быть огромное количество выполняемых действий. Итак, продолжим. Для начала сразу после слова private впишите следующее: procedure CreateDesk; . В этой процедуре мы и создадим наше поле. После {$R *.dfm} впишите такие строки
procedure TForm1.CreateDesk;
var
DeskPart: TGLCube;// части игрового поля
x,z: Integer;//координаты кубиков по x и z
begin
for x := -1 to 1 do //устанавливаем координаты по x
for z := -1 to 1 do //устанавливаем координаты по z
begin
DeskPart := TGLCube.CreateAsChild(Desk); //создаем кубик и делаем его дочерним нашему Desk
DeskPart.Position.X := X;// перемещаем кубик в центр клетки
DeskPart.Position.Z := Z;
DeskPart.CubeWidth := 1; //задаем длину и ширину кубика
DeskPart.CubeDepth := 1;
with DeskPart.Material do //задаем материал
begin
MaterialLibrary := GLMaterialLibrary1;
LibMaterialName := 'DeskMat';
end;
end;
end;
С созданием игрового поля мы разобрались. Теперь перейдем к тому, как мы будем расставлять по полю крестики и нолики. Снова в раздел private впишите procedure: PickObject(x, y: integer);. В скобках обозначаются типы переменных, которые будут сообщаться процедуре при вызове. Теперь добавим в программу еще четыре переменных, которые нам будут нужны. Первая обозначает объект, на который мы щелкнули, две другие – игроков, которые должны ходить, а четвертая – счетчик, следящий за количеством фигур на поле. Итак, в раздел Var, идущий перед словом implementation, впишите впишите:
Pick: TGLBaseSceneObject; //объект, на который кликает игрок
Player1, Player2: Boolean; //переменные, обозначающие игроков, какая находится в true, тот игрок и ходит
ProxyCounter: integer;// счетчик, чтобы прокси объекты не путались между собой
Теперь напишем непосредственно код процедуры:
procedure TForm1.PickObject(x,y: integer); //выбираем объект, над которым находился курсор мыши
var
OProxy, XaProxy: TGLProxyObject;//прокси объекты
begin
Pick := Viewer.Buffer.GetPickedObject(x,y);
if (Player1 and (Pick <> nil)) then //проверяем, какой игрок сейчас ходит и выбран ли объект
begin
if not (Pick.ClassType = TGLCube) then //если игрок щелкнул не на поле, то выдаем сообщение и прекращаем выполнение операции
begin
ShowMessage('Вы не можете поставить здесь ' + 'O');
exit;
end;
if Pick.Count = 0 then //проверяем, есть ли у выбранного объекта дочерние объекты
begin
OProxy := TGLProxyObject.CreateAsChild(Pick);//создаем прокси объект и делаем его дочерним сегменту поля
OProxy.MasterObject := O1;//устанавливаем объект, который будет копировать прокси
OProxy.ProxyOptions := [pooObjects];//копироваться будет только объект
OProxy.Name := 'Proxy' + inttostr(ProxyCounter); //присваиваем имя объекту
OProxy.Direction := O1.Direction; //направление оставляем таким же, как и начального объекта
OProxy.Position.X := OProxy.Position.X - 0.5;//помещаем объект в центр выбранного объекта
OProxy.Position.Z := OProxy.Position.Z + 0.5;
OProxy.Position.Y := OProxy.Position.Y + 0.7;
Player1 := False; // меняем игрока
Player2 := true;
ProxyCounter := ProxyCounter + 1;//меняем счетчик
Form1.Caption := 'Сейчас ходят Х';
exit;
end
else
begin
exit;
end;
end;
if Player2 and (Pick<>nil) then //далее идет то же, что и в предыдущих строках, но только теперь для крестиков
begin
if not (Pick.ClassType = TGLCube) then
begin
ShowMessage('Вы не можете поставить здесь ' + 'X');
exit;
end;
if Pick.Count = 0 then
begin
XaProxy := TGLProxyObject.CreateAsChild(Pick);
XaProxy.MasterObject := X1;
XaProxy.ProxyOptions := [pooObjects];
XaProxy.Name := 'Proxy' + inttostr(ProxyCounter);
XaProxy.Direction := X1.Direction;
XaProxy.Position.X := XaProxy.Position.X - 0.5;
XaProxy.Position.Z := XaProxy.Position.Z + 0.5;
XaProxy.Position.Y := XaProxy.Position.Y + 0.7;
Player2 := False;
Player1 := True;
ProxyCounter := ProxyCounter + 1;
Form1.Caption := 'Сейчас ходят О';
exit;
end
else
begin
exit;
end;
end;
end;
Вот практически и все, осталось только дописать вызовы этих процедур. В обработчике события OnCreate нашей формы напишите:
CreateDesk;//Вызываем процедуру, в которой создаем кубик
Player1 := true;//устанавливаем, какой игрок ходит первым
ProxyCounter := 1;
А в обработчике события onmousedown Viewer’а впишите
if ssLeft in Shift then //щелчок был произведен левой кнопкой мыши
PickObject(X, Y);
Теперь можете запустить игру. Все должно работать хорошо. Однако есть одно «но» - поле и фигуры не выглядят, как нарисованы. Для того, чтобы добавить cell-shading, выберите любой материал и в свойстве Shader выберите GLCelShader1, тоже проделайте и с остальными. Теперь все объекты будут выглядеть нарисованными.
Ну вот и все! Основа игры готова. Правда, здесь нет меню и при построении фигур в одну линию Вам придется определять победителя самим. Однако я постараюсь описать эти аспекты в ближайшее время!!! Удачи.

Статья взята с сайта http://glscene.ru/
Категория: 3D графика | Добавил: Ivin (02.04.2008)
Просмотров: 6748 | Рейтинг: 4.5/2 |