#send-event #input #bevy #hotkey #gamedev #user-input #cheat-code

bevy-input-sequence

识别输入序列并发送事件

5个版本 (破坏性更新)

0.5.0 2024年7月5日
0.4.0 2024年4月23日
0.3.0 2024年3月8日
0.2.0 2024年2月24日
0.1.0 2023年8月19日

#456游戏开发

MIT/Apache

47KB
625行代码

bevy-input-sequence

从键盘或游戏手柄中检测输入序列

使用案例

  • 热键
  • 作弊码
  • 开发者界面

安装

cargo install bevy-input-sequence

代码示例

这些代码片段也是doctests,因此它们会以不同的方式执行

  • 默认插件
  • 使用最小插件

运行示例

按键序列运行系统

按下键序列时发送事件

use bevy::prelude::*;
use bevy_input_sequence::prelude::*;

fn main() {
    App::new()
        .add_plugins(MinimalPlugins)
        .add_plugins(InputSequencePlugin::default())
        .add_systems(Startup, setup)
        .update(); // Normally you'd run it here.
}

fn setup(mut commands: Commands) {
    commands.add(
        KeySequence::new(say_hello, 
                         keyseq! { H I })
        .time_limit(Duration::from_secs(2))
    );
}

fn say_hello() {
    info!("hello");
}

按下游戏手柄按钮序列时发送事件

键盘没有身份问题

use bevy::prelude::*;
use bevy_input_sequence::prelude::*;

// Define an event
#[derive(Event, Clone, Debug)]
struct MyEvent;

// Add event as an key sequence
fn main() {
    App::new()
        .add_plugins(MinimalPlugins)
        .add_plugins(InputSequencePlugin::default())
        .add_event::<MyEvent>()
        .add_systems(Startup, setup)
        .update(); // Normally you'd run it here.
}

fn setup(mut commands: Commands) {
    commands.add(
        KeySequence::new(action::send_event(MyEvent), 
                         keyseq! { ctrl-E L M })
    );
}

fn check_events(mut events: EventReader<MyEvent>) {
    for event in events.read() {
        info!("got event {event:?}");
    }
}

按下按钮序列可能很重要

接受游戏手柄输入

use bevy::prelude::*;
use bevy_input_sequence::prelude::*;

// Define an event
#[derive(Event, Clone, Debug)]
struct MyEvent(Gamepad);

// Add event as an key sequence
fn main() {
    App::new()
        .add_plugins(MinimalPlugins)
        .add_plugins(InputSequencePlugin::default())
        .add_event::<MyEvent>()
        .add_systems(Startup, setup)
        .update(); // Normally you'd run it here.
}

fn setup(mut commands: Commands) {
    commands.add(
        ButtonSequence::new(action::send_event_with_input(|gamepad| MyEvent(gamepad)), 
            [GamepadButtonType::North,
             GamepadButtonType::East,
             GamepadButtonType::South,
             GamepadButtonType::West])
    );
}

fn check_events(mut events: EventReader<MyEvent>) {
    for event in events.read() {
        info!("got event {event:?}");
    }
}

键序列创建模式

键序列构建器

use bevy::prelude::*;
use bevy_input_sequence::prelude::*;

#[derive(Event, Clone)]
struct MyEvent;

fn create_key_sequence(mut commands: Commands) {
    commands.add(KeySequence::new(
        action::send_event(bevy::app::AppExit::default()), 
        keyseq! { ctrl-E L M }
    ));
}

fn create_key_sequence_and_add_it_to_an_entity(mut commands: Commands) {
    let parent = commands.spawn_empty().id();
    commands.entity(parent).add(KeySequence::new(
        action::send_event(MyEvent), 
        keyseq! { ctrl-E L M }
    ));
    // OR
    commands.spawn_empty().add(KeySequence::new(
        action::send_event(MyEvent), 
        keyseq! { ctrl-E L M }
    ));
}

添加命令

高级创建

use bevy::prelude::*;
use bevy_input_sequence::prelude::*;

fn create_key_sequence_within_command(mut commands: Commands) {
    commands.add(|world: &mut World| {
        let builder = KeySequence::new(
            move || { info!("got it"); },
            keyseq! { ctrl-E L M }
        );
        let key_sequence: KeySequence = builder.build(world);
        // And then put it somewhere? It ought to go as a component.
    });
}

可运行示例

键码

keycode 示例识别按键序列 W D S AW A S D 并触发一个独立的事件。

cargo run --example keycode

keymod

keymod 示例识别 ctrl-W ctrl-D ctrl-S ctrl-A 并触发一个事件。

cargo run --example keymod

gamepad_button

gamepad_button 示例识别游戏手柄按钮 北 东 南 西 或 Xbox 控制器上的 Y B A X 并触发一个事件。

cargo run --example gamepad_button

multiple_input

multiple_input 示例识别游戏手柄按钮 北 东 南 西,Xbox 控制器上的 Y B A X,或键盘上的 W D S A 并触发一个事件。

cargo run --example multiple_input

注意:键盘上只会识别 W D S A 或控制器上会识别 Y B A X。但目前不会识别混合序列,如 W D A X。如果需要实现这一点以及如何实现,正在考虑中。如果您对此有任何想法,请提出问题或拉取请求。

only_if

only_if 示例识别 空格 并在游戏模式下触发事件。Escape 键在菜单和游戏模式之间切换应用。它通过仅在游戏模式下发送 空格 事件来实现这一点。

cargo run --example only_if

run_if

run_if 的行为与 only_if 相同,但实现方式不同。它将 InputSequencePlugin 系统放置在配置为仅在游戏模式下运行的系统集中。因此,切换游戏和菜单模式的 Escape 键不能是一个 KeySequence

cargo run --example run_if

兼容性

bevy-input-sequence bevy
0.5 0.14
0.3 ~ 0.4.0 0.13
0.2 0.12
0.1 0.11

许可协议

此软件包根据 MIT 许可证或 Apache 许可证 2.0 许可。

依赖项

~24–58MB
~1M SLoC