![]() |
|
||||||||||
|
|||||||
|
|
« Предыдущая тема | Следующая тема » |
| Опции темы | Опции просмотра |
|
![]() |
![]() |
|
|||||
|
Регистрация: May 2011
Сообщений: 8
|
Добрый день!
Делаю онлайн игру. Игрок летает по карте и объекты, которые должны попасть в поле его зрения добавляются в ролик. Столкнулся с такой ситуацией: (UniversalShip - символ) var mc:UniversalShip = new UniversalShip() занимает 5 мс. Конструктор специально замерял - столько времени не занимает. Мне нужно создать таких экземпляров за раз штук 300. Учитывая время на добавление клипа в ролик и т.п. - около 10 мс, т.е. в сумме на 1 такой клип - 15мс. 300 клипов - 4,5 с - явно больше 60 мс (для частоты кадров 24/с). Окей, с 300 клипами я немного переборщил, это был "стресс тест" для игры. Но, учитывая игроков, НПС и другие игровые объекты может понадобиться создание около 20-30 экземпляров клипа за период одного кадра (450 мс уже не так много, но все же fps падает ужасно, нужно сократить время добавления клипа раз в 10!). Вопрос: как это оптимизировать? Кстати, столько же объектов и удаляется, а так как очистка памяти у флэша срабатывает примерно через равные промежутки времени, то в такие моменты игра подвисает примерно на пол секунды. Как это исправить? Или дело не может быть в очистке памяти? Зависит ли время создания экземпляра MovieClip от количества кадров в клипе? Клип не должен проигрываться, а только стоять на одном кадре. Дело в том, что символ UniversalShip содержит все корабли в отдельных кадрах. Игра получает с сервера тип корабля и переключает клип (gotoAndStop) на фрейм с названием - "тип корабля". Может, стоит сделать первый кадр пустым для ускорения создания и добавления клипа в ролик? |
|
|||||
|
буду краток
модератор форума
Регистрация: Sep 2003
Адрес: Ближайшее Замкадье
Сообщений: 3,110
Записей в блоге: 28
|
Попробуйте создать пул объектов. т.е. создайте , например, при загрузке уровня 300 экземпляров UniversalShip, а затем вместо создания нового - берёте из пула, соответственно вместо удаления - помечаете удалённым (отвязывайте от всяких специфических вещей) и в следующий раз реиспользуйте.
Но всё равно при переходе на новый кадр могут быть тормоза. Тут уже надо думать над кэшированием и реиспользованием битмап и другим трюкачеством.
__________________
Отряд Котовскага Последний раз редактировалось Котяра; 27.05.2011 в 21:58. |
|
|||||
|
Регистрация: May 2011
Сообщений: 8
|
Спасибо, попробую!) А что насчет кадров - если клип использует только 1 кадр из тех, что есть внутри него, остальные висят в памяти и тормозят его или нет?
|
|
|||||
|
буду краток
модератор форума
Регистрация: Sep 2003
Адрес: Ближайшее Замкадье
Сообщений: 3,110
Записей в блоге: 28
|
Цитата:
Пустой первый кадр может помочь немного. А вообще, советую следующее: Отказаться от мувиклипов и каждый специфический объект делать отдельным спрайтом. вместо gotoAndStop(frame) использовать getDefinitionByName("ShipClass"+frame); примеры в хелпе. Для каждого из таких объектов заводить свой отдельный пул объектов для реиспользования. Если объекты Битмапы, а не вектор - то можно использовать общую bitmapData на все объекты одного типа. Да и для вектора, можно предварительно отрисовать в битмапу, а затем её использовать. Всё, конечно, зависит от контекста и преждевременная оптимизация не нужна. Да и затраты на кэширование могут превысить профит, если объекты очень разнообразны.
__________________
Отряд Котовскага Последний раз редактировалось Котяра; 27.05.2011 в 23:47. |
|
|||||
|
Регистрация: May 2011
Сообщений: 8
|
getDefinitionByName - это как раз то, что я искал, когда переносил проект с AS2! Только мне тогда этого не посоветовали...
Только что проверил - пустой первый кадр почти полностью убрал затраты времени на создание экземпляров мувика (конкретно строчка с "new"). Если использовать спрайты вместо MovieClip - в параметрах символа все-равно выбирать MovieClip, но в коде писать var mc:Sprite = new (getDefinitionByName("ShipClass"+frame) as Class)() ? Вообще, имеет ли смысл использовать спрайты, если внутри базового символа корабля во Flash уже добавлено несколько символов как "мувиклипы", которые содержат анимацию, должны поворачиваться и изменять свои размеры во время игры? Добавлено через 36 минут Почитал мануалы...) Я так понял, если объект сделан средствами дизайнера, то он в любом случае будет мувиклипом. Спрайты должны быть целиком созданы из AS, а значит чтобы перенести корабли в спрайты, мне нужно сохранить координаты всех вложенных объектов мувика корабля и создавать эти объекты вручную в конструкторе спрайта. Но имеет ли это смысл, если картинка корабля (вложена в мувик корабля) маскируется (т.е. она в любом случае символ, созданный в флэшевом дизайнере)? Т.к. корабли не квадратной формы, png не спасает - нужно обрабатывать клик мышкой именно по непрозрачной области картинки, а тут нужна маска. Создать её из кода не представляю возможным - маска должжна повторять форму корабля. Или, возможно в коде накрыть маской только непрозрачные области png? |
|
|||||
|
буду краток
модератор форума
Регистрация: Sep 2003
Адрес: Ближайшее Замкадье
Сообщений: 3,110
Записей в блоге: 28
|
Я бы всё-таки вытащил корабли из одного общего мувика. расположение в кадрах плохо влияет на расширяемость. например у вас будет 500 разных типов кораблей. в этом случае они будут лежать в одном мувике и в одном swf. А если бы они были в разных спрайтах-мувиках. можно было бы их и в отдельные ыца pfibdfnm. подгружать только необходимые.. итд итп.
__________________
Отряд Котовскага |
|
|||||
|
Регистрация: Nov 2009
Адрес: СПб
Сообщений: 2,236
|
Цитата:
/****************************************************************/ /* Transparent Image & Mouse */ /****************************************************************/ public static function mouseHits(target:DisplayObject):Boolean{ if (target == null || target.stage == null){ return false; } if (target.hitTestPoint(target.stage.mouseX, target.stage.mouseY)){ var aMatrix:Matrix = new Matrix(); aMatrix.translate(-target.mouseX, -target.mouseY); var bd:BitmapData= new BitmapData(1, 1, true, 0x00000000); bd.draw(target, aMatrix); var alpha:uint = ((bd.getPixel32(0, 0) >> 24) & 0xFF); bd.dispose(); return alpha > 0x0F; } return false; } Относительно оптимизации - все правильно, объекты нужно создать заранее (без фанатизма - например, в объеме левела). Потом просто addChild/removeChild. И по поводу самих игровых объектов - я лично предпочитаю, чтобы они были контейнерами с мувиклипами-холдерами, упорядоченными по глубине, в которые можно поставить требуемые мувики/изображения в соответствии с конфигурацией игрового объекта. |
![]() |
![]() |
Часовой пояс GMT +4, время: 00:01. |
|
|
« Предыдущая тема | Следующая тема » |
|
|