@kuaw26

Плавная анимация 30-100 объектов на ActionScript 3

Хочу сделать для своей Flash игры анимацию воздушными шариками которые пролетают через экран при успешном прохождении уровня.

Но не получается сделать это плавно и что бы еще и процессор не отжирало сильно.
Шарики у меня это муви клипы, которым я рандомно изменяю размер в большую и меньшую сторону, что бы создать впечатление «разных» шариков. Движение шариков делаю с использованием библиотеки TweenMax.

Но результат меня удручает своим качеством.

вот кусок кода который я использую:

public static function randomScale(shape: DisplayObject, ll: Number, ul: Number): void
{
var sc: Number = 1 + Math.random() * ((Math.random() < 0.5) ? 1 : -1);
sc = ((sc < ll) || (sc > ul)) ? 1 : sc;
if (sc != 1)
{
shape.scaleX = sc;
shape.scaleY = sc;
}
}

/**
* Произвести запуск объектов в полет от низа контейнера к верху, можно использовать для оформления прохождения уровня.
*
* @param parent - родительский контейнер внутри которого будут летать объекты.
* @param duration - длительность анимации.
* @param delayMax - максимальная задержка перед анимацией.
* @param deltaX - максимальное отклонение по координате X в лево или право, для придания естественности поведения.
* @param scale - применять изменение масштаба объектов в диапазоне от 0.7 до 1.5.
* @param callback - функция вызываемая по окончанию анимации.
*/
public static function fly(parent: DisplayObjectContainer, shapes: Vector.,
duration: Number, delayMax: Number,
deltaX: uint,
scale: Boolean = false,
callback: Function = null): void
{
// получаем габариты родительского контейнера
var w: uint = parent.width;
var h: uint = parent.height;
var cnt: uint = shapes.length;

// запускаем объекты один за одним
for each (var shape: MovieClip in shapes)
{
// случайное положение объекта
shape.x = Math.round(Math.random() * w);
shape.y = h + 5; // исходно объекты находятся внизу
shape.visible = false;
// изменение масштаба объекта в небольшм диапазоне
if (scale)
{
randomScale(shape, 0.7, 1.5);
}
parent.addChild(shape);

// запускаем анимацию полета
TweenMax.to(shape, duration, // длительность анимации
{delay: delayMax * Math.random(), // произвольная задержка 0...delayMax секунды, что бы выглядело естественно
x: shape.x + (Math.round(Math.random() * deltaX * 2) - deltaX), // точка назначения отличается ± deltaX от исходной
y: -150, // объекты улетают за границу экрана
ease: Linear.easeIn, // объекты летят с линейной скоростью
visible: false, // в конце они становятся невидимыми
onInit: showShape,
onInitParams: [shape],
onComplete: removeShape, // метод для зачистки по окончании анимации
onCompleteParams: [shape]
});
}
function showShape(child: MovieClip): void
{
child.visible = true;
}
/** Зачистка по окончании анимации */
function removeShape(child: MovieClip): void
{
// удаляем объекты из контейнера по окончанию анимации
parent.removeChild(child);
}
}
}
  • Вопрос задан
  • 5754 просмотра
Пригласить эксперта
Ответы на вопрос 4
Ну так и сделайте в цикле создание мувиков со случайным размером и случайной координатой х, потом к каждому добавьте ENTER_FRAME и соответственно функцию, которая будет случайным образом в каждом кадре менять немного координату х (что бы он как будто от ветра дрожит в легкую) и уменьшать координату у, дабы он вверх летел. Ну и сделайте частоту смены кадров 41 в секунду. Должно получится все плавно и красиво. Можно ещё сам шарик внутри санимировать для реалистичности. Что бы он немного менял форму.
Ответ написан
kashey
@kashey
Программирую большую половину жизни
Есть два совета которые помогут вам какую бы анимацию вы не делали
не применяйте то что не видно — если ты смещаете обьект на 10 пиксель за секунду в 100 FPS — каждый раз смешаете на 0.01 — смысла в этом нету, а проц кушает.

Давайте посмотрим глубже.
100 обьектов смешаются на 10 пикселей. В 100 FPS
Вы пробуете это сделать, тормоза, прощай 100 FPS. Цикл…

Теперь давайте не будем смешать их на невидимые растояния. Также каждому дадим некий стартовый «офсет»
В итоге — за каждый тик сместиться только 10 обьектов. В след тик — другие 10.
За «видимый» тик — все.

Утверждение — если разбивать анимацию на части, и не анимировать все обьекты — это поднимет FPS
Поднятие FPS сгладит возможные скачки сдвига обьектов.
И — чем быстрее работает — тем еще более быстрее работает…

Я такую технологию сильно опробовал в свое время на shadow-mapping( через текстуры ) — надо обновлять кубик. Вот полный апдейт 6ти граней тормозил. А если в тик только две грани — нормально. А поднятие FPS не дало заметить что некоторые грани сушествуют немного не в том времени
Ответ написан
@kuaw26 Автор вопроса
Пока все экперименты с плавностью свелись к следующему: если делать время «полета» шариков через весь экран более 5 секунд, например 10, то получается плавно, но сильно медленно :(, игрок такие шарики быстро проклинать начнет.
Ответ написан
Комментировать
@Dendroid
Для обычного, векторного движка флэша анимировать 100 объектов с приличным fps - практически непосильная задача. Переходите на GPU рендеринг, какой-нибудь Starling вам поможет, там тоже есть мувиклипы и TweenMax, так что эту часть кода даже переделывать не придётся.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы