2014-12-11 3 views
0

Я начинаю программировать на Java & Я делаю приложение, требующее, чтобы объект перемещался по сетке, заполненной квадратами. Объект должен перемещать только один квадрат за раз, и если пользователь хочет перейти на другой квадрат, он должен снова нажать клавишу. Мой метод шаг следующие:Как остановить объект от перемещения по нажатой клавише

public void move() { 
    x += dx; 
    y += dy; 
} 

Я использую интерфейс KeyListener для реализации Keypressed, keyTyped и keyReleased методы и у меня есть условия, как в фрагменте ниже внутри Keypressed

//KeyPressed 
int c = e.getKeyCode(); 

    if (c == KeyEvent.VK_UP) { 
     player.setDy(-5); 
    } 

Этот позволяет объекту свободно перемещаться. Однако он будет продолжать двигаться, пока нажимается стрелка ВВЕРХ. Есть ли какой-либо способ, чтобы объект двигался вверх, произнося -5 один раз, а затем останавливался, даже если клавиша все еще нажата? Я не уверен, нужно ли мне изменить метод перемещения или методы KeyListener для этого. Надеюсь, что я был достаточно ясен по поводу того, что я прошу, и я был бы очень признателен за любые указания.

ответ

0

Прежде всего: вы должны использовать Synchronization, если вы вызываете методы класса из таких слушателей, как keyPressed или keyReleased - это потому, что ваш метод-слушатель может быть вызван из нескольких потоков, поэтому ваш метод класса (player.setDy()) может (и будет) вызываться параллельно - вам нужно будет сделать что каждый звонок setDy происходит до следующий.

также: keyTyped намного лучше во многих случаях: https://stackoverflow.com/a/7071810/351861

Примером может выглядеть следующим образом:

public void keyTyped(KeyEvent arg0) { 
    if(arg0.getKeyCode() == KeyEvent.VK_UP) 
    { 
     synchronized(player) 
     { 
      player.setDy(-5); 
     } 
    } 
} 

это будет вызывать setDy последовательно и надежно.Теперь все, что вам нужно сделать, это убедиться, что setDy работает по назначению, следовательно, устанавливает только

-1

просто переместить эту

int c = e.getKeyCode(); 

if (c == KeyEvent.VK_UP) { 
    player.setDy(-5); 
} 

из Keypressed метода либо в keyreleased метода или в keytyped метода. Для удобства использования keyifped в вашем случае, вероятно, лучше, так что он уже перемещается, когда вы начинаете нажимать клавишу.

Разница между этими тремя методами:

Keytyped вызывается только один раз в keypressing действия (означает нажать и отпущена) в самом начале.

Вручную будет называться несколько раз при нажатии.

Keyreleased вызывается один раз, когда ключ снова освобождается.

+0

В то время как все еще правильный ответ, в нем отсутствуют основные части информации - вы можете включить примеры, которые показывают, как использовать keyReleased , например – specializt

+0

Спасибо за ответ. Я пробовал это, но объект продолжает «навсегда» двигаться, не останавливаясь, как только выйдет ключ. – AmazingBergkamp

0

простой было бы добавить логическое значение, чтобы указать, что движущееся нажата клавиша

член класса: boolean movingKeyPressed = false

в ключе нажата:

if (movingKeyPressed) { 
    return; 
} else { 
    // do stuff 
    movingKeyPressed = true; 
} 

в ключе выпущен метод:

movingKeyPressed = false; 
+0

, используя простой логический элемент класса, будет создавать бесшумные гоночные условия, когда несколько кнопок будут нажаты параллельно или в очень быстром порядке - использование «AtomicBoolean» всегда является лучшим выбором, если ваше значение можно изменить из нескольких потоков, методы прослушивания – specializt

+0

Оба логических и синхронизационных предложения помогли исправить эту проблему, спасибо вам обоим. – AmazingBergkamp

Смежные вопросы