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

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

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

Регистрация: Feb 2012
Сообщений: 3
По умолчанию Оптимизация обработки событий клавиатуры

Делаю многопользовательскую игрушку, клиент пишу на AS3. Передвижение персонажа осуществляется с клавиатуры. Все вроде бы банально, но дело в том, что при нажатии и удержании клавиши после небольшой задержки начинают имитироваться быстрые повторные нажатия. И, что интересно, Firefox имитирует только нажатие (событие KEY_DOWN), а вот Opera "гоняет" клавишу туда-сюда (KEY_DOWN - KEY_UP). Это в Ubuntu, в других ОС не проверял еще.

Вся проблема в том, что мне необходимо отправлять на сервер сообщения о том, что пользователь нажал какую-либо клавишу, и что он отпустил ее (по нажатию/отпусканию клавиши меняется состояние объекта). Так вот в случае с Оперой клиент начинает безумно "засорять эфир" потоком сообщений о событиях, которые на самом деле не происходят (имитируемые нажатия клавиши). Мне это очень не нравится, т.к. повышает нагрузку на сервер и сеть.

Есть какие-то готовые решения этой проблемы? У меня есть одна идея, но для ее реализации надо быть уверенным, что у всех клиентов скорость повторных нажатия примерно одинакова, а уверенности такой нет. А может, под виндой такой проблемы нет?

Старый 10.02.2012, 19:26
t4arty вне форума Посмотреть профиль Отправить личное сообщение для t4arty Найти все сообщения от t4arty
  № 2  
Ответить с цитированием
t4arty

Регистрация: May 2010
Адрес: пространство в положении
Сообщений: 219
поставте булевый флаг (true/false) и от него "прыгайте".

Старый 11.02.2012, 12:31
Rex вне форума Посмотреть профиль Отправить личное сообщение для Rex Найти все сообщения от Rex
  № 3  
Ответить с цитированием
Rex

Регистрация: Feb 2012
Сообщений: 3
Цитата:
Сообщение от t4arty Посмотреть сообщение
поставте булевый флаг (true/false) и от него "прыгайте".
Это работает в Firefox, но Opera будет менять флаг туда-сюда, т.к. она имитирует и отпускание клавиши.

Хочу попробовать такой способ: в событии KEY_DOWN устанавливать некий счетчик в значение, скажем, 10. По событию KEY_UP для этого счетчика будет устанавливаться коэффициент 0.9 (до события он равен единице). А в EnterFrame перемножать коэффициент на счетчик, и если коэффициент уменьшился, скажем, ниже 3, только тогда отсылать в сокет сообщение о том, что клавиша отпущена. Если имитируются быстрые нажатия и отпускания, то счетчик не будет опускаться ниже определенной величины (зависит от скорости нажатий). Мне это кажется костылем, но если другого способа не найду, буду делать так.

Старый 12.02.2012, 15:26
expl вне форума Посмотреть профиль Отправить личное сообщение для expl Найти все сообщения от expl
  № 4  
Ответить с цитированием
expl

блогер
Регистрация: Feb 2006
Сообщений: 1,474
Записей в блоге: 3
У Вас наверняка есть игровой цикл (по таймеру или ENTER_FRAME).
Создаете поле
Код AS3:
privte var isNeededKeyDown:Boolean = false;
В этом цикле проверяете, нажата ли клавиша:
Код AS3:
var newIsNeededKeyDown:Boolean = inp.code[код нужной клавиши];
if (newIsNeededKeyDown != isNeededKeyDown)
{
    isNeededKeyDown = newIsNeededKeyDown;
    if (isNeededKeyDown)
    {
        dispatchEvent(new Event("neededKeyDown"));
    }
    else
    {
        dispatchEvent(new Event("neededKeyUp"));
    }
}
Проверить, нажата ли клавиша в определённый момент можно с помощью класса Input отсюда http://www.flasher.ru/forum/blog.php?b=524

Старый 12.02.2012, 16:08
Wolsh вне форума Посмотреть профиль Отправить личное сообщение для Wolsh Найти все сообщения от Wolsh
  № 5  
Ответить с цитированием
Wolsh
Нуб нубам
 
Аватар для Wolsh

модератор форума
Регистрация: Jan 2006
Адрес: Бердск, НСО
Сообщений: 6,445
expl Уже второй раз вижу отсылку к этому классу как панацее от всего, хотя автор ясно выразился, о чем он:
Цитата:
Я написал более универсальный класс Input.as, который решает все эти проблемы - отслеживает открытие контекстного меню, потерю фокуса окна и сбрасывает состояние мыши и клавиатуры.
Rex, не проще ли повесить отменяемый кейдауном таймер на кейап? Насколько я понимаю, события в опере приходят фактически одновременно. Когда приходит событие отпускания, делаем небольшую задержку, и если во время нее пришло событие нажатия, то не отсылаем "наверх" ни кейап, ни последний кейдаун. Если время прошло, а клавишу не "нажали", то отсылаем кейап – он реальный.
__________________
Reality.getBounds(this);

Старый 12.02.2012, 16:27
expl вне форума Посмотреть профиль Отправить личное сообщение для expl Найти все сообщения от expl
  № 6  
Ответить с цитированием
expl

блогер
Регистрация: Feb 2006
Сообщений: 1,474
Записей в блоге: 3
Цитата:
expl Уже второй раз вижу отсылку к этому классу как панацее от всего, хотя автор ясно выразился, о чем он:
А я виноват, если 2 задачи подходят?


Последний раз редактировалось expl; 12.02.2012 в 18:18.
Старый 12.02.2012, 19:00
Wolsh вне форума Посмотреть профиль Отправить личное сообщение для Wolsh Найти все сообщения от Wolsh
  № 7  
Ответить с цитированием
Wolsh
Нуб нубам
 
Аватар для Wolsh

модератор форума
Регистрация: Jan 2006
Адрес: Бердск, НСО
Сообщений: 6,445
Вы класс-то смотрели?
Код AS3:
//Обработка событий клавиатуры
root.stage.addEventListener(KeyboardEvent.KEY_DOWN,onKeyDown);
root.stage.addEventListener(KeyboardEvent.KEY_UP, onKeyUp);
 
private function onKeyDown(event:KeyboardEvent):void {
	code[event.keyCode] = true;
	//Если хотите узнать код клавиши - просто раскомментируйте код ниже
	//trace(event.keyCode);
}
private function onKeyUp(event:KeyboardEvent):void {
	code[event.keyCode]=false;
}
И каким образом этот подход поможет в ситуации, когда Опера генерит бесконечный цикл нажатий и отпусканий клавиши?
И у топикстартера вроде была одна задача.
__________________
Reality.getBounds(this);

Старый 12.02.2012, 19:33
expl вне форума Посмотреть профиль Отправить личное сообщение для expl Найти все сообщения от expl
  № 8  
Ответить с цитированием
expl

блогер
Регистрация: Feb 2006
Сообщений: 1,474
Записей в блоге: 3
Цитата:
Сообщение от Wolsh Посмотреть сообщение
И каким образом этот подход поможет в ситуации, когда Опера генерит бесконечный цикл нажатий и отпусканий клавиши?
И у топикстартера вроде была одна задача.
По крайней мере в случае не оперы - поможет.
Вобщем проверка нажатости/отжатости по таймеру/ентерфрейму сработает и для Оперы, только если события отжатия/нажатия "фактически одновременно".
Не знаю вот хуже это или лучше, чем ваш подход с таймерами для Оперы (последняя версия на винде никаких повторов не делает). Но, по крайней мере надежнее для остальных бравзеров.

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

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

Старый 13.02.2012, 23:09
Rex вне форума Посмотреть профиль Отправить личное сообщение для Rex Найти все сообщения от Rex
  № 10  
Ответить с цитированием
Rex

Регистрация: Feb 2012
Сообщений: 3
Всем спасибо за рекомендации, буду пробовать. Потом отпишу, что получилось.

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

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

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


 


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


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