Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add is_* and as_* methods to the event enums #949

Merged
merged 5 commits into from
Feb 2, 2025

Conversation

joshka
Copy link
Collaborator

@joshka joshka commented Nov 26, 2024

Often application code only cares about a small subset of possible
events. These methods make it simpler to write code which checks whether
an event is a particular event type or converts events into the specific
type (returning an Option).

A simple example of this is waiting for any key, which now becomes:

while !event::read()?.is_key_press() {}

This can help simplify some nested match blocks. E.g.:

match event {
    Event::Key(key) if key.kind == KeyEventKind::Press => { ... }
	_ => {}
}

becomes:

if let Some(key) = event.as_key_press() { ... }

Similar flexible methods are aded across all the event enums:

  • Event::is_focus_gained()

  • Event::is_focus_lost()

  • Event::is_key()

  • Event::is_mouse()

  • Event::is_paste()

  • Event::is_resize()

  • Event::is_key_press()

  • Event::as_key_press() -> Option<&KeyEvent>

  • MouseEventKind::is_*()

  • MouseButton::is_*()

  • KeyEventKind::is_*()

  • KeyEvent::is_press()

  • KeyEvent::is_release()

  • KeyEvent::is_repeat()

  • KeyCode::is_*()

  • KeyCode::is_function_key(n)

  • KeyCode::is_char(c)

  • KeyCode::as_char() -> Option<char>

  • KeyCode::is_media_key(media)

  • KeyCode::is_modifier(modifier)

@joshka joshka requested a review from TimonPost as a code owner November 26, 2024 02:06
@joshka joshka changed the title Add is_ and as_ methods to the event enums Add is_* and as_* methods to the event enums Nov 26, 2024
Often application code only cares about a small subset of possible
events. These methods make it simpler to write code which checks whether
an event is a particular event type or converts events into the specific
type (returning an Option).

This can help simplify some nested match blocks. E.g.:

```rust
match event {
    Event::Key(key) if key.kind == KeyEventKind::Press => { ... }
}
```

becomes:

```rust
if let Some(key) = event.as_key_press() { ... }
```

Similar flexible methods are aded across all the event enums:

- `Event::is_focus_gained()`
- `Event::is_focus_lost()`
- `Event::is_key()`
- `Event::is_mouse()`
- `Event::is_paste()`
- `Event::is_resize()`

- `Event::is_key_press()`
- `Event::as_key_press() -> Option<&KeyEvent>`

- `MouseEventKind::is_*()`
- `MouseButton::is_*()`
- `KeyEventKind::is_*()`

- `KeyEvent::is_press()`
- `KeyEvent::is_release()`
- `KeyEvent::is_repeat()`

- `KeyCode::is_*()`
- `KeyCode::is_function_key(n)`
- `KeyCode::is_char(c)`
- `KeyCode::as_char() -> Option<char>`
- `KeyCode::is_media_key(media)`
- `KeyCode::is_modifier(modifier)`
@joshka
Copy link
Collaborator Author

joshka commented Nov 26, 2024

There is an in-flight PR in derive_more that would be also be useful. It adds an AsVariant derive. This would make it easy to deal with e.g. if let Some(mouse) = event.as_mouse() { ... } etc. I'd like to consider waiting for that and adding it to this PR.

Obviously a proper match statement is much better when dealing with more than one event type, but there are many use cases that this change would make simpler.

@joshka
Copy link
Collaborator Author

joshka commented Dec 26, 2024

The derive_more change seems stalled for now, so I added the as_* functions manually.

- add is_key_release() and is_key_repeat() checks
- add as_key_event()
- rename as_key_press() to as_key_press_event()
- add as_key_repeat_event()
- add as_key_release_event()
- add as_mouse_event()
- add as_paste_event()
- more tests
- update event-match and key-display examples
Copy link
Member

@TimonPost TimonPost left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice! Helper functions always good to have :)

src/event.rs Outdated Show resolved Hide resolved
src/event.rs Outdated Show resolved Hide resolved
@TimonPost TimonPost merged commit e063091 into crossterm-rs:master Feb 2, 2025
0 of 6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants