Форум Flasher.ru

Форум Flasher.ru (http://www.flasher.ru/forum/index.php)
-   ActionScript 3.0 (http://www.flasher.ru/forum/forumdisplay.php?f=83)
-   -   Запись действий пользователя. Погрешность Timer. (http://www.flasher.ru/forum/showthread.php?t=155990)

Cheburashka 13.05.2011 20:37

Запись действий пользователя. Погрешность Timer.
 
Здравствуйте. У меня возникла проблема с таймером (или не с ним).
Мне нужно организовать запись и воспроизведение действий пользователя в игре tower defence.
Как реализовал. Есть один таймер, который генерирует событие. В обработчике этого события происходит обновление всех объектов (башни, крипы, летящие пули).
Сохраняя определенное действие пользователя (построил/продал башню, пустил следующую волну и т.д.) я указываю в какой tick таймера это произошло, типа:
Код AS3:

{tick : 2342, action : 'sold_tower'};

Проигрывая игру, все действия воспроизводятся по этому таймеру, по которому и записывались.
Игра так же интерактивная, но записанные действия воспроизводятся без участия юзера.
Тут и начинается проблема: не всегда результат воспроизведения совпадает с "оригиналом". Если просто включить проигрывание и ничего не делать - результат нужный. Но если, например, сделать окно флеш плеера не активным, или запустить 2 окна параллельно - создать другие условия - результат воспроизведения расходится с оригинальным. Не проверял, но почти уверен, что запуск на компе с другой конфигурацией даст тот же эффект.
Для удачного результата может хватить того, что в какой-то момент времени в воспроизводимой игре 1 башня не выстрелила в крипа, в которого выстрелила в оригинале.
Рандома в игре нет.
Читал, что Timer не точен, но тут вопрос: если все изменения происходят четко по тику таймера, то одинаковые ситуации должны быть и при 33 тика в секунду и при 54, например.
Подскажите, плиз, как можно решить эту проблему. Может нужно использовать не таймер, а что-то другое?
Спасибо.

Rzer 13.05.2011 20:45

Event.ENTER_FRAME и считать кадры. Как записывать, так и воспроизводить только через это событие. Рассинхронизация происходит из-за того, что у тебя скорее всего перемещения объектов идёт через ENTER_FRAME, а запись через таймер. FrameRate падает при не активности окна до 4 кадров в секунду, в то время как таймер работает одинаково.


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

Cheburashka 13.05.2011 21:26

Спасибо, за ответ.
Цитата:

у тебя скорее всего перемещения объектов идёт через ENTER_FRAME, а запись через таймер
Нет, все идет по одному таймеру, ни одного ENTER_FRAME в проекте нет.
Изменение скорости тоже реализовано, к нему нареканий нет.
Что мне даст переход с таймера на ENTER_FRAME? Полезут минимум эти же баги, если не добавятся новые.

Добавлено через 58 минут
Возможно я погорячился. Осознал, что какой-то рандом произойти может. При выборе цели для башни используется for each, поэтому при одинаковых условиях, башня может выбрать в качестве цели любого крипа из нескольких одинаковых - первого попавшегося. Но сорсы на работе, поэтому сейчас проверить не смогу. Попробую for i.

Rzer 14.05.2011 02:16

А как прости, идёт перемещение крипов? Что-то я сомневаюсь, что таймером. И вообще таймер на гарантирует, что на следующий тик пройдёт столько же времени, что и при записи ролика.

Cheburashka 14.05.2011 02:37

Цитата:

А как прости, идёт перемещение крипов? Что-то я сомневаюсь, что таймером.
Так и происходит:
Цитата:

Есть один таймер, который генерирует событие. В обработчике этого события происходит обновление всех объектов (башни, крипы, летящие пули).
+ передвижение тут же.
Цитата:

И вообще таймер на гарантирует, что на следующий тик пройдёт столько же времени, что и при записи ролика.
Да, но опять же, по идее главное в каком тике произошло действие, а какой между тиками интервал должно быть без разницы.

Dukobpa3 14.05.2011 11:20

А поиск пути как реализован? Там разве нет рандома? Например сейчас крип обходит препятствие отсюда а потом оттуда.

В оригинале он был от башни на 50пкс, а в риплее на 54, и башня стреляет в другого.

Cheburashka 14.05.2011 18:26

A*. Да, спасибо за совет, действительно, там тоже из-за for each может быть рандом.

Добавлено через 42 часа 36 минут
Прошелся по всем циклам for each, заменил на while те, из-за которых могут происходить случайности. Не помогло.
Заменил Timer на ENTER_FRAME - поведение то же.
В общем при этих изменениях в коде, флеш ведет себя так же как и до них.
Провел тест: запустил 3 окна, в которых проигрываются одинаковые записи. В том, которое активно, результат правильный - игрок не потерял ни одной жизни (как и было при записи). А те 2 окна, которые были не на первом плане, показывают неверный результат - в обоих потеряно по 3 жизни (тут результаты почти идентичны).
Средний fps активного окна 29.8, а не ативных - 29.15.

Подскажите, плиз, куда еще копать.

Добавлено через 45 часов 18 минут
Всем спасибо, пока смог добиться точности в 0.1%. Откуда идет погрешность пока не вижу, но все стало лучше после использования updateAfterEvent() для TimerEvent.


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

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