Форум Flasher.ru
Ближайшие курсы в Школе RealTime
Список интенсивных курсов: [см.]  
  
Специальные предложения: [см.]  
  
 
Блоги Правила Справка Пользователи Календарь Поиск рулит! Сообщения за день Все разделы прочитаны
 

Вернуться   Форум Flasher.ru > Flash > ActionScript 3.0

Версия для печати  Отправить по электронной почте    « Предыдущая тема | Следующая тема »  
Опции темы Опции просмотра
 
Создать новую тему Ответ
Старый 13.09.2013, 17:32
AlexCooper вне форума Посмотреть профиль Отправить личное сообщение для AlexCooper Найти все сообщения от AlexCooper
  № 1  
Ответить с цитированием
AlexCooper
 
Аватар для AlexCooper

Регистрация: Sep 2008
Адрес: Черкассы
Сообщений: 1,167
Записей в блоге: 1
Отправить сообщение для AlexCooper с помощью ICQ Отправить сообщение для AlexCooper с помощью Skype™
Цитата:
Сообщение от Tails Посмотреть сообщение
AlexCooper,
Вы 10 раз в секунду создаёте новый экземпляр Date и вызываете его геттер.
Для получения прошедшего времени просто дёргайте функцию getTimer() из пакета: flash.utils
согласен что getTimer() будет работать быстрее.
p.s. Но это уже другая история)
__________________
return this...

Старый 13.09.2013, 18:00
Nooob вне форума Посмотреть профиль Отправить личное сообщение для Nooob Найти все сообщения от Nooob
  № 2  
Ответить с цитированием
Nooob
 
Аватар для Nooob

Регистрация: Mar 2007
Сообщений: 319
Потому что Elastic Racetrack
любое выполнение кода тоже время
1. выполнить код 200 раз с интервалом 10 ms не то же самое что подождать 2000 ms, в любом случае будет тратиться время на повторный запуск таймера - это и будет погрешность.
2. цикл кадра в виртуальной машине тоже не постоянный http://www.craftymind.com/2008/04/18...sh-9-and-avm2/ он состоит из последовательных этапов (выполнение кода, апдейт таймеров, вход в кадр, рендеринг, выход из кадра, включение сборки мусора если нужно, обработка лоадеров и тд и тп), поэтому момент повторного запуска таймера зависит не от константного времени работы, а от удачного попадания в этап апдейта таймеров и времени работы предыдущих этапов (на разных машинах время будет разное). этот цикл запускается не раз в 1ms а раз в 1 кадр. тоесть если у тебя будет 60 fps то время обработки повторного таймера будет меняться +/- 16 ms.
3. Выполнение цикла кадра AVM можно приостановить извне (попытаться закрыть окно, свернуть вкладку/окно, вызвать контекстное меню и тд) если приостановить выполнение то соответсвенно у тебя так же сдвинется отсечка таймера
Поэтому не нужно завязываться на правильность работы таймера, лучше слушать событие входа в кадр и определять поведение основываясь на времени с момента запуска AVM getTimer()

Старый 13.09.2013, 19:32
AlexCooper вне форума Посмотреть профиль Отправить личное сообщение для AlexCooper Найти все сообщения от AlexCooper
  № 3  
Ответить с цитированием
AlexCooper
 
Аватар для AlexCooper

Регистрация: Sep 2008
Адрес: Черкассы
Сообщений: 1,167
Записей в блоге: 1
Отправить сообщение для AlexCooper с помощью ICQ Отправить сообщение для AlexCooper с помощью Skype™
Akopalipsis getTimer возвращает время в миллисекундах от старта запуска виртуальной машины AVM1/2 , грубо говоря время в мс от начала работы программы. Если к примеру дату еще можно изменить то getTimer это только геттер и изменить обнулить его можно только перезапустив приложение. Соответсвено привязав движение ( или что вам нужно ) к этому счётчику асинхронизировать что-либо будет очень сложно.
__________________
return this...

Старый 13.09.2013, 21:24
Tails вне форума Посмотреть профиль Отправить личное сообщение для Tails Найти все сообщения от Tails
  № 4  
Ответить с цитированием
Tails
 
Аватар для Tails

блогер
Регистрация: Dec 2008
Адрес: г. Чебоксары
Сообщений: 2,259
Записей в блоге: 6
Akopalipsis,
Всё очень просто, смотри.
Для начала создаёшь обычный таймер с интервалом 60fps (или какую тебе нужно частоту обновления) и обычную переменную на уровне класса с типом Number, для расчётов:
Код AS3:
private var lastTime:Number = 0;
private var timer:Timer = new Timer(1000 / 60);
Соответственно, подписываешь функцию слушатель, которую таймер будет дёргать 60 раз в секунду.
Далее, на каждой итерций, в функций листенере расчитываеш реально прошедшее время таким вот не замысловатым образом:
Код AS3:
private function onTimerTick(e:TimerEvent):void{
    var currentTime:Number = getTimer();                          // Текущее время
    var elapsedTime:Number = (currentTime - lastTime) / 1000;     // Реально прошедшее время с последней иттераций
    lastTime = currentTime;                                       // Запоминаем текущее время для следующего вызова.
}
Так ты получаешь в переменной elapsedTime - реально прошедшее время. Для удобства, его лучше перевести в секунды (разделить на 1000).

Далее всё становится ещё проще.
Тебе нужно рисовать некоторую линию от 0:0. Всё что для этого нужно - это запомнить текущее положение линий (до куда её нарисовали от 0:0) и указать расстояние, на которое она рисуется за 1 секунду реального времени. Выглядеть это может примерно так:
Код AS3:
/// Скорость рисования линий за 1 секунду.
private static const DRAW_SPEED:Number = 15;
 
private var linePoint:Point = new Point(0, 0);
 
// На каждой иттераций таймера, ты имеешь прошедшее время с момента последнего вызова, 
// которое можеш передавать функций рисовалке линий:
 
private function lineAnimation(time:Number):void{
 
    // Эта функция знает лишь то, что с последнего вызова прошло time секунд.
    // Так как мы имеем скорость рисования линий за 1 секунду, мы можем найти расстояние
    // на которое она нарисуется за текущее прошедшее время.
 
    // Новая позиция для линий:
    linePoint.x += time * DRAW_SPEED;
 
    // Код, рисующий линию к новой координате
    // ...
 
}
Вот и всё. Ничего сложного если совсем немного вникнуть. Все ваши анимаций, скорости перемещения персонажа и другие параметры изменения, должны указываться как - изменение за 1 секунду времени.

По такому принципу, например, работает анимация в Starling. На основе прошедшего времени работают физические движки. По этому-же принципу можно делать и "не лагающие игры". То-есть, лагать они конечно-же могут, будет уменьшаться частота обновления мира (fps), но эффекты при этом будут проигрываться с нормальной скоростью, а не замедленной. Уменьшится fps но действие в игре будет идти с той-же скоростью.
__________________
Дети не должны знать о своих родителях


Последний раз редактировалось Tails; 13.09.2013 в 21:51.
Старый 13.09.2013, 23:03
Akopalipsis вне форума Посмотреть профиль Найти все сообщения от Akopalipsis
  № 5  
Ответить с цитированием
Akopalipsis
Banned

Регистрация: Mar 2013
Сообщений: 1,864
Tails Спасибо большое за обьяснение! Несколько дней у меня наверное ещё займет геометрия, но как только закончу, первым делом в эту тему и пробовать. А то постоянно читаю о разнице во времени ентерфрайма и таймера. Лучше сразу научиться делать с getTimer(), чем в будущем пожалеть, что не отвел одного дня для разбора темы.

Старый 14.09.2013, 00:05
dimarik вне форума Посмотреть профиль Отправить личное сообщение для dimarik Найти все сообщения от dimarik
  № 6  
Ответить с цитированием
dimarik
.
 
Аватар для dimarik

модератор форума
Регистрация: Sep 2003
Адрес: Москва
Сообщений: 4,630
Записей в блоге: 20
Комменты не читал, смотрите сюда.
__________________
Воспитан в TimeZero. Работаю в Mail.ru.

Старый 28.10.2013, 00:53
Akopalipsis вне форума Посмотреть профиль Найти все сообщения от Akopalipsis
  № 7  
Ответить с цитированием
Akopalipsis
Banned

Регистрация: Mar 2013
Сообщений: 1,864
На несколько минут руки застыли над клавиатурой и...( не знаю как задать этот вопрос )
Может кто нибудь рассказать принцип по которому только один класс в приложении является
EnterFrame-ом.
Создаю я класс синглетон для всего приложения. А дальше что? Если делать события, то они сразу сведут на нет все getTimer-ы. Если сделать метод и передавать туда ссылку на метод, который по таймеру будет получать в параметры прошедшее время, то ведь это тоже ведь сведёт на нет все труды?
Обьясните на словах, как это делается?


Последний раз редактировалось Akopalipsis; 28.10.2013 в 01:49.
Старый 28.10.2013, 01:40
Wolsh вне форума Посмотреть профиль Отправить личное сообщение для Wolsh Найти все сообщения от Wolsh
  № 8  
Ответить с цитированием
Wolsh
Нуб нубам
 
Аватар для Wolsh

модератор форума
Регистрация: Jan 2006
Адрес: Бердск, НСО
Сообщений: 6,445
Ну, например инвалидация. Модель посылает событие об изменении, но Вид не пытается сделать перерисовку сразу же. В обработчике события от Модели Вид только устанавливает флаг isChanged = true;
Второй механизм проверяет флаги по событию таймера, или рендера, или ентерфрейму, и увидев флаг true делает соответствующее обновление, после чего снова устанавливает флаг в false.
__________________
Reality.getBounds(this);

Старый 28.10.2013, 01:49
Dukobpa3 вне форума Посмотреть профиль Отправить личное сообщение для Dukobpa3 Найти все сообщения от Dukobpa3
  № 9  
Ответить с цитированием
Dukobpa3
 
Аватар для Dukobpa3

блогер
Регистрация: Oct 2010
Адрес: Киев
Сообщений: 1,678
Записей в блоге: 12
Отправить сообщение для Dukobpa3 с помощью Skype™
Таймер физически не может выдавать значения чаще чем раз в кадр.
Соответственно погрешность зависит от фпс в первую очередь.
К тому же если вы взяли к примеру 100 мс - то это 10 повторений в секунду. А фпс допустим 24. 1000/24 = 41.6666.
т.е. 100 мс это 2.4 кадра на один тик.
Хотите точный таймер - используйте периоды кратные длине кадра. Но даже в таком случае точность [почти] гарантируется только без нагрузок. При любых нагрузках - длина кадра начинает скакать. Там дольше считали, там быстрее получилось и в таком духе. Плюс от системы тоже зависит.

Короче таймер во флеше нифига не таймер с такой реализацией.
Единственный гарантированный метод выше упоминали - подписка на ентерфрейм + замер кол-ва милисекунд от предыдущего кадра.
__________________
Кто к нам с чем для чего - тот у нас того от того.

Старый 28.10.2013, 02:59
Akopalipsis вне форума Посмотреть профиль Найти все сообщения от Akopalipsis
  № 10  
Ответить с цитированием
Akopalipsis
Banned

Регистрация: Mar 2013
Сообщений: 1,864
Спасибо Вам! Пока хотел написать уточнения к вопросу, из сказанных Вами слов получилось вообразить процесс в голове и я начал делать, чтобы показать про что именно я говорю. Но как всегда ( у меня )
возникли мелкие заминки.. И я сегодня уже не потяну, перенесу на завтра)

Создать новую тему Ответ Часовой пояс GMT +4, время: 23:28.
Быстрый переход
  « Предыдущая тема | Следующая тема »  
Опции темы
Опции просмотра
Комбинированный вид Комбинированный вид

Ваши права в разделе
Вы не можете создавать новые темы
Вы не можете отвечать в темах
Вы не можете прикреплять вложения
Вы не можете редактировать свои сообщения

BB коды Вкл.
Смайлы Вкл.
[IMG] код Вкл.
HTML код Выкл.


 


Часовой пояс GMT +4, время: 23:28.


Copyright © 1999-2008 Flasher.ru. All rights reserved.
Работает на vBulletin®. Copyright ©2000 - 2026, Jelsoft Enterprises Ltd. Перевод: zCarot
Администрация сайта не несёт ответственности за любую предоставленную посетителями информацию. Подробнее см. Правила.