Как сделать игру на renpy

Создание простой игры в RenPy

Создание визуальных новелл далеко не такое сложное дело, как может показаться. И поможет нам в этом деле движок RenPy: http://renpy.org. С одной стороны, движок простой и будет понятен даже для начинающих. С другой стороны, движок достаточно мощный и позволяет создавать реально крутые игры. Для начала движок нужно скачать и установить. Ничего сложного в этом процессе нет, все настройки по умолчанию хороши. Вот так выглядит главное окно RenPy:

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Слева список проектов, справа опции активного проекта (в списке проектов выделен синим). Чтобы создать свою игру нужно кликнуть “Добавить новый проект” под списком проектов. Далее движок задаст несколько простых вопросов. Помните, имя игры должно быть на английском языке.

Итак, после создания проекта можно приступать непосредственно к написанию игры. В списке редактирования выбираем script.rpy, открывается редактор файлов (редактор по умолчанию, предлагаемый RenPy — Editra достаточно хорош). Мне нравятся тёмные цветовые схемы для написания текстов, так что тема Dessert меня просто спасает. Вот как выглядит Editra после некоторой настройки у меня:

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

По коду тут тоже всё достаточно просто. В строке 7 определяем персонажа с именем “Эйлин”, имя которого будет писаться текстом цвета #c8ffc8 (цвета можно взять в любом графическом редакторе, например, GIMP или Photoshop). Для краткости написания персонаж назначен на короткое имя “e”. В 13 и 15 строке буквально написано: персонаж “e”(Эйлин) говорит на экране то, что указано в кавычках. Строки, начинающиеся со знака решётки (#) являются комментариями разработчика и на ход выполнения не влияют.

Сделаем немного графики для игры. По умолчанию разрешение нашей игры 800х600. Эту настройку можно поменять в файле options.rpy, но для первой игры такое разрешение оптимально. Поэтому нужно создать в Comipo панель размером 800х600. При изменении размера с помощью перетаскивания мышью возле панели пишется, какого она размера:

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Пускай в игре мы хотим воссоздать вот такую сценку:

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

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

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Код создания персонажей уже был рассмотрен. Здесь мы в строках 1 и 5 создаём новых персонажей: m и dex. Нововведением являются состояния персонажа и картинки для каждого состояния. Например, для персонажа m задано состояние oho, ему соответствует картинка Mala-o.png (строка 2).

Игра начинает выполнение с метки label start: (11 строка). Далее показываем, что сначала у нас всё будет происходить на чёрном экране (scene black). Строки 13 и 14 — просто текст, который будет показан на экране. Модификатор with показывает модификатор (анимацию), с которым будет отображаться данный объект. Анимаций много, применяться могут чуть ли не к чему угодно.

Строка 16: show dex norm at left with dissolve. Читается так: показать персонажа dex в состоянии norm, слева, с анимацией плавного появления. Строка 17 — также просто отображение текста, но так как перед текстом у нас есть имя персонажа, то оно тоже будет отображено.

Строки 23 и 24 — анимация обмена мест Мали и Дэкса. В этих строках используется команда show, но так как персонаж уже есть на экране, то к нему просто будет применена анимация.

По сути — всё, наша первая игра готова. Она имеет небольшой исходный код, не очень сложна для понимания. Здесь кроется ещё одна хитрость в изучении RenPy — изучать его надо постепенно, по одной добавляя новые фишки, и смотря как они влияют. Хорошим подспорьем является Руководство для начинающих. Ещё много полезных ссылок можно найти в русской Wiki проекта.

Источник

Пишем текстовую игру на Python/Ren’Py ч.2: мини-игры и подводные камни

Краткое содержание предыдущих двадцати пяти тысяч серий: мы пишем текстовую игру про плавание по морю и ввязывание в истории. Пишем мы её на движке Ren’Py, который изначально предназначен для визуальных новелл, но после минимальной настройки способен делать всё, что нам надо. В прошлой статье я рассказал, как сделать простенькую интерактивную читалку, а в этой мы добавим ещё пару экранов с более сложными функциями и наконец поработаем на питоне.
Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Прошлая статья закончилась на том, что игрок может читать текст, смотреть картинки и влиять на развитие сюжета. Если бы мы собирались портировать книги-игры Браславского или писать CYOA в духе Choice of Games – этого бы хватило. Но в игре про мореходство нужен хотя бы простенький интерфейс собственно мореходства. Собрать полноценный симулятор, как в Sunless Sea, в Ren’Py можно, но трудозатратно и в целом бессмысленно. К тому же мы не хотим сделать своё Sunless Sea с бурятками и буузами, поэтому ограничимся чем-то вроде глобальной карты в “Космических Рейнджерах”: десяток-другой активных точек, из каждой из которых можно отправиться в несколько соседних. Примерно вот так:

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Displayables, экраны и слои

Для самого интерфейса нам нужно просто вывести на экран кучу кнопок (по одной на каждую точку) и фоновый рисунок; для этого хватит одной Displayable типа Imagemap. Принципиально она не сильно отличается от своего аналога в HTML: это картинка, на которой определены активные зоны, каждая со своим действием. Однако работать с голой Displayable неудобно, да и с архитектурной точки зрения это некрасиво. Поэтому, прежде чем браться за код, стоит разобраться с иерархией элементов, которые Ren’Py выводит на дисплей.

Самый нижний уровень – это Displayables, то есть виджеты, встроенные или созданные разработчиками конкретной игры. Каждый из них выполняет какую-то базовую функцию: показывает картинку, выводит текст, обеспечивает ввод и т.п. Displayables обычно группируются в экраны, которые обеспечивают уже более абстрактные взаимодействия: например, вывод текста и внутриигровые меню выполняются экраном nvl, который включает собственно текст, фон, рамку и кнопки меню. Одновременно можно показывать сколько угодно экранов: на одном, к примеру, может быть текст, на другом кнопки, регулирующие громкость музыки, а на третьем какие-нибудь летающие поверх всего этого снежинки. По мере необходимости можно показывать или убирать отдельные экраны с мини-играми, меню сохранений и всем остальным, что нужно для игры. И, наконец, существуют слои. Работать напрямую со слоями нужно нечасто, но знать об их существовании необходимо. Фоновый рисунок, например, не имеет отношения к системе экранов и выводится ниже них в слое master.

Итак, описание экрана путешествий выглядит следующим образом:

Сперва объявляется экран map_screen(). Тэг опциональный; он просто позволяет группировать экраны для команд типа “Убрать все экраны, связанные с перемещением”. Zorder – это “высота” экрана, по которой решается, какие элементы будут друг друга заслонять. Поскольку мы задали zorder=2, а у экрана nvl дефолтный zorder=1, во время путешествия игрок не будет видеть окна с текстом. Но самое главное – этот экран модальный, то есть никакие элементы ниже него не будут получать события ввода. Получается, что экран nvl с появлением карты блокируется, поэтому нам не нужно самим отслеживать game state и следить, чтобы клик по карте заодно не промотал текст.

Сам Imagemap состоит из двух основных элементов: тэга auto и списка активных зон. Auto содержит ссылку на набор файлов, которые будут использоваться в качестве фона. Именно набора, а не единой картинки: отдельно лежит файл, в котором все кнопки нарисованы как неактивные, отдельно – в котором все они нажаты и так далее. А Ren’Py уже сам выбирает нужный фрагмент из каждого файла и составляет картинку на экране. И, наконец, активные зоны (hotspot). Они описываются кортежем из четырёх целых чисел (координаты и размер) и объектом действия. Кортеж мы не хардкодим, а используем атрибут объекта; в описании экрана вместо значения всегда можно вставить переменную или атрибут. Объект действия описывает, что произойдёт по нажатию кнопки и контролирует, должна ли быть кнопка активна в данный момент. Ren’Py предоставляет довольно много встроенных действий для рутинных задач типа переходов по сценарию или сохранения игры, но можно сделать и свой. Наконец, последним добавляется рисунок корабля и трансформация, благодаря которой он не просто выводится на экран, а ползёт из точки А в точку Б. Трансформации описываются отдельным языком ATL (Animation & Transformation Language).

С экранами связан один подводный камень: код экрана исполняется не непосредственно перед его показом, а заранее. Происходит это когда угодно движку и сколько ему угодно раз, поэтому всё, к чему в этом коде обращаются, должно быть инициализировано ещё до начала игры и не должно влиять на состояние других важных переменных.

Играем в карты

В предыдущей статье я обещал показать два способа делать интерфейсы в Ren’Py. Первый мы только что увидели: он довольно прост, но отнюдь не универсален. Я так и не понял, например, как на экранном языке описать перетягивание объектов мышью и обрабатывать коллизии. Или как верстать экраны, если количество элементов на них определяется в ходе игры. К счастью, Displayables – это полноценные виджеты: они могут включать в себя другие Displayables, ловить события ввода и при необходимости меняться. Следовательно, можно описать в одной Displayable всю мини-игру практически так же, как мы бы сделали для отдельного приложения, и вставить в проект.

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

Игра карточная — значит, в ней фигурируют карты. Код Displayable, отображающей маленькую карту, выглядит вот так:

Это, по сути, самая простая возможная Displayable. Она состоит из двух других: фоновой картинки, выбираемой в зависимости от масти, и текста с номиналом. Оба метода (не считая конструктора) необходимы для работы Displayable: self.render возвращает текстуру, а self.visit –
список всех Displayables, входящих в данную. И она действительно рисует маленькую карту; вот несколько таких карт на экране колоды:

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Уже неплохо, но карта сама по себе умеет только находиться на экране, и то только если её кто-нибудь туда поставит. Чтобы в мини-игру можно было, собственно, играть, нужно добавить внешнюю Displayable, способную обрабатывать ввод и обсчитывать игровую логику. Карты и прочие элементы интерфейса будут входить в неё так же, как текстовые поля и фон являются частями карты. Отличаться эта Displayable будет наличием метода self.event(), который получает на вход события PyGame. ССЫЛКА НА PYGAME.EVENT Примерно вот так (полный код доступен на гитхабе в классе Table):

Об очереди событий можно не беспокоиться: движок сам раздаст все события всем элементам, которые активны в данный момент. Методу остаётся только проверить, интересует ли его произошедшее, ответить на событие и завершить взаимодействие. Взаимодействие в Ren’Py приблизительно эквивалентно тику игровой логики в других движках, но не ограничено по времени. В общем случае это одна команда игрока и ответ игры на неё, хотя иногда (например, при промотке текста) взаимодействия могут завершаться сами собой.
Эту Displayable, как и все остальные, мы завернём в экран:

conflict_table в данном случае не имя класса, а глобальная переменная, в которой хранится соответствующая Displayable. Выше упоминалось, что код экрана в принципе может выполняться в любое время, но перед показом он выполнится непременно, иначе игра не будет знать, что ей, собственно, выводить. Поэтому вполне безопасно непосредственно перед мини-игрой выполнить что-то вроде conflict_table.set_decks(player_deck, opponent_deck) и полагаться на то, что перед игроком окажется ровно то, что нужно. Аналогичным образом по завершении мини-игры можно обратиться к результатам, которые хранятся в том же объекте.

Надо сказать, что использование глобальных переменных – это не ограничение Ren’Py, а наше собственное решение. Поддерживаются экраны и Displayables, которые способны принимать аргументы и возвращать значения, но с ними несколько сложнее. Во-первых, поведение таких экранов слабо задокументировано. По крайней мере, разобраться, в какой именно момент экран начинает своё первое взаимодействие и когда именно возвращает контроль сценарию, довольно сложно. А это очень важный вопрос, так как не зная ответа на него, сложно гарантировать, что весь предшествующий конфликту текст будет показан до начала конфликта, а следующий за конфликтом текст показан не будет. Во-вторых, с использованием глобальных переменных большинство нужных для мини-игры объектов инициализируется только один раз, а потом мы меняем их атрибуты при каждом следующем запуске. В противном случае пришлось бы с каждым конфликтом тратить время на подгрузку всех необходимых файлов; игра ощутимо лагает, если к HDD параллельно обращаются ещё, например, торрент и антивирус. Наконец, к картам обращается не только экран конфликта, но и несколько других экранов, поэтому логично использовать одни и те же Displayables везде, где они нужны.

Послесловие

На этом собственно программная часть разработки заканчивается и начинается наполнение игры контентом. Литературой в игре занимаюсь в основном не я, поэтому о структуре повествования и стилистике рассуждать не стану. На эту тему могу посоветовать почитать, например, классическую статью о структуре CYOA. Или неплохое руководство по написанию убедительных независимых NPC от сценариста 80 days.
Ещё больше ссылок (а также обзоров на свежие англоязычные работы и статей на смежные темы) можно найти в блоге Эмили Шорт.

Источник

Как сделать игру на renpy

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Плюшка №11) Картинки на кнопках выбора

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

А вставка картинки осуществляется прямо в текст кнопки:
menu:
__»С картинкой|icn vk»:
____pass

по желанию можно и выравнивание указать там же, в тексте кнопки:
__»С картинкой, по центру|icn prefs|.5″:
или:
__»Без картинки, по центру||.5″:

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Руслан, Плюшка №1) меню в виде анимированного отгибающегося уголка страницы:

Если хотите вместо «назад» иметь » пропуск » + меню сворачивается.

imagebutton idle «btn_skip_idle.png» hover «btn_skip_hover.png» insensitive «btn_skip_insensitive.png» xpos 763 ypos 75 focus_mask True action [Show(«scr_list»), Hide(«scr_btns»), Skip()]

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Руслан, Плюшка №5) Поле ввода текста с клавиатуры, снабженное кнопками OK и Cancel

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Руслан, Плюшка №10) Добавление слайдера «Прозрачность текстового окна» на экран настроек (или в quick_menu).

wnd_alpha_adjust = ui.adjustment(range=1.0, value=persistent.wnd_alpha, adjustable=True, changed=wnd_alpha_update)
есть range=1.0

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Плюшка №12) Скролл любого, даже не бесшовного фона

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

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Плюшка №13. Добавление шкалы отношений с героями (любвиметр) Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpyКак сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpyКак сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Делаете романтическую игру, в которой нужно пристально следить за ходом развития отношений с персонажами? Тогда эта плюшка для вас! Статья посвящена добавлению в игру специального слайд-бара, отвечающего за наглядное отображение повышения/понижения уровня отношений с героями, будь то любовь или дружба! Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpyЮзайте на здоровье!

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Плюшка №14) Динамический фон

Работая над новеллой «Сателлит», я столкнулся с такой проблемой. У меня был динамический фон – плывущие по небу облака и движущийся немного с другой скоростью пейзаж. Всё было замечательно, пока по экрану не начали двигаться спрайты. По завершении движения или при уничтожении спрайта Renpy перерисовывает фон. А значит, анимация запускается заново. Происходит рывок. Допустим тучки прошли только треть пути, и тут их возвращают на исходную. Выглядит это очень некрасиво. Но чтобы фон не перерисовывался, его можно засунуть в экран, который будет выводиться прямо поверх фона, но под спрайтами. Как это сделать, видно из кода по ссылке.

Как сделать игру на renpy. Смотреть фото Как сделать игру на renpy. Смотреть картинку Как сделать игру на renpy. Картинка про Как сделать игру на renpy. Фото Как сделать игру на renpy

Плюшка №15) Несколько текстбоксов

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

* На экране может быть любое количество диалогов
* Позиция и ширина/высота окошек определяются автоматически
* Настраивается внешний вид диалога, отступы, фон
* На экране может не отображаться основной текстбокс
* Диалоги не исчезнут при нажатии «h»
* При автоматическом создании файла перевода, текст диалогов переводится

Источник

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *