Информация

Обсуждало 7 человек

Опрос от автора

Чтобы принять участие в голосовании, зарегистрируйтесь, пожалуйста!

Создание панели инвентаря для квеста.

ActionScript 1.0/2.0
02 октября 2011 в 18:53:01

Как-то раз вздумалось мне сделать настоящий классический квест, со сбором предметов, скрещиванием их между собой и применением на различные объекты. Как человек с ограниченным временем, я решила не изобретать велосипед, а поискать готовое решение в интернете. Но, к моему сожалению, приличного решения я так и не нашла, либо оказалась не в состоянии его понять )). Поэтому было решено создать все с нуля, заодно и потренироваться в программировании. Эта статья предназначена для новичков во флеше, которые возможно столкнутся с такой же проблемой. Статья будет основана на моей игре Зазеркалье, и, соответственно, все примеры взяты из этой игры.
Итак, для создания инвентаря нам понадобятся массивы, вообще для данной задачи они подходят как нельзя лучше. Массивы – это упорядоченное множество данных, каждый элемент которого имеет свой индекс, или, проще говоря, свой порядковый номер. Для данной задачи мы будем использовать как одномерные массивы, так и многомерные.
Для начала создаем новый массив
mas_inventory = new Array();

Для удобства использования в дальнейшем, я создала массив имен предметов, который был нужен для первого уровня игры.
mas_inventory_name = ["книга", "волосы", "полынь", "яйца", "нож", "мышь", "хвост", "зажигалка", "пепел", "стакан", "Зелье", "стакан с яйцами", "стакан с яйцами и полынью", "стакан с яйцами полынью и хвостом"];

В него мы занесли названия всех используемых на 1-м уровне предметов, это позволяет легко к ним обращаться.
Далее создаем массив
mas_inventory_yn = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0];

Это так называемый заполненный массив, т.е. он содержит 14 элементов,
значения которых равны нулю. С помощью этого массива мы определяем, собран ли предмет или нет. Если значение равно нулю, то предмет еще не собран, если единице, то собран. Изначально у нас нет ни одного предмета, т.е. все значения равны 0.
Следующий массив
mas_inventory_position = [];

Это позиция предметов из массива mas_inventory в нашей панели инвентаря, он пока пуст, как и mas_inventory. Потому что мы еще не знаем, какой предмет будет собран первым, какой вторым и т.д.
И наконец, массив mas_proverka, он нужен для проверки пересечения предметов. Т.е. для определения, какой предмет взаимодействует с другим каким либо предметом. Возможно это не самая удачная реализация, но мне она, во всяком случае, была понятна).
Этот массив является многомерным. А точнее двухмерным. Т.к. мы проверяем «пересечение» (взаимодействие) двух предметов.
Мы создаем его и сразу заполняем сотнями при помощи 2-х циклов.
var mas_proverka:Array = new Array(); for (k=0; k<=13; k++) { for (j=0; j<=13; j++) { mas_proverka[[k, j]] = 100; } }

Индексы k и j от 0 до 13 включительно – т.к. у нас 14 предметов. Нумерация идет от 0, а не от 1, поэтому конечный индекс 13. Этот массив представляет собой таблицу, состоящую из 14 строк и 14 столбцов, ячейки которой, в данный момент заполнены сотнями. Сотня это просто условное обозначение пустого пересечения, т.е. условие, когда между предметами нет взаимодействия.
Далее я меняю конкретные значения ячеек, в соответствие с сюжетом игры.
mas_proverka[[4, 5]] = 6; mas_proverka[[7, 1]] = 8; mas_proverka[[3, 9]] = 11; mas_proverka[[2, 11]] = 12; mas_proverka[[6, 12]] = 13; mas_proverka[[8, 13]] = 10;

Числа, которыми я заполняю ячейки, также не случайны, они означают индекс предмета в массиве mas_inventory_name.
Например, mas_proverka[[4, 5]] = 6 означает, что 4 и 5 предмет - нож и мышь (напоминаем, что индексация в массиве идет от нуля), дают при взаимодействии элемент с индексом 6, т.е. хвост.
Также для проверки нам понадобятся 2 переменные
predmet1 = 100; predmet2 = 100;

Итак, в целом участок кода выглядит так
mas_inventory = new Array(); mas_inventory_name = ["книга", "волосы", "полынь", "яйца", "нож", "мышь", "хвост", "зажигалка", "пепел", "стакан", "Зелье", "стакан с яйцами", "стакан с яйцами и полынью", "стакан с яйцами полынью и хвостом"]; mas_inventory_yn = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]; mas_inventory_position = []; var mas_proverka:Array = new Array(); for (k=0; k<=13; k++) { for (j=0; j<=13; j++) { mas_proverka[[k, j]] = 100; } } mas_proverka[[4, 5]] = 6; mas_proverka[[7, 1]] = 8; mas_proverka[[3, 9]] = 11; mas_proverka[[2, 11]] = 12; mas_proverka[[6, 12]] = 13; mas_proverka[[8, 13]] = 10; predmet1 = 100; predmet2 = 100;

Этот участок должен размещаться в кадре перед основной сценой, в которой мы будем использовать панель инвентаря.
Теперь можно приступать, так сказать, ко второму этапу. Это сбор предметов и их взаимодействие. Предмет, как правило – это клип в кадре. Сбор предметов у меня осуществляется по нажатию на клип.
Например,
_root.fire_press.onPress = function() { mas_inventory_yn[7] = 1; //заменяем значение в массиве, которое показывает, что предмет собран. mas_inventory_position.push(7); //добавляем в конец массива элемент, число 7 показывает, какой именно предмет мы собрали, это предмет с индексом 7 из массива mas_inventory_name, а именно – зажигалка. };

Таким образом, мы заполняем массив mas_inventory_position .
Далее переходим к выбору предметов в меню и проверки их взаимодействия. Рассмотрим на примере одного слота меню.
Первое условие, которое мы проверяем –
if (predmet1 == 100) { predmet1 = mas_inventory_position[0]; // если предмет не был выбран, т.е. на него не кликали мышкой для выбора, то мы выбираем данный предмет, т.к. это первый слот меню – мы приравниваем переменную predmet1 к первому элементу из массива mas_inventory_position (т.е. элементу с индексом 0). А значение этого элемента показывает нам, что именно за предмет мы взяли. } else { predmet2 = mas_inventory_position[0]; // Если же предмет был уже выбран предыдущим действием, то мы приравниваем уже переменную predmet2 к первому элементу из массива mas_inventory_position (подразумевается, что predmet1 у нас уже выбран до этого. }

Напоминаю, что 100 – это у нас условно пустое значение, т.е. предмет не выбран.
Далее проверяем условие
if (predmet1 == predmet2) { predmet1 = 100; predmet2 = 100; }

Т.е. если игрок два раза подряд щелкнул на один и тот же предмет – выбор отменяется.
Обе переменные снова принимают нулевое значение.
Далее проверяем условие
if (mas_proverka[[predmet1, predmet2]] == 100) { predmet1 = 100; predmet2 = 100; }

Т.е. смотрим в нашем двумерном массиве пересечений нулевые значения,
например predmet1=7 , а predmet2 =3,
Программа проверяет пересечение 7 –го столбца и 3- ей строки, если они равны 100, то обе переменных опять «обнуляются».

И, наконец, самый сложный случай, когда наступает взаимодействие.
if ((mas_proverka[[predmet1, predmet2]] != 100) and (mas_proverka[[predmet1, predmet2]] != undefined)) { mas_inventory_position.splice(0, 1); //удаляем один элемент массива mas_inventory_position.splice с индексом 0 (т.к. это у нас 1-й слот) , он же второй предмет, на который мы кликнули мышкой и который привел к взаимодействию (predmet2). //Далее удаляем первый предмет, который привел к взаимодействию (predmet1), который мы выбрали на шаг раньше, при удалении проверяем пограничные варианты, если на момент взаимодействия мы собрали всего 2 предмета. for (k=0; k<=mas_inventory_position.length; k++) { if (mas_inventory_position[k] == predmet1) { if (k == 0) { mas_inventory_position.shift(); } else if (k == mas_inventory_position.length) { mas_inventory_position.pop(); } else { mas_inventory_position.splice(k, 1); } } } mas_inventory_position.push(mas_proverka[[predmet1, predmet2]]); //добавляем в конец нашего массива предмет, получившийся в результате взаимодействия. predmet1 = 100; // обнуляем переменные predmet2 = 100; // обнуляем переменные } }

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

Обновлено: 03 октября 2011 в 02:27:21

Обсуждение (вниз)

Не хватает только вашего мнения. Зарегистрируйтесь, чтобы написать!

04 октября 2011 в 16:31:57

(начинаю биться головой об стенку. после 5 удара кожа рвется, оставляя кровавые следы. после 10 удара титановый череп начинает крошить кирпич)

04 октября 2011 в 13:47:44

В этом году, например, вышло "Черное зеркало 3". Я в первые 2 части играл, отличный квест кстати. И проблемы пиксельхантинга там нет, активные точки можно подсветить в любой момент.

04 октября 2011 в 13:40:55

"разве пиксельхантинговые квесты не померли еще в середине 90х?"

cyborg, а с чего ты это взял? У них есть своя преданная аудитория и они прекрасно сосуществуют с другими жанрами.

04 октября 2011 в 10:12:55

Это ты умрешь скоро

04 октября 2011 в 09:36:19

разве пиксельхантинговые квесты не померли еще в середине 90х?

04 октября 2011 в 08:01:44

Или что ?

04 октября 2011 в 00:28:00

metseldr, хватит мусорить...

04 октября 2011 в 00:27:11

"Блииин ваще чет трудное решение, почему бы просто не добалять предметы в массив по ходу игры, а потом удалять их оттуда?"

Там не просто предметы, а, так сказать, "запчасти" для предметов. И это усложняет задачу. Хотя, конечно, код можно сделать более компактным. Но это уже дело вкуса :-)

03 октября 2011 в 22:49:26

sO3WXOZIT0E
&feature=related

03 октября 2011 в 22:13:51

BsjAzOGe0cI

03 октября 2011 в 21:27:35

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

03 октября 2011 в 12:12:52

Надо нашего киборга( садлера )закинуть в прошлое что бы он прихлопнул с.....

03 октября 2011 в 11:48:21

И у каждого терминатора будет панель для инвентаря. Блин, да они ж тут всё растащат.

03 октября 2011 в 11:35:29

Это програмиромые коды запуска терминаторов
что же ты сделала
Теперь всем знают как унечтожить всем
Ты нас обрекла
Такой и знал что если и будет конец света то в нем будет виновата бабай

03 октября 2011 в 02:06:11

Haruka25, ты можншь отредактировать и отправить на перемодерацию :)
Ну а вобще все доступно объяснила

03 октября 2011 в 02:03:26

Мэр AleXNoD, учту на будущее, спасибо)

02 октября 2011 в 23:23:01

Код красивее бы выглядел с тегами code.
http://fundux.ru/help/format
Fundux.ru v.3.0 © 2006-2021 AleXNoD
Портал русских флеш игр и flash мультов