如何在 cocos2d-x 中捕获按住键盘事件?
How to catch Press and Hold key board event in cocos2d-x?
我这里有一个函数,可以在按下每个键时移动 Sprite。现在我也想在按住 键时移动它而不是重复按键,但我不知道该怎么做。请指导我,非常感谢您的帮助。
keyBoardListener->onKeyPressed = [](EventKeyboard::KeyCode keyCode, Event* event)
{
Vec2 location = event->getCurrentTarget()->getPosition();
switch (keyCode)
{
case EventKeyboard::KeyCode::KEY_LEFT_ARROW:
case EventKeyboard::KeyCode::KEY_A:
event->getCurrentTarget()->setPosition(location.x - 10.0f, location.y);
break;
case EventKeyboard::KeyCode::KEY_RIGHT_ARROW:
case EventKeyboard::KeyCode::KEY_D:
event->getCurrentTarget()->setPosition(location.x + 10.0f, location.y);
break;
case EventKeyboard::KeyCode::KEY_UP_ARROW:
case EventKeyboard::KeyCode::KEY_W:
event->getCurrentTarget()->setPosition(location.x, location.y + 10.0f);
break;
case EventKeyboard::KeyCode::KEY_DOWN_ARROW:
case EventKeyboard::KeyCode::KEY_S:
event->getCurrentTarget()->setPosition(location.x, location.y - 10.0f);
break;
}
};
没有事件会在按下某个键时连续触发,因此解决问题的一种方法是使用一个全局(或 class 或其他)变量来跟踪 x 轴上的运动,一个用于y 轴。
要仅使用两个变量而不是为每个键单独使用一个变量,您可以使用 2 个整数,比方说 xMovement 和 yMovement,并根据按下的键将它们的值设置为 -1、0 或 1。如果 xMovement 为 -1,则将精灵向左移动,如果为 1,则将其向右移动,如果为 0,则根本不移动它。 y 轴也一样。为此,您应该像这样更改代码:
keyBoardListener->onKeyPressed = [](EventKeyboard::KeyCode keyCode, Event* event)
{
switch (keyCode)
{
case EventKeyboard::KeyCode::KEY_LEFT_ARROW:
case EventKeyboard::KeyCode::KEY_A:
xMovement--;
break;
case EventKeyboard::KeyCode::KEY_RIGHT_ARROW:
case EventKeyboard::KeyCode::KEY_D:
xMovement++;
break;
case EventKeyboard::KeyCode::KEY_UP_ARROW:
case EventKeyboard::KeyCode::KEY_W:
yMovement++;
break;
case EventKeyboard::KeyCode::KEY_DOWN_ARROW:
case EventKeyboard::KeyCode::KEY_S:
yMovement--;
break;
}
};
现在你还应该添加一个按键释放事件,其中 incrementation/decrementation 应该与按键事件相反:
keyBoardListener->onKeyReleased = [](EventKeyboard::KeyCode keyCode, Event* event)
{
switch (keyCode)
{
case EventKeyboard::KeyCode::KEY_LEFT_ARROW:
case EventKeyboard::KeyCode::KEY_A:
xMovement++;
break;
case EventKeyboard::KeyCode::KEY_RIGHT_ARROW:
case EventKeyboard::KeyCode::KEY_D:
xMovement--;
break;
case EventKeyboard::KeyCode::KEY_UP_ARROW:
case EventKeyboard::KeyCode::KEY_W:
yMovement--;
break;
case EventKeyboard::KeyCode::KEY_DOWN_ARROW:
case EventKeyboard::KeyCode::KEY_S:
yMovement++;
break;
}
};
现在,要真正移动您的精灵,只需在每帧调用的更新函数中执行类似这样的操作:
float newPosX = sprite->getPositionX() + (xMovement * 10.f);
float newPosY = sprite->getPositionY() + (yMovement * 10.f);
sprite->setPosition(newPosX, newPosY);
您还需要一些机制来确保 xMovement 和 yMovement 保持在边界内(在我的示例中,如果您同时按下向左箭头和 'a' 键,精灵将以两倍的速度移动 :P ) , 但这只是一个粗略的例子来演示如何使用键盘事件和更新功能来实现连续移动。
我这里有一个函数,可以在按下每个键时移动 Sprite。现在我也想在按住 键时移动它而不是重复按键,但我不知道该怎么做。请指导我,非常感谢您的帮助。
keyBoardListener->onKeyPressed = [](EventKeyboard::KeyCode keyCode, Event* event)
{
Vec2 location = event->getCurrentTarget()->getPosition();
switch (keyCode)
{
case EventKeyboard::KeyCode::KEY_LEFT_ARROW:
case EventKeyboard::KeyCode::KEY_A:
event->getCurrentTarget()->setPosition(location.x - 10.0f, location.y);
break;
case EventKeyboard::KeyCode::KEY_RIGHT_ARROW:
case EventKeyboard::KeyCode::KEY_D:
event->getCurrentTarget()->setPosition(location.x + 10.0f, location.y);
break;
case EventKeyboard::KeyCode::KEY_UP_ARROW:
case EventKeyboard::KeyCode::KEY_W:
event->getCurrentTarget()->setPosition(location.x, location.y + 10.0f);
break;
case EventKeyboard::KeyCode::KEY_DOWN_ARROW:
case EventKeyboard::KeyCode::KEY_S:
event->getCurrentTarget()->setPosition(location.x, location.y - 10.0f);
break;
}
};
没有事件会在按下某个键时连续触发,因此解决问题的一种方法是使用一个全局(或 class 或其他)变量来跟踪 x 轴上的运动,一个用于y 轴。
要仅使用两个变量而不是为每个键单独使用一个变量,您可以使用 2 个整数,比方说 xMovement 和 yMovement,并根据按下的键将它们的值设置为 -1、0 或 1。如果 xMovement 为 -1,则将精灵向左移动,如果为 1,则将其向右移动,如果为 0,则根本不移动它。 y 轴也一样。为此,您应该像这样更改代码:
keyBoardListener->onKeyPressed = [](EventKeyboard::KeyCode keyCode, Event* event)
{
switch (keyCode)
{
case EventKeyboard::KeyCode::KEY_LEFT_ARROW:
case EventKeyboard::KeyCode::KEY_A:
xMovement--;
break;
case EventKeyboard::KeyCode::KEY_RIGHT_ARROW:
case EventKeyboard::KeyCode::KEY_D:
xMovement++;
break;
case EventKeyboard::KeyCode::KEY_UP_ARROW:
case EventKeyboard::KeyCode::KEY_W:
yMovement++;
break;
case EventKeyboard::KeyCode::KEY_DOWN_ARROW:
case EventKeyboard::KeyCode::KEY_S:
yMovement--;
break;
}
};
现在你还应该添加一个按键释放事件,其中 incrementation/decrementation 应该与按键事件相反:
keyBoardListener->onKeyReleased = [](EventKeyboard::KeyCode keyCode, Event* event)
{
switch (keyCode)
{
case EventKeyboard::KeyCode::KEY_LEFT_ARROW:
case EventKeyboard::KeyCode::KEY_A:
xMovement++;
break;
case EventKeyboard::KeyCode::KEY_RIGHT_ARROW:
case EventKeyboard::KeyCode::KEY_D:
xMovement--;
break;
case EventKeyboard::KeyCode::KEY_UP_ARROW:
case EventKeyboard::KeyCode::KEY_W:
yMovement--;
break;
case EventKeyboard::KeyCode::KEY_DOWN_ARROW:
case EventKeyboard::KeyCode::KEY_S:
yMovement++;
break;
}
};
现在,要真正移动您的精灵,只需在每帧调用的更新函数中执行类似这样的操作:
float newPosX = sprite->getPositionX() + (xMovement * 10.f);
float newPosY = sprite->getPositionY() + (yMovement * 10.f);
sprite->setPosition(newPosX, newPosY);
您还需要一些机制来确保 xMovement 和 yMovement 保持在边界内(在我的示例中,如果您同时按下向左箭头和 'a' 键,精灵将以两倍的速度移动 :P ) , 但这只是一个粗略的例子来演示如何使用键盘事件和更新功能来实现连续移动。