Как сделать движок для игры

Как написать свой игровой движок с нуля

Возможно, тема надоевшая, но я поискал в интернете на эту тему и понял что в интернете(youtube, yandex, habr) нет ничего полезного, вернее оно есть, но без объяснений.

Сразу скажу что, C# я знаю больше чем C++, просьба отталкивать от этого.

Что я подразумеваю под словом ‘с нуля’.
1. Нужно определиться с языком программирования. C++ или C#?
Если я напишу: “Мне нужен обоснованный ответ!”, будет немного грубо.
По этому, желательно обосновать ответ и написать названия книг по выбранному языку.
Не нужно писать: вот C++ быстрее чем C#, пиши на C++ и т.д.
2. Какой фреймворк? (Если неправильно назвал поправьте)
OpenTK, GLFW и т.д. Источники, где можно поподробнее разобраться.
3. Что нужно знать в языке программирования что бы написать свой игровой движок?
Пример ответа: Нужно уметь пользоваться массивами, отладчиком, искать ошибки и т.д.
4. Ну и с чего стоит начать, после изучения языка.

Вроде всё изложил.

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

Написать свой движок или воспользоваться существующим?
Доброго времени суток, уважаемые форумчане! Работаю в игровом движке Unity3D уже полтора года.

Как установить игровой движок(Crystal Space)?
Как установить игровой движок(Crystal Space) ?

Игровой движок
Всем привет! У меня к вам вопрос: Я прочитал про Ogre3D, и понял, что это вовсе не игровой.

C++ 3D игровой движок
Добрый день. Подскажите пожалуйста трёхмерный игровой движок, который можно подключить к Visual.

Ответ на твой вопрос зависит от того что ты хочешь получить на выхлопе?
По тому что если тебе нужен CryBiteUnrealUnity 10K5000 то запросы одни, а если тебе двиг для майнкрафта то запросы другие.

Добавлено через 1 час 0 минут
Я предположу, что ты делаешь CryBiteUnrealUnity 10K5000.

С языком все просто, c# это по сути скриптовый язык. В C# есть встроенный менеджер памяти, что для риалтайма – зло.
В с++ есть возможность прямого управления памятью. У с++ есть шаблоны, что часто очень полезно. В остальном по сути братья близнецы. Хочется тебе с# бери его, если же не хочешь потом жалеть, то с++.

Те же фростбайты, анриалы, юнити и край энжины написаны на c/c++, сам сделай выводы.

У шарпа вообще плюсов нет :), помогите их найти? Единственный аргумент в таких спорах что я слышал, это дот нет и куча библиотек, так ведь у с++ тоже их море, один qt если вспомнить, а в контексте разработки с нуля с# не о чем

Опять же, если ты будешь писать свой серьезный движ то использовать сторонние библиотеки не будешь, по тому что все будешь писать под свои запросы. По тому openTK тебе не нужен, тебе нужно что-то типа glfw+gluw, которые только лишь создают окно и импортируют функции api opengl (ты же на opengl смотришь?), но можешь и по хардкору #include и самому импортировать функции и создавать окна.

Все что нужно знать об openGL есть тут.

Конкретно тебе нужно знать:
1.1) как создать окно
Первый самый простой этап.
2.1) ты должен узнать что такое шейдер, как его скомпилить на гпу, как его применить.
2.2) как создать vao (обязательно нужно разобраться как использовать несколько атрибутов), и как его выводить (рисовать), тут ты узнаешь что заходит на вход вершинному шейдеру и что выходит из фрагментного.

Тут ты уже поймешь как работает opengl, тебе станет очень радостно если ты добрался до сюда.

2.3) Ты должен загрузить изображение, создать текстуру, установить ее в семплер, внести изменения в код шейдера и любоваться своей текстурой.
Второй этап закончен. Ты уже можешь что-то рисовать посредством шейдеров.

Вот от сюда будет начинаться что-то серьезное.
3.1) Нужно будет разобраться с тем что такое fbo, как его создавать, как его применять/чистить и как в него рендерить.
3.2) Зная что такое fbo, нужно будет в первый раз что то отрендерить в текстуру (тобишь в fbo), сделаешь тени.

Вот на этом моменте кончается 90% работы. Можешь начать с этого после изучения языка.

Потом ты еще должен будешь выбрать аудио апи аля OpenAl.

Что нужно знать о языке?
Само собой нужно уметь работать с массивами, циклами (for, while), блоками ветвлений (if/else, switch/case), структуры. Потом ты должен знать как алоцировать память динамически, аля new и delete, указатели ( не умные, а обычные, умные таковыми только называются).
Не плохо бы знать ооп (классы, наследование), опять же, перегрузка и таблицы виртуальных функций для риалтайма зло.

Самые важные вопросы ты не спросил. Это что нужно знать о том что нужно знать о программировании.
Так вот, знать нужно алгоритмы и патерны проектирования. Если с первым все ясно, то второе нужно по тому что иначе твой вдиж станет лапшой с такой скоростью что ты не заметишь.

Игра своими руками. Создание трехмерного игрового движка на базе GLScene

С этого номера мы начинаем публикацию серии статей, в которых детально рассмотрим различные этапы создания трехмерной игры. Вы повысите свои навыки программирования и, что называется, заглянете за завесу тайны, отделяющую серьезных разработчиков игр от простых смертных.
Движок любой игры складывается из многих и часто независимых частей-кирпичиков: контроль столкновений, физическая модель, игровой интерфейс, главное меню, загрузка уровней и многое другое. Есть специфические кирпичики, которые нужны только для какого-то одного жанра. Например, модуль погодных явлений важен и нужен в авиационном или морском симуляторе, а в стратегии реального времени он второстепенен или вообще не нужен, а в футбольном симуляторе ни к чему модуль выстрелов. Но несколько десятков кирпичиков присутствуют в любой игре. В серии статей мы расскажем о каждом из таких кирпичиков, покажем, как он реализуется и как его связать с остальными. К концу цикла вы сможете из этих кирпичиков собрать свою собственную компьютерную игру довольно высокого уровня.

Читать еще:  Из чего дешевле сделать баню

Что это вы тут делаете?
Для тех, кто пропустил какие-то из предыдущих моих статей (или даже все), отвечу на возникшие у вас вопросы. Так сказать, небольшое техническое вступление.
Почему Delphi? Эта среда разработки и язык программирования Object Pascal достаточно гибкие, чтобы создать полноценную трехмерную игру практически любого жанра с современным уровнем графики. Многие возразят, что стандартом де-факто разработки компьютерных игр является MSVC++ или другие среды на основе С++. Но подобные стандарты, как это часто бывает, складываются стихийно. Не будем смешивать два понятия — язык и среда разработки.
C++, безусловно, мощнее, чем Object Pascal. Но он и менее высокоуровневый, то есть в разы сложнее. Для новичков С++ подходит слабо. Object Pascal же не только простой, но и достаточно гибкий, чтобы на нем можно было разработать полноценную компьютерную игру современного уровня. Теперь о средах. Тут так категорично не скажешь. Среда разработки

Несмотря на то что все примеры кода, которые будут приводиться в этом цикле статей, будут написаны на Delphi с применением GLScene, они будут полезны и тем, кто программирует на других языках и с другими графическими библиотеками. Ведь общие принципы создания графического движка не зависят ни о того, ни от другого. Итак. мы начинаем.

Зачем нужен трехмерный движок?
Товарищи новички, сосредоточьтесь! Возможно, то, что я сейчас скажу, с первого раза будет не очень понятно. Обязательно перечитайте и вникните: это один из основных принципов программирования вообще и разработки сложных систем (а игра — это сложная система) в частности. Представьте себе какую-нибудь проcтенькую игру. Пинг-понг, к примеру. Программист написал его на чистом OpenGL, исходники уместились строк эдак в 200. Что там будет движком, а что основным кодом игры? Так прямо сразу и не скажешь. А если подумать, такое разделение на движок и основной код вообще не нужно.

язык программирования (хотя, на самом деле, можно копнуть еще глубже — до железа). Далее идут команды OpenGL API (если мы именно с его помощью программируем). На этом уровне мы можем отдать команду вроде “нарисовать полигон” и “поменять местами видимую и теневую части видеобуфера”. Потом — команды GLScene. На этом уровне мы можем дать команды вроде “построить куб”, “загрузить модель в формате 3ds” и “наложить на модель такую-то текстуру”. А вот дальше —игровой движок. И, наконец, игровой код, который может давать игровому движку команды вроде “загрузить уровень”, “выстрелить таким-то персонажем из такого-то оружия” и “показать заставочный ролик”. В идеальном случае каждый уровень абстракции пользуется командами только предыдущего уровня. Не всегда это возможно. Но к этому надо стремиться, так как в таком случае код будет быстрым, удобным и легкочитаемым.

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

Или же вызываем функцию Assigned, которая делает то же самое. И вот тут вас подстерегает один гигантский подводный камень, на который рано или поздно наталкивались все программисты. Если вы освободили объект методом Free, это не гарантирует, что переменная объекта стала равно nil! То есть при определенном стечении обстоятельств в примере выше, даже если сфера уничтожена, условие будет выполняться. Если вы в условии после проверки обращаетесь с этой сфере (а так почти всегда и бывает), произойдет критическая ошибка, что чревато вылетом игры в синие форточки. Чтобы гарантировать, что освобожденный объект станет равным nil, используйте специальную процедуру FreeAndNil, например:
FreeAndNil(Sphere)
Теперь вы можете быть уверенными в том, что никогда не обратитесь к уже несуществующему объекту. Описанную процедуру создания и уничтожения объектов можно применять к любым объектам GLScene.

Зачем играм аккумулятор?
Рассмотрим пример выше с пулеметом. Обычно в играх пули — это не просто сферы, а сложные объекты, у которых к тому же еще и текстура имеется. Каждый раз, когда вы создаете пулю, освобождается участок памяти, устанавливаются

свойства этой пули, загружается модель пули, загружается текстура (с винчестера!). Все это занимает определенное время. Если число пуль, которые изрыгает пулемет в секунду, очень велико, могут начаться дикие тормоза, особенно на слабых компьютерах. С уничтожением пуль такая же проблема: надо выгрузить объект, освободить память. То же самое относится не только к пулям, но и к любым объектам, которые часто появляются и исчезают, например к каплям дождя, искрам от электропроводки. Подобная расточительность системных ресурсов в компьютерных играх неприемлема. Вы же не хотите, чтобы вашу игру можно было запустить только на суперкрутой графической станции?
Выход простой. Прикидываем, сколько в среднем объектов подобного рода может существовать одновременно. Допустим, пулемет может выбросить несколько сотен пуль за десяток секунд, и за этот же десяток секунд пули обязательно долетят до цели. Перед началом игры создаем все сто пуль. Лучше всего это делать во время загрузки уровня. Небольшой задержки никто не заметит. Далее пули помещаются в список или массив, который называем аккумулятором. Делаем пули невидимыми или выносим их куда-нибудь за пределы игрового пространства. Как только пулемет начал стрелять, вместо того чтобы создавать пули, мы перемещаем в нужное место уже созданные пули из аккумулятора и делаем их видимыми. Как только пуля достигнет цели, мы не уничтожаем ее, а вновь делаем невидимой и помещаем в аккумулятор. В итоге для каждой пули мы экономим время создания и время уничтожения. А это очень и очень много! А что если мы немного ошиблись в своих прикидках, пули в аккумуляторе кончились, а пулемет продолжает стрелять? Тут уж ничего не поделаешь — придется новые пули создавать динамически, пока в аккумулятор не вернутся старые. И новые пули тоже не будем уничтожать, а запасем в аккумуляторе — вдруг еще понадобятся.

Читать еще:  Как сделать азиатские глаза

Tree:=TGLFreeFrom(glscene1.objects.AddNewChild(TGLFreeFrom));
//Загружаем
его модель:
Tree.LoadFromFile(‘Tree.3ds’);
//Загружаем его текстуру:
Tree.Material.Texture.Disabled:=false;
Tree.Material.Texture.Image,LoadFromFile(‘tree.jpg’);
//А теперь создадим десять деревьев-клонов в случайных местах:
for i:=1 to 10 do begin
//Создаем очередной прокси-объект
proxy:=TGLProxyObject(glscene1.objects.AddNewChild(TGLProxyObject));
with proxy do begin
//В свойство MasterObject записываем наше дерево-образец
MasterObject:=Tree;
//Показываем, что наследоваться должна только структура объекта
ProxyOptions:=[pooObjects];
//Ориентацию дерева в пространстве надо оставить неизменной
Direction:= Tree.Direction;
Up:= Tree.Up;
//А вот положение задаем случайное
Position.X:=Random(100);
Position.Y:=Random(100);
//И повернем дерево на случайный угол, чтобы лучше смотрелось
RollAngle:=Random(360);
end;
end;
Теперь у нас есть десяток деревьев по цене одного. Обратите внимание, что если мы как-нибудь изменим объект-оригинал, это изменение мгновенно отразится на всех объектах-клонах.

* * *
Мы рассказали о первом кирпичике. В следующих статьях мы подарим вам целый грузовик таких кирпичей, из которых вы сможете построить трехмерный игровой движок своей мечты. Ну а чтобы вам было проще, на компакт мы выкладываем последнюю протестированную версию GLScene.

Game Engine своими руками #1

Сегодня мы поговорим об игровых движках, причем не о том, как и где их можно надыбать (об этом уже много говорилось в твоем любимом Х.), а о том, как самому написать и обустроить этот самый движок, чтобы потом не было стыдно ни тебе, ни мне. Дело это, скажу сразу, довольно сложное, причем сложное на столько, что на нем можно хорошо заработать и прославиться, чем многие программеры и пользуются. Я не буду пытаться рассказывать тебе о том, как сделать хорошую игру (может быть в следующий раз), не буду рассказывать и о том, как написать ту или иную часть движка, в этой статье ты вообще не увидишь ни одной строчки кода, а лучше расскажу о том, о чем следует хорошенько подумать прежде,
чем бросаться писать свой движок, и как в
общем можно организовать этот процесс, чтобы добиться хорошего результата малой кровью.

Если ты решил написать игровой движок, то значит ты уже хоть что-то знаешь, а как минимум неплохо владеешь тем или иным языком программирования. Если ты вынес со школьной скамьи основы Бейсика, то тебе, конечно, выбирать не приходится, но я, все же, не советовал бы тебе браться за игру, пока ты не овладеешь более совершенным инструментом. Если ты пишешь только на Delphi, и пишешь довольно долго, то у тебя есть хоть какие-то шансы выжить, но в идеале желательно овладеть языком Си, все-таки все солидные игры пишутся сегодня именно на нем. Лучше всего для нашего дела подойдет Visual C++ от Microsoft, желательно шестой версии, хотя это и не принципиально. Если ты долгое время общался с другими компиляторами, например от Borland, то тебе, конечно, имеет смысл оставаться в родной среде.

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

Прежде, чем писать движок, надо точно определиться с его специализацией и возможностями. Конечно, можно сделать игру и без предварительных планировок и раздумий, но поверь мне, тебе будет намного легче потом, если ты потратишь немного времени и обдумаешь все детали проекта сейчас. Первое, о чем стоит задуматься так это тип игры, для которой твой движок будет предназначен: будет ли это продвинутая RPG, либо гоночная аркада, либо это будет очередной шутер аля Quake. Будет ли твой движок поддерживать моды или он будет абсолютно закрытым. Стоит ли писать поддержку сети или можно обойтись сингл-плейером с глубоко проработанным сюжетом. Разберемся со всем этим по отдельности.

И так, давай разберемся в чем же кроется принципиальная разница при написании движка взависимости от его специализации.

Если твой движок будет предназначаться для простенькой двухмерной аркады или скроллера, то тебе имеет смысл оформить свой движок в виде статичной (LIB) или динамической (DLL) библиотеки, описать в ней несколько необходимых высокоуровневых функций для вывода спрайтов, анимации палитры и воспроизведения звуков. Этого тебе вполне хватит. Потом, когда ты будешь писать игры, ты просто подключишь эту библиотечку с движком и воспользуешься
необходимой функцией.

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

При создании 3D движка для шутеров вроде Анрыла и Квейка, очевидно, в первую очередь стоит позаботиться о рендере, т.е. той части движка, которая будет отвечать за прорисовку (рендеринг) окружающего мира. Ты должен заранее определиться с системой, которую ты планируешь использовать. Будут ли это BSP-деревья (Quake), портальный движок (Unreal) или quad-деревья (Tribes). Особо ярые энтузиасты могут заняться строганием воксельного движка.

Читать еще:  Как сделать div ссылкой

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

Уверен, что про моды ты слышал не раз. Может быть, даже сам принял участие в их создании и уж точно попробовал клепать уровни для любимой Кваки или Халф-лайфа. Сейчас инет просто расходится по швам от обилия модов для игрушек, есть люди, которые до сих пор пишут моды для первоквака. С помощью мода первоначальную игру можно просто-таки вывернуть наизнанку, поменять не только внешний вид, но и
кардинально перевернуть гейм-плей, а можно просто слегка изменить правила, например замедлить практически до нуля скорость снарядов от BFG и так вот резвиться. Всей этой романтики
не было бы вообще, если бы умные программеры, такие как Джон Кармак, не предусмотрели бы поддержку этих самых модов в своих движках.

Ты можешь спросить, почему большинство игр все же не поддерживают моды если это так круто? Ответить однозначно на этот вопрос довольно сложно, но можно привести несколько основополагающих доводов. Во-первых, поддержка модов дело довольно сложное, а порой совсем и не нужное, представь себе мод “Rocket Arena” для Сапера. Во-вторых, поддержка модов может нанести, не очевидные сначала, как моральные, так и финансовые убытки разработчику, если какой-нибудь Вася из Таганрога выложит в сеть мод, форматирующий винт при каждом запуске игры. Поэтому-то Кармак и пишет собственные компиляторы, чтобы еще на этапе создания мода присечь попытки деструктивной деятельности.

Существует вариант, когда движок поддерживает не моды, а внешние ресурсы в виде самодельных карт к игре, моделек, текстурок, звуков и т.п. Но в этом случае стоит серьезно задуматься о написании собственных утилит или о поддержке существующих бесплатных редакторов, потому что не у всех юзеров на компе стоят лицензионные 3D Studio MAX и Photoshop (ха-ха).

ОК, ты окончательно и бесповоротно решил писать поддержку модов, тогда давай обсудим как это все дело можно обустроить. Если ты хочешь разрешить пользователям модифицировать только ресурсы, то тебе не о чем беспокоиться, всего лишь нужно предусмотреть чтение небольшого файлика из каталога с модом, в котором будет сказано, как сам мод называется и какую карту нужно запустить первой, этого достаточно (в Half-Life этим файликом был ‘liblist.gam’). Если же ты хочешь разрешить программирование мода, то это более серьезно. Нужно подумать о безопасном месте в котором код мода будет храниться. Это не может быть самостоятельное приложение, так как моду необходимо, чтобы была запущена сама игра. Самым популярным решением является использование DLL (иногда разработчики меняют у файла расширение, чтобы смутить окружающих). DLL (Dynamic-Link Library) или динамические библиотеки это файлы в которых хранится набор некоторых функций, которые затем могут быть вызваны из любой другой программы при условии, что программа знает имя функций содержащихся в DLL. Когда моды организуются в виде динамических библиотек, заранее оговаривается какие функции по умолчанию должны содержаться в коде мода, а затем движок просто вызывает эти функции, не задумываясь над тем с каким именно модом он работает и где расположены функции, которые он вызывает. Причем код самой “родной” игры также можно выполнить в виде мода.

Программирование движка для игр поддерживающих мультиплейер – дело архисложное. Тут мало уметь написать код отправляющий пакет данных, нужно хорошенько обдумать как будет организован сам процесс общения компьютеров.

Наиболее распространенной является модель “Клиент-Сервер”, когда один компьютер назначается сервером и начинает игру, а другие машины-клиенты потом к нему коннектятся, т.е. подсоеденяются. Сервер периодически опрашивает клиентов на предмет новых совершенных игроками действий, собирает инфу обрабатывает и раздает обратно, чтобы клиенты могли узнать последние новости друг о друге. На сервере хранится вся информация о положении и действиях игроков и других важных объектов. Если связь с клиентом была потеряна, то сервер либо делает его недоступным для других клиентов, либо просто оставляет его на растерзание врагам. Всякая мелочь типа разлетающихся гильз, облачков дыма от выстрелов, пятен крови и т.п. дело сугубо личное для каждого клиента и поэтому обрабатывается именно на клиентской машине. Сервер просто сообщает клиентам, что, например, игрока номер 2, только что офигенно разнесло на куски взрывом гранаты, а клиент уж сам решает рисовать эти куски или нет,
в зависимости от игровых настроек. Само собой игрок сидящий на сервере получает некоторые преимущества, так как вся информации крутится на его компе, особенно это заметно при плохом коннекте у клиентов. Что самое интересное, при такой организации сетевых взаимоотношений в движке можно не писать отдельно код для сингл-плейера и код для мултиплейера, просто при одиночной игре одна и та же машина выполняет роль как сервера, так и клиента. Все очень просто

Ну что, надеюсь ты понял, что написание движка дело довольно ответственное и это тебе не под “Ya mama” зажигать. Но я верю, что у тебя все получится, а если ты еще не почувствовал силы в своих руках, тогда не расстраивайся, мы сделаем все что сможем, чтобы помочь тебе в твоих девелоперских начинаниях. Главное не останавливайся перед трудностями и у тебя все получится!

Источники:

http://www.cyberforum.ru/game-engine/thread2265455.html

http://www.igromania.ru/article/4018/Igra_svoimi_rukami_Sozdanie_trehmernogo_igrovogo_dvizhka_na_baze_GLScene.html

http://xakep.ru/2001/12/14/14126/

Ссылка на основную публикацию
Статьи на тему: