Просмотр полной версии : Можно ли переместить клип от одного родителя к другому?
У меня возникла необходимость в определённый момент вырвать клип-наследник из клипа-родителя на более высокий уровень. Не знаю, можно ли так сделать через скрипт, но в редакторе Flash эта операия была бы эквивалентна действию "Break Apart".
Просто мне нужно сделать скролл на контейнер с объектами. Каждый объект из клипа-контейнера скролла можно перемещать в определённую зону, после чего он там и должен остаться. Но вот как сделать, чтобы после перемещения, он больше не принадлёжал бы клипу-контейнеру, т.е. уходил бы в _root?
Нет, так сделать нельзя.
Доставайте (приаттачивайте) мувики из библиотеки.
То есть каждый раз работать с новым клипом?
Ну хорошо, а можно ли сделать подобие скрола, но который работал бы без клипа-контейнера, и все перемещаемые объекты были бы в _root. При этом объекты, которые следует прокручивать, были бы указаны в массиве.
Можно написать собственный скроллинг.
PS. Вы, случайно, не что-то типа инвентаря делаете?
Возможно такое решение:
Итемы находятся в инвентаре как обычно и скроллируются.
При нажатии (onPress), итем в инвентаре делается невидимым (_visible = false), а в специальный мувике поверх сцены (предназначенном для итемов перемещения по сцене) приаттачивается из библиотеки тот же итем в тех же координатах, визуально подменяя итем инвентаря.
Для точности позиционирования, чтобы не было видно подмены, можно использовать методы localToGlobal (определяем текущее положение итема инвентаря относительно _root), lobalToLocal (переводим эти координаты в нужные координаты контейнера, где будут происходить перемещения итемов на сцене).
Для перемещения итема по сцене использовать onMouseMove.
Для укладки итема в инвентарь то же делать в обратной последовательности.
Как-то слишком негуманно. Может лучше заставить определённые объекты не перемещаться вместе со скролом?
Вполне гуманно и логично. Я бы так сделал.
К тому же часто видим в играх, что итем в инвентаре и итем на сцене выгляд по разному.
Не нужно привязываться к объекту, как к конкретному предмету.
Удобнее всего, когда информация о предметах хранится в самих итемах. Я реализовал перетаскивание и масштабирование. А теперь придётся работать по другому принципу?
Хранить инфу в самих итемах - это не дело.
Конечно, база данных для итемов должна быть независима от самих итемов на сцене. Так далеко не уедешь.
Используйте массив.ы
Мне придётся использовать массивы 80*10. Многомерные. А в объектах можно хранить десятки свойств.
80 x 10 - это всего лишь двумерный массив.
А в дву- и более -мерных массивах тоже можно хранить массу свойств. Я, кстати, так и делаю.
Нужно правильно организовать структуру.
PS. В AS, по сути, массив - это тоже объект, только без визуального представления.
Так зачем превращать объект, имеющий визуальное представление, в хранилище данных?
Если проект куцый, то так можно сделать. если что-то посложнее - извольте структуру продумать более оптимально.
Добавлено через 5 минут
var allitems:Array = new Array();
for (id = 0; id <= 80; id++)
{
allitems[id] = new Array();
}
allitems[0]['prop1'] = 'some property1';
allitems[0]['prop2'] = 'some property2';
allitems[1]['prop1'] = 'some property1';
allitems[1]['prop2'] = 'some property2';
//и т.д.
Можете показать примрер добавления многомерных массивов. Предположим, у меня есть функция :
function addClip(id,name,description,mass,usable,show)
{
//....
}
В ней в массив ary должна добавиться эта запись.
var ary:Array = new Array();
for (id = 0; id < 80; id++)
{
ary[id] = new Array();
}
function addClip(id, name, description, mass, usable, show)
{
ary[id]['name'] = name;
ary[id]['description'] = description;
ary[id]['mass'] = mass;
ary[id]['usable'] = usable;
ary[id]['show'] = show;
}
Обращение очень простое:
trace(ary[20]['name'])
Добавлено через 3 минуты
Если заранее неизвестно, сколько id, не создаем заренее структуру 2-го уровня, то вариант просто создавать вложенный массив второго уровня по ходу, на лету:
var ary:Array = new Array();
function addClip(id, name, description, mass, usable, show)
{
if (ary[id] == undefined) ary[id] = new Array();//если слот под данный итем еще не создавали
ary[id]['name'] = name;
ary[id]['description'] = description;
ary[id]['mass'] = mass;
ary[id]['usable'] = usable;
ary[id]['show'] = show;
}
Таким образом, имеем БД, никак не связанную с происходящим на сцене, пока явно не изменим в ней данные, вследствие каких-то событий.
А если ID каждый раз разные, посылаются из игры? Как можно присваивать порядковые номера каждому новому айтему?
А если ID каждый раз разные, посылаются из игры? Как можно присваивать порядковые номера каждому новому айтему?
Не очень понял вопрос. Возможно для этого - второй вариант, когда id заранее неизвестен:
var ary:Array = new Array();
function addClip(id, name, description, mass, usable, show)
{
if (ary[id] == undefined) ary[id] = new Array();//если слот под данный итем еще не создавали
ary[id]['name'] = name;
ary[id]['description'] = description;
ary[id]['mass'] = mass;
ary[id]['usable'] = usable;
ary[id]['show'] = show;
}
Или речь о том, что могут быть разные экземпляры одного и того же итема?
Нет, ID это идентификатор сущности оружия, первый может быть 105, а второй - 5883. Т.е. сделать запись не по ID, а по порядковому номеру, запоминая номер последнего добавленного элемента, и наращивая его при добавлении.
Вариант 1.
Тогда нужно иметь два основных массива - один - в котором описаны дефолтные и неизменяемые свойства - типа description, mass.
Второй - массив "активных" итемов, разных экземпляров разных итемов, у которых могут меняться нужные свойства, которые могут быть в игре разными. Как я понял по названию, это типа show?
Также у итема на сцене будет еще одно свойство, которое определяет, что это, собственно, за итем, то есть соответствие id из первого массива, сущность.
А при добавлении итема на сцену нужно производить определенные действия.
var items:Array = new Array(); //БД видов итемов
for (id = 0; id < 80; id++)
{
items[id] = new Array();
}
function addDefault(id, name, description, mass)
{
items[id]['name'] = name;
items[id]['description'] = description;
items[id]['mass'] = mass;
}
addDefault(105, 'Палка', 'Палка для тыкания', 10);
addDefault(106, 'Ножик', 'Ножик для резания', 30);
//.... и .т.д.
var itemsInPlay:Array = new Array(); //БД экземпляров итемов в игре
var id_inPlay:Number = 0;
function addClip(id_itemType, show, usable):Number //возвращает, если надо id итема в игре (id_inPlay)
{
id_inPlay++;
if (itemsInPlay[id_inPlay] == undefined) itemsInPlay[id_inPlay] = new Array();//если слот под данный итем еще не создавал
itemsInPlay[id_inPlay]['id_itemType'] = id_itemType;
itemsInPlay[id_inPlay]['usable'] = usable;
itemsInPlay[id_inPlay]['show'] = show;
return id_inPlay; //если надо
}
В какой-то момент времени добавляем в игру итем с id = 2 - Ножик, его id в игре будет = 1.
Его show и usable = false
addClip(105, false, false);
Вернет id = 1, то есть идентификатор итема в игре
В другой момент можно будет узнать другие свойства данного итема (т.е. типовые):
Сперва узнаем id (сущность в вашей терминологии)
var id:Number = itemsInPlay[1]['id_itemType'];
затем по id уже неизменные свойства
trace(items[id]['name']);
trace(items[id]['mass']);
trace(items[id]['description']);
На самом деле, это первое, что в голову пришло, могут быть другие реализации.
Вариант 2.
Можно иметь одну общую базу типовых итемов, и просто в неком свойстве типового итема указывать в виде некого свойства набор (вложенный массив) соответственных итемов на сцене, это еще одна или даже две вложенности, если с учетом индивидуальных свойств в игре.
Я имел в виду просто запись по порядку. То есть у каждого айтема есть идентификатор в игре, и идентификатор порядкового номера элемента в инвентаре на Flash. Это ведь не самостоятельная игра на Flash, а просто файл интерфейса.
Например, есть предметы:
номер id name
1 34 MyWeapon1
2 766 Gun22
3 45675 Cannon1
4 22 Grenade45
итд.
При добавлении предмета в инвентарь функцией addClip, каждый объект получает свой порядковый номер, к которому можно обращаться. Например, есть массив ary, обращаемся к объекту номер 3, для свойства name:
trace(ary[3]['name'])
//Cannon1
Я именно это и имел ввиду в последнем посте.
Фразу "А при добавлении итема на сцену" можно считать за "А при добавлении итема в инвентарь".
И весь принцип тот же самый.
id_inPlay++; - это например отражает "каждый объект получает свой порядковый номер, "
и т.д.
А как удалять целую строку в массиве, уплотнять, и если нужно, полностью стирать все строки?
var itemsInventory:Array = new Array(); //итемы в инвентаре
var id_inventory:Number;
function addClip(id_itemType, show, usable):Number //возвращает id итема в инвентаре
//для задания текущего
id_inventory == undefined ? id_inventory = 0 : id_inventory++;
//если слот под данный итем еще не создан
if (itemsInventory[id_inventory] == undefined) itemsInventory[id_inventory] = new Array();
itemsInventory[id_inventory]['id_itemType'] = id_itemType;
itemsInventory[id_inventory]['usable'] = usable;
itemsInventory[id_inventory]['show'] = show;
trace('Знесли в массив, его id ' + id_inventory);
return id_inventory;
}
//заполняем итемами
addClip(100, false, false);
addClip(101, false, false);
addClip(102, false, false);
addClip(103, false, false);
trace(itemsInventory + ' Длина массива: ' + itemsInventory.length);
//удаляем итем с id = 2
itemsInventory.splice(2, 1); //удаляем начиная с 2 индекса 1 элемент
trace(itemsInventory + ' Длина массива: ' + itemsInventory.length);
Работает на vBulletin ® версия 3.7.3. Copyright ©2000-2026, Jelsoft Enterprises Ltd. Перевод: zCarot
Copyright © 1999-2008 Flasher.ru. All rights reserved.