Возможно вы искали: 'Void Rim'

May 12 2025 01:24:28
  • Как сделать 8Gamers.Ru домашней страницей?
  • Игры
    • База данных по играх
    • Игровые новости
    • Игровая индустрия
    • Обзоры на игры
    • Прохождения игр
    • Гайды к играм
    • Превью о играх
    • Игровые тизеры
    • Игровые арты
    • Игровые обои
    • Игровые скриншоты
    • Игровые обложки
    • Игровые трейлеры
    • Игровое видео
    • Вышедшие игры
    • Ближайшие релизы игр
  • Кино и ТВ
    • База данных по кино
    • Статьи о кино
    • Постеры
    • Кадры из кино
    • Кино трейлеры
    • Сегодня в кино
    • Скоро в кино
  • Комиксы и манга
    • Манга по алфавиту
    • База данных по комиксах
    • Читать онлайн комиксы
    • Читать онлайн манга
    • База персонажей
  • Читы и коды
    • Чит-коды для PC игр
    • Чит-коды для консольных игр
    • Трейнеры
    • Коды Game Genie
  • Моддинг
    • Модификации
    • Карты к играм
    • Программы для моддинга
    • Статьи о моддинге
  • Геймдев
    • Всё о создании игр
    • Список движков
    • Утилиты в помощь игроделу
    • Конструкторы игр
    • Игровые движки
    • Библиотеки разработки
    • 3D-модели
    • Спрайты и тайлы
    • Музыка и звуки
    • Текстуры и фоны
  • Рецензии
    • Игры
    • Кино
    • Аниме
    • Комиксы
    • Мангу
    • Саундтреки
  • Саундтреки
    • Лирика
  • Файлы
    • Патчи к играм
    • Русификаторы к играм
    • Сохранения к играм
    • Субтитры к кино
  • Медиа
    • Видео
    • Фото
    • Аудио
    • Фан-арты
    • Косплей
    • Фото с виставок
    • Девушки из игр
    • Рисунки
    • Рисуем онлайн
    • Фотохостинг
  • Юмор
    • Анекдоты
    • Афоризмы
    • Истории
    • Стишки и эпиграммы
    • Тосты
    • Цитаты
  • Флеш
    • Азартные
    • Аркады
    • Бродилки
    • Гонки
    • Для девочек
    • Для мальчиков
    • Драки
    • Квесты
    • Леталки
    • Логические
    • Мультфильмы
    • Открытки
    • Приколы
    • Разное
    • Спорт
    • Стратегии
    • Стрелялки
Статистика

Статей: 87772
Просмотров: 96030355
Игры
Injustice:  Gods Among Us
Injustice: Gods Among Us
...
Dark Souls 2
Dark Souls 2
Dark Souls II - вторая часть самой хардкорной ролевой игры 2011-2012 года, с новым героем, сюжето...
Battlefield 4
Battlefield 4
Battlefield 4 - продолжение венценосного мультиплеер-ориентированного шутера от первого ли...
Кино
Steins;Gate
Steins;Gate
Любители японской анимации уже давно поняли ,что аниме сериалы могут дать порой гораздо больше пи...
Ку! Кин-дза-дза
Ку! Кин-дза-дза
Начинающий диджей Толик и всемирно известный виолончелист Владимир Чижов встречают на шумной моск...
Обзоры на игры
• Обзор Ibara [PCB/PS2] 18346
• Обзор The Walking ... 18789
• Обзор DMC: Devil M... 19864
• Обзор на игру Valk... 15867
• Обзор на игру Stars! 17754
• Обзор на Far Cry 3 17935
• Обзор на Resident ... 16012
• Обзор на Chivalry:... 17495
• Обзор на игру Kerb... 17970
• Обзор игры 007: Fr... 16604
Превью о играх
• Превью к игре Comp... 17946
• Превью о игре Mage... 14451
• Превью Incredible ... 14706
• Превью Firefall 13462
• Превью Dead Space 3 16325
• Превью о игре SimC... 14717
• Превью к игре Fuse 15432
• Превью Red Orche... 15532
• Превью Gothic 3 16334
• Превью Black & W... 17345
Главная » Статьи » Всё о XNA » Пространственные преобразования

Пространственные преобразования

Лабораторная работа №15. Пространственные преобразования объектов

Эта лабораторная работа посвящена пространственным преобразованиям трехмерных объектов. В частности, здесь мы поговорим о перемещении объектов, об их масштабировании, обсудим настройку перемещения камеры.

Цель работы
  • Научиться перемещать трехмерные объекты в пространстве
Задачи работы
  • Освоить технику перемещения объектов
  • Освоить технику масштабирования объектов
  • Освоить технику перемещения камеры
Пространственные преобразования объектов

Создадим новый проект P15_1 и на его примере рассмотрим следующие пространственные преобразования объектов
  • Перемещение
  • Вращение
  • Масштабирование
Для выполнения этих операций нам понадобится модификация мировой матрицы. Модификации, соответствующие перемещению объекта мы выполним по клавиатурным командам, остальные модификации будут выполняться автоматически в цикле обновления.
Для этого примера мы создали несколько простых трехмерных моделей в редакторе Blender. В частности – это два разноцветных шара и куб. Вот как выглядит игровой экран проекта P15_1 (рис. 15.1.).


Рис. 15.1. Игровой экран проекта P15_1

Для упрощения работы с несколькими игровыми объектами мы создадим игровой компонент - modCls, который будет отвечать за хранение параметров, соответствующих этим объектам и за их визуализацию. В листинге 15.1. вы можете видеть код этого объекта.

Листинг 15.1. Код класса modCls
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Content;
 
namespace P15_1
{
    public class modCls : Microsoft.Xna.Framework.DrawableGameComponent
    {
        //Модель
        Model myModel;
        //Мировая матрица
        public  Matrix WorldMatrix;
        //Соотношение сторон экрана
        public  float aspectRatio;
        //Для управления графическим устройством
        GraphicsDeviceManager graphics;
        //Конструктор получает на вход 
        //игровой класс, модель, объект для управления графическим устройством
        public modCls(Game game, Model mod, GraphicsDeviceManager grf)
            : base(game)
        {
            myModel = mod;
            graphics = grf;
            aspectRatio = (float)graphics.GraphicsDevice.Viewport.Width /
(float)graphics.GraphicsDevice.Viewport.Height;
        }
 
        public override void Update(GameTime gameTime)
        {
 
            foreach (ModelMesh mesh in myModel.Meshes)
            {
                //Для каждого эффекта в сети
                foreach (BasicEffect effect in mesh.Effects)
                {
                    //Установить освещение по умолчанию
                    effect.LightingEnabled = true;
                    effect.EnableDefaultLighting();
                    //установить матрицы
                    effect.World = WorldMatrix;
                    effect.View = Matrix.CreateLookAt(new Vector3(0.0f, 0.0f, 10.0f), Vector3.Zero, Vector3.Up);
                    effect.Projection = Matrix.CreatePerspectiveFieldOfView(MathHelper.ToRadians(45.0f),
                         aspectRatio, 1.0f, 1000.0f);
                }
            }
 
            base.Update(gameTime);
        }
        public override void Draw(GameTime gameTime)
        {
            foreach (ModelMesh mesh in myModel.Meshes)
            {
                mesh.Draw();
            }
            base.Draw(gameTime);
        }
    }
}

 


Управление объектами возложено на основной игровой класс – его метод Update используется для вычисления новых позиций объектов и обновления информации объектов. Код этого класса вы можете видеть в листинге 15.2. Шар, расположенный сверху, автоматически циклически изменяет размер, куб вращается вокруг осей X и Y, шар, расположенный ниже, можно перемещать. Клавиши-стрелки используются для перемещения по осям X и Y (вверх, вниз, влево и вправо), клавиши W и S перемещают объект вперед и назад по оси Z.

Листинг 15.2. Код класса Game1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
 
namespace P15_1
{
    public class Game1 : Microsoft.Xna.Framework.Game
    {
        GraphicsDeviceManager graphics;
        //Мировая матрица
        Matrix WorldMatrixM, WorldMatrixM1, WorldMatrixM2;
        //Направление движения для модели modelCls1
        Vector3 directM1;
        //Модели - 
        //modelCls вращается
        //modelCls1 перемещается по клавиатурным командам
        //modelCls2 изменяет размер
        modCls modelCls, modelCls1, modelCls2;
        //Переменные для текущего размера и 
        //текущего приращения размера модели modelCls2
        float size, sizeDelta;
        public Game1()
        {
            graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
        }
 
        protected override void LoadContent()
        {
            //загрузка моделей и создание объектов, используемых для 
            //хранения информации о моделях и их вывода на экран
            modelCls = new modCls(this, Content.Load<Model>("cube"), graphics);
            modelCls1 = new modCls(this, Content.Load<Model>("ball"), graphics);
            modelCls2 = new modCls(this, Content.Load<Model>("ball2"), graphics);
            //Добавляем объекты в коллекцию Components - для их 
            //автоматического вывода на экран
            Components.Add(modelCls);
            Components.Add(modelCls1);
            Components.Add(modelCls2);
            //Значения для приращения размера и текущего размера
            sizeDelta = 0.01f;
            size = 0.5f;
            //Установка исходного положения для модели modelCls1
            directM1 = new Vector3(2.0f, -1.0f, 1.0f);
            //Установка матриц, которые используются для управления объектами
            WorldMatrixM = Matrix.Identity;
            WorldMatrixM1 = Matrix.CreateTranslation(directM1);
            WorldMatrixM2 = Matrix.CreateScale(size);
        }
 
        protected override void Update(GameTime gameTime)
        {
 
            KeyboardState kb = Keyboard.GetState();
            //По нажатии клавиши-стрелки "вверх" перемещаем модель
            //modelCls1 вверх
            if (kb.IsKeyDown(Keys.Up))
            {
                directM1.Y=directM1 .Y +0.1f;
                WorldMatrixM1 = Matrix.CreateTranslation(directM1);
            }
            //Нажатие клавиши "вниз" - перемещение вниз
            if (kb.IsKeyDown(Keys.Down))
            {
                directM1.Y = directM1.Y - 0.1f;
                WorldMatrixM1 = Matrix.CreateTranslation(directM1);
            }
            //Нажатие клавиши "влево" - перемещение влево
            if (kb.IsKeyDown(Keys.Left))
            {
                directM1.X = directM1.X - 0.1f;
                WorldMatrixM1 = Matrix.CreateTranslation(directM1);
            }
            //Нажатие клавиши "вправо" - перемещение вправо
            if (kb.IsKeyDown(Keys.Right))
            {
                directM1.X = directM1.X + 0.1f;
                WorldMatrixM1 = Matrix.CreateTranslation(directM1);
            }
            //Нажатие клавиши "W" - перемещение вперед
            if (kb.IsKeyDown(Keys.W))
            {
                directM1.Z = directM1.Z - 0.1f;
                WorldMatrixM1 = Matrix.CreateTranslation(directM1);
            }
            //Нажатие клавиши "S" - перемещение назад
            if (kb.IsKeyDown(Keys.S))
            {
                directM1.Z = directM1.Z + 0.1f;
                WorldMatrixM1 = Matrix.CreateTranslation(directM1);
            }
 
            //Если текущий размер меньше 0.5 - 
            //устанавливаем приращение, равное 0.01
            //Если текущий размер больше 1.5 -
            //устанавливаем приращение -0.01
            if (size < 0.5) sizeDelta = 0.01f;
            if (size > 1.5) sizeDelta = -0.01f;
            size += sizeDelta;
 
            //Матрица для объекта modelCls1 устанавливается для поворота его вокруг
            //осей X и Y на один градус
            WorldMatrixM = WorldMatrixM * Matrix.CreateRotationY(MathHelper.ToRadians(1))*
                Matrix .CreateRotationX (MathHelper .ToRadians (1));
            //Установка матрицы для объекта modelCls2
            WorldMatrixM2 = Matrix.CreateScale(size) * Matrix.CreateTranslation(new Vector3(-5.0f, 2.0f, -3.0f));
            //Передаем матрицы объектам
            modelCls.WorldMatrix = WorldMatrixM;
            modelCls1.WorldMatrix = WorldMatrixM1;
            modelCls2.WorldMatrix = WorldMatrixM2;
            base.Update(gameTime);
        }
 
        protected override void Draw(GameTime gameTime)
        {
            graphics.GraphicsDevice.Clear(Color.CornflowerBlue);
 
            base.Draw(gameTime);
        }
    }
}

 


Рассмотрев способы модификации объектов, поговорим об особенностях настройки камеры.

Настройка перемещения камеры: базовые приемы

Камера играет огромную роль в трехмерных играх. В играх от первого лица позиция камеры ассоциируется с позицией игрока. Примерами таких игр игры класса simulator, shooter. В играх от третьего лица (strategy) камера расположена выше игрока и сдвинута назад – играющий может видеть своего персонажа и часть карты.

Рассмотрим простой пример управления камерой, в котором реализовано перемещение камеры, а так же изменение угла зрения. Фактически это – пример работы камеры от первого лица. Изменение угла зрения очень похоже на изменение фокусного расстояния в оптических приборах – увеличение фокусного расстояния, которое приводит к уменьшению угла зрения, позволяет «приближать» далеко расположенные объекты. Уменьшение фокусного расстояния, соответствующее увеличению угла зрения, позволяет охватить взглядом большую территорию.

Создадим новый проект – P15_2. Рассмотрим на его примере вышеописанные операции с камерой.

В листинге 15.3. вы можете найти код класса Game1, реализующего демонстрацию работы с камерой.

Листинг 15.3. Код класса Game1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
 
namespace P15_2
{
    public class Game1 : Microsoft.Xna.Framework.Game
    {
        //соотношение сторон окна вывода
        float aspectRatio;
 
        //Матрицы
        Matrix viewMatrix;
        Matrix projMatrix;
        Matrix worldMatrix;
        //Модель
        Model ball;
 
        // Позиция и вращение камеры
        Vector3 camPos = new Vector3(0, 0, -50);
        float camRotation;
 
        // Направление камеры
        Vector3 cameraDirection = new Vector3(0, 0, 1);
 
        // Установка скорости поворота и передвижения
        float rotationSpeed = 0.01f;
        float forwardSpeed = 1.0f;
 
        //Угол зрения камеры
        float viewAngle = MathHelper.ToRadians(45.0f);
        GraphicsDeviceManager graphics;
 
        public Game1()
        {
            graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
        }
 
        protected override void LoadContent()
        {
            //Загрузка модели
            ball = Content.Load<Model>("ball");
            //Установка мировой матрицы
            worldMatrix = Matrix.Identity;
            //Соотношение сторон
            aspectRatio = (float)graphics.GraphicsDevice.Viewport.Width /
(float)graphics.GraphicsDevice.Viewport.Height;
 
        }
 
        protected override void Update(GameTime gameTime)
        {
            //Получить состояние клавиатуры
            KeyboardState keyboardState = Keyboard.GetState();
 
            //Поворот влево
            if (keyboardState.IsKeyDown(Keys.Left))
            {
                 camRotation += rotationSpeed;
            }
            //Поворот вправо
            if (keyboardState.IsKeyDown(Keys.Right))
            {
                camRotation -= rotationSpeed;
            }
 
            //Переедвижение вперед
            if (keyboardState.IsKeyDown(Keys.Up))
            {
                //Создаем матрицу поворота
                Matrix forwardMov = Matrix.CreateRotationY(camRotation);
                //Создаем новый вектор, содержащий скорость движения
                Vector3 v = new Vector3(0, 0, forwardSpeed);
                //Трансформируем матрицу в вектор
                v = Vector3.Transform(v, forwardMov);
                //модифицируем позицию таким образом, чтобы
                //она соответствовала новым данным
                camPos.Z += v.Z;
                camPos.X += v.X;
            }
            //Передвижение назад
            if (keyboardState.IsKeyDown(Keys.Down))
            {
                Matrix forwardMovement = Matrix.CreateRotationY(camRotation);
                Vector3 v = new Vector3(0, 0, -forwardSpeed);
                v = Vector3.Transform(v, forwardMovement);
                camPos.Z += v.Z;
                camPos.X += v.X;
            }
 
            //Уменьшение угла обзора камеры
            if (keyboardState.IsKeyDown(Keys.W))
            {
                viewAngle -= MathHelper.ToRadians(1.0f);
            }
            //Увеличение угла обзора камеры
            if (keyboardState.IsKeyDown(Keys.S))
            {
                viewAngle += MathHelper.ToRadians(1.0f);
            }
            //Если новый угол обзора вышел за дозволенные пределы
            //изменяем его
            if (viewAngle > MathHelper.ToRadians(180.0f)) viewAngle = MathHelper.ToRadians(179.9f);
            if (viewAngle < MathHelper.ToRadians(0.0f)) viewAngle = MathHelper.ToRadians(0.1f);
 
            Matrix rotationMatrix = Matrix.CreateRotationY(camRotation);
 
            // Вектор направления камеры
            Vector3 cameraTransformed = Vector3.Transform(cameraDirection, rotationMatrix);
 
            // Вычисляем положение камеры
            Vector3 cameraLookat = camPos + cameraTransformed;
 
            // Устанавливаем матрицу вида
            viewMatrix = Matrix.CreateLookAt(camPos, cameraLookat, new Vector3(0.0f, 1.0f, 0.0f));
            //Устанавливаем проекционную матрицу
            projMatrix = Matrix.CreatePerspectiveFieldOfView(viewAngle, aspectRatio, 1.0f, 1000.0f);
 
            base.Update(gameTime);
        }
        /// 
        /// This is called when the game should draw itself.
        /// 
        /// Provides a snapshot of timing values.
        protected override void Draw(GameTime gameTime)
        {
            graphics.GraphicsDevice.Clear(Color.CornflowerBlue);
 
            foreach (ModelMesh mesh in ball.Meshes)
            {
                foreach (BasicEffect effect in mesh.Effects)
                {
                    effect.LightingEnabled = true;
                    effect.EnableDefaultLighting();
                    effect.Projection = projMatrix;
                    effect.View = viewMatrix;
                    effect.World = worldMatrix;
 
                }
                mesh.Draw();
            }
 
            base.Draw(gameTime);
        }
    }
}

 


На рис. 15.2. вы можете видеть изображение игрового экрана проекта P15_2.


Рис. 15.2. Экран проекта P15_2

Шар, который мы видим в окне, искажен – угол обзора камеры увеличен, а расстояние от камеры до объекта сильно уменьшено.

Настройка перемещения камеры: продвинутые приемы

Рассмотрим пример, иллюстрирующий работу с камерой в режиме от первого лица и в режиме вида от третьего лица. Для подготовки этого примера мы использовали справочные материалы по XNA.

Создадим новый проект P15_3. Наш проект выполняет следующие действия. Он выводит на экран плоскость и набор кубов, среди которых может двигаться шар. Причем, движение может осуществляться в двух режимах. В первом режиме демонстрируется работа камеры при виде от первого лица – шар в таком случае не выводится, сцена выглядит так, как будто мы смотрим на нее с позиции шара. Во втором режиме демонстрируется вид от третьего лица – камера находится выше объекта. В играх часто применяется следующий прием – главный игровой объект неподвижен, а игровой мир перемещается, создавая иллюзию движения этого объекта. В нашем случае все выглядит точно так же – шар неподвижно находится в центре экрана, но за счет перемещения игровой сцены создается иллюзия его движения по экрану и по сцене.

В листинге 15.3. вы можете найти код класса Game1, который содержит пример. Для перемещения используются клавиши-стрелки, для смены состояний камеры – клавиши A и S. Клавиша A переключает программу в режим камеры от первого лица, S – в режим вида от третьего лица. Клавиша R уменьшает поле зрения камеры, клавиша F – увеличивает.

Листинг 15.4. Код класса Game1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
 
namespace P15_3
{
    public class Game1 : Microsoft.Xna.Framework.Game
    {
        GraphicsDeviceManager graphics;
        //Матрицы
        Matrix viewMatrix;
        Matrix projMatrix;
        //Модели
        Model ball, cube, plane;
        // Позиция объекта, поворот
        Vector3 avatarPosition = new Vector3(0, 0, -50);
        float avatarlRotation;
 
        // Положение камеры
        Vector3 cameraReference = new Vector3(0, 0, 10);
        Vector3 thirdPersonReference = new Vector3(0, 200, -200);
 
        // Скорости поворота и движения
        float rotationSpeed = 1f / 60f;
        float forwardSpeed = 50f / 60f;
 
        //Поле зрения камеры
        float viewAngle = MathHelper.ToRadians(45.0f);
 
        //Расстояние от камеры до переднего и заднего плана
        //static float nearClip = 5.0f;
        float nearClip = 1.0f;
        float farClip = 2000.0f;
 
        // Установка позиции камеры 2 - вид от третьего лица
        //1 - от первого лица
        int cameraState = 2;
        //Соотношение сторон экрана
        float aspectRatio;
       public Game1()
        {
            graphics = new GraphicsDeviceManager(this);
            Content.RootDirectory = "Content";
        }
 
        protected override void LoadContent()
        {
            //Загрузка моделей
            ball = Content.Load<Model>("ball");
            cube = Content.Load<Model>("cube");
            plane = Content.Load<Model>("plane");
            aspectRatio = (float)graphics.GraphicsDevice.Viewport.Width /
  (float)graphics.GraphicsDevice.Viewport.Height;
        }
 
        protected override void Update(GameTime gameTime)
        {
          //обновить положение объекта
            UpdateAvatarPosition();
            base.Update(gameTime);
        }
 
        protected override void Draw(GameTime gameTime)
        {
            graphics.GraphicsDevice.Clear(Color.CornflowerBlue);
            //Если состояние камеры 1 - вызвать процедуру
            //обновлеие камеры от первого лица
            //если 2 - от третьего лица
            switch (cameraState)
            {
                case 1:
                    UpdateCamera();
                    break;
                case 2:
                    UpdateCameraThirdPerson();
                    break;
            }
            //вывести объекты сцены
            DrawScene();
                      //Если выбран вид от третьего лица - вывести объект
            if (cameraState == 2)
            {
                DrawModel(ball, Matrix.CreateRotationY(avatarlRotation) * Matrix.CreateTranslation(avatarPosition));
            }
 
            base.Draw(gameTime);
        }
 
        //Обновляем состояние объекта
        void UpdateAvatarPosition()
        {
            KeyboardState keyboardState = Keyboard.GetState();
 
            //Поворот влево
            if (keyboardState.IsKeyDown(Keys.Left))
            {
                avatarlRotation += rotationSpeed;
            }
            //Поворот вправо
            if (keyboardState.IsKeyDown(Keys.Right) )
            {
                avatarlRotation -= rotationSpeed;
            }
            //Движение вперед
            if (keyboardState.IsKeyDown(Keys.Up) )
            {
                Matrix forwardMovement = Matrix.CreateRotationY(avatarlRotation);
                Vector3 v = new Vector3(0, 0, forwardSpeed);
                v = Vector3.Transform(v, forwardMovement);
                avatarPosition.Z += v.Z;
                avatarPosition.X += v.X;
            }
            //Движение назад
            if (keyboardState.IsKeyDown(Keys.Down) )
            {
                Matrix forwardMovement = Matrix.CreateRotationY(avatarlRotation);
                Vector3 v = new Vector3(0, 0, -forwardSpeed);
                v = Vector3.Transform(v, forwardMovement);
                avatarPosition.Z += v.Z;
                avatarPosition.X += v.X;
            }
            //Переключить на режим камеры от первого лица
            if (keyboardState.IsKeyDown(Keys.A))
            {
                cameraState=1;
            }
 
            //Переключить на режим камеры от третьего лица
            if (keyboardState.IsKeyDown(Keys.S))
            {
                cameraState = 2;
            }
            //Уменьшение угла обзора камеры
            if (keyboardState.IsKeyDown(Keys.R))
            {
                viewAngle -= MathHelper.ToRadians(1.0f);
            }
            //Увеличение угла обзора камеры
            if (keyboardState.IsKeyDown(Keys.F))
            {
                viewAngle += MathHelper.ToRadians(1.0f);
            }
            //Если новый угол обзора вышел за дозволенные пределы
            //изменяем его
            if (viewAngle > MathHelper.ToRadians(180.0f)) viewAngle = MathHelper.ToRadians(179.9f);
            if (viewAngle < MathHelper.ToRadians(0.0f)) viewAngle = MathHelper.ToRadians(0.1f);
        }
 
        //Обновляем состояние камеры при выбранном виде от первого лица
        void UpdateCamera()
        {
            //Текущая позиция камеры
            Vector3 cameraPosition = avatarPosition;
            //Поворот
            Matrix rotationMatrix = Matrix.CreateRotationY(avatarlRotation);
 
            // Направление камеры
            Vector3 transformedReference = Vector3.Transform(cameraReference, rotationMatrix);
 
            // Новая позиция камеры
            Vector3 cameraLookat = cameraPosition + transformedReference;
 
            //Матрица вида
            viewMatrix = Matrix.CreateLookAt(cameraPosition, cameraLookat, new Vector3(0.0f, 1.0f, 0.0f));
            //проекционная матрица
            projMatrix = Matrix.CreatePerspectiveFieldOfView(viewAngle, aspectRatio, nearClip, farClip);
        }
 
        //Обновляем положение камеры при выбранном виде от третьего лица
        void UpdateCameraThirdPerson()
        {
            //Поворот камеры
            Matrix rotationMatrix = Matrix.CreateRotationY(avatarlRotation);
 
            // Направление камеры
            Vector3 transformedReference = Vector3.Transform(thirdPersonReference, rotationMatrix);
 
            // Позиция камеры
            Vector3 cameraPosition = transformedReference + avatarPosition;
 
            //Матрица вида
            viewMatrix = Matrix.CreateLookAt(cameraPosition, avatarPosition, new Vector3(0.0f, 1.0f, 0.0f));
            //Проецкионная матрица
            projMatrix = Matrix.CreatePerspectiveFieldOfView(viewAngle, aspectRatio, nearClip, farClip);
        }
 
       //Вывод объектов сцены
        void DrawScene()
        {
            //Вывести кубы, расположенные в пять рядов
            //по пять штук в трех уровнях
            for (int x = 0; x < 5; x++)
            {
                for (int y = 0; y < 3; y++)
                {
                    for (int z = 0; z < 5; z++)
                    {
                        DrawModel(cube, Matrix.CreateTranslation(x * 40, y * 3, z * 40));
                    }
                }
            }
            //Вывести плоскость - при выводе увеличиваем модель и поворачиваем соответствующим
            //образом
            DrawModel(plane, Matrix.CreateScale (100)*Matrix .CreateRotationY (MathHelper .ToRadians (90))*
                Matrix.CreateRotationZ(MathHelper.ToRadians(90))*
                Matrix .CreateTranslation (80,-2.5f,80));
        }
 
        //Процедура вывода модели
        //Принимает мировую матрицу для позиционирования модели
        //и переменную модели
 
        void DrawModel(Model model, Matrix world)
        {
            foreach (ModelMesh mesh in model.Meshes)
            {
                foreach (BasicEffect effect in mesh.Effects)
                {
                    effect.LightingEnabled = true;
                    effect.EnableDefaultLighting();
                    effect.Projection = projMatrix;
                    effect.View = viewMatrix;
                    effect.World = world;
                }
                mesh.Draw();
            }
        }
    }
}

 


На рис. 15.3. вы можете видеть состояние игрового экрана проекта P15_3 в режиме вида от третьего лица.


Рис. 15.3. Экран проекта P15_3, вид от третьего лица

На рис. 15.4. вы можете видеть состояние экрана проекта P15_3 в режиме вида от первого лица.


Рис. 15.4. Экран проекта P15_3, вид от первого  лица

На рис. 15.5. вы можете видеть состояние экрана проекта P15_3 в режиме вида от третьего лица с уменьшенным полем видимости камеры.


Рис. 15.3. Экран проекта P15_3, вид от третьего лица, уменьшенное поле видимости

Вопросы

1) Мировая матрица объекта преобразована таким образом: worldMatrix = Matrix.CreateScale(2.0f). Как изменится объект после применения такого преобразования?
  • a. Уменьшится в два раза
  • b. Увеличится в два раза
  • c. Повернется вокруг оси X
  • d. Переместится в начало координат
2) Мировая матрица объекта преобразована таким образом: worldMatrix = Matrix.CreateTranslation(10.0f, 0.0f, -12.0f). Как изменится объект после применения такого преобразования?
  • a. Уменьшится в 2 раза
  • b. Увеличится в 2 раза
  • c. Переместится в позицию 10,0,-12
  • d. Переместится в начало координат
3) Мировая матрица объекта преобразована таким образом: worldMatrix = Matrix.CreateRotationY (MathHelper.ToRadians (10)). Как изменится объект после применения такого преобразования?
  • a. Переместится в позицию 10,10,10
  • b. Уменьшится в 10 раз
  • c. Повернется вокруг оси Y на 10 градусов
  • d. Повернется вокруг оси X на 10 градусов
4) Команда Matrix.CreateLookAt(new Vector3(0.0f, 0.0f, 10.0f), Vector3.Zero, Vector3.Up) позволяет создать камеру, которая
  • a. Находится в точке 0,0,0 и направлена в точку 0,0,10
  • b. Находится в точке 0,0,10 и направлена на точку 0,0,0
  • c. Находится в точке 0,0,1 и направлена на точку 0,0,10
  • d. Находится в точке 0,0,10 и направлена на точку 0,0,1
5) Команда Matrix.CreatePerspectiveFieldOfView(MathHelper.ToRadians(45.0f), aspectRatio, 1.0f, 1000.0f) позволяет настроить перспективную проекцию сцены на экран с углом зрения, равным
  • a. 0,7853 градуса
  • b. 45 градусов
  • c. 180 градусов
  • d. 5 градусов
6) При использовании этого вида проекции объекты, которые расположены дальше от камеры, выглядят меньшими, чем те, которые расположены ближе. Так же объекты подвергаются перспективным искажениям. О каком виде проекции идет речь?
  • a. Ортогональная
  • b. Перспективная
  • c. Аксонометрическая
  • d. Косоугольная
7) При использовании этого вида проекции объекты, находящиеся на различных расстояниях от камеры, не меняют размеров и не искажаются.
  • a. Ортогональная
  • b. Перспективная
  • c. Аксонометрическая
  • d. Косоугольная
1176 Прочтений •  [Пространственные преобразования] [08.08.2012] [Комментариев: 0]
Добавил: Ukraine Vova
Ссылки
HTML: 
[BB Url]: 
Похожие статьи
Название Добавил Добавлено
• Пространственные преобразования Ukraine Vova 08.08.2012
Ни одного комментария? Будешь первым :).
Пожалуйста, авторизуйтесь для добавления комментария.

Проект входит в сеть сайтов «8Gamers Network»

Все права сохранены. 8Gamers.NET © 2011 - 2025

Статьи
Рецензия на Pressure
Рецензия на Pressure
Чтобы обратить на себя внимание, начинающие маленькие разработчики, как правило, уходят в жанры, ...
Рецензия на Lost Chronicles of Zerzura
Рецензия на Lost Chron...
Игры, сделанные без любви и старания, похожи на воздушный шар – оболочка есть, а внутри пусто. Lo...
Рецензия на The Bridge
Рецензия на The Bridge
«Верх» и «низ» в The Bridge — понятия относительные. Прогуливаясь под аркой, можно запросто перей...
Рецензия на SimCity
Рецензия на SimCity
Когда месяц назад состоялся релиз SimCity, по Сети прокатилось цунами народного гнева – глупые ош...
Рецензия на Strategy & Tactics: World War 2
Рецензия на Strategy &...
Название Strategy & Tactics: World War II вряд ли кому-то знакомо. Зато одного взгляда на ее скри...
Рецензия на игру Scribblenauts Unlimited
Рецензия на игру Scrib...
По сложившейся традиции в информационной карточке игры мы приводим в пример несколько похожих игр...
Рецензия на игру Walking Dead: Survival Instinct, The
Рецензия на игру Walki...
Зомби и продукция-по-лицензии — которые и сами по себе не лучшие представители игровой биосферы —...
Обратная связь | RSS | Донейт | Статистика | Команда | Техническая поддержка