Use bitflags for keyboard::Modifiers

This commit is contained in:
Héctor Ramón Jiménez 2021-07-12 22:01:57 +02:00
parent 735cfb7908
commit b57d567981
No known key found for this signature in database
GPG key ID: 44B88EB52AB1EE8D
6 changed files with 78 additions and 72 deletions

View file

@ -8,6 +8,7 @@ license = "MIT"
repository = "https://github.com/hecrj/iced"
[dependencies]
bitflags = "1.2"
[dependencies.palette]
version = "0.5.0"

View file

@ -1,20 +1,53 @@
/// The current state of the keyboard modifiers.
#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
pub struct Modifiers {
/// Whether a shift key is pressed
pub shift: bool,
use bitflags::bitflags;
/// Whether a control key is pressed
pub control: bool,
/// Whether an alt key is pressed
pub alt: bool,
/// Whether a logo key is pressed (e.g. windows key, command key...)
pub logo: bool,
bitflags! {
/// The current state of the keyboard modifiers.
#[derive(Default)]
pub struct Modifiers: u32{
/// The "shift" key.
const SHIFT = 0b100 << 0;
// const LSHIFT = 0b010 << 0;
// const RSHIFT = 0b001 << 0;
//
/// The "control" key.
const CTRL = 0b100 << 3;
// const LCTRL = 0b010 << 3;
// const RCTRL = 0b001 << 3;
//
/// The "alt" key.
const ALT = 0b100 << 6;
// const LALT = 0b010 << 6;
// const RALT = 0b001 << 6;
//
/// The "windows" key on Windows, "command" key on Mac, and
/// "super" key on Linux.
const LOGO = 0b100 << 9;
// const LLOGO = 0b010 << 9;
// const RLOGO = 0b001 << 9;
}
}
impl Modifiers {
/// Returns true if the [`SHIFT`] key is pressed in the [`Modifiers`].
pub fn shift(self) -> bool {
self.contains(Self::SHIFT)
}
/// Returns true if the [`CTRL`] key is pressed in the [`Modifiers`].
pub fn control(self) -> bool {
self.contains(Self::CTRL)
}
/// Returns true if the [`ALT`] key is pressed in the [`Modifiers`].
pub fn alt(self) -> bool {
self.contains(Self::ALT)
}
/// Returns true if the [`LOGO`] key is pressed in the [`Modifiers`].
pub fn logo(self) -> bool {
self.contains(Self::LOGO)
}
/// Returns true if a "command key" is pressed in the [`Modifiers`].
///
/// The "command key" is the main modifier key used to issue commands in the
@ -22,24 +55,13 @@ impl Modifiers {
///
/// - It is the `logo` or command key (⌘) on macOS
/// - It is the `control` key on other platforms
pub fn is_command_pressed(self) -> bool {
pub fn command(self) -> bool {
#[cfg(target_os = "macos")]
let is_pressed = self.logo;
let is_pressed = self.logo();
#[cfg(not(target_os = "macos"))]
let is_pressed = self.control;
let is_pressed = self.control();
is_pressed
}
/// Returns true if the current [`Modifiers`] have at least the same
/// keys pressed as the provided ones, and false otherwise.
pub fn matches(&self, modifiers: Self) -> bool {
let shift = !modifiers.shift || self.shift;
let control = !modifiers.control || self.control;
let alt = !modifiers.alt || self.alt;
let logo = !modifiers.logo || self.logo;
shift && control && alt && logo
}
}

View file

@ -43,18 +43,8 @@ impl Application for App {
}
fn menu(&self) -> Menu<Message> {
let alt = Modifiers {
alt: true,
control: false,
logo: false,
shift: false,
};
let ctrl_shift = Modifiers {
control: true,
shift: true,
logo: false,
alt: false,
};
let alt = Modifiers::ALT;
let ctrl_shift = Modifiers::CTRL | Modifiers::SHIFT;
Menu::with_entries(vec![
menu::Entry::dropdown(

View file

@ -146,7 +146,7 @@ impl Application for Example {
Event::Keyboard(keyboard::Event::KeyPressed {
modifiers,
key_code,
}) if modifiers.is_command_pressed() => handle_hotkey(key_code),
}) if modifiers.command() => handle_hotkey(key_code),
_ => None,
}
})

View file

@ -362,7 +362,7 @@ where
Event::Keyboard(keyboard::Event::CharacterReceived(c))
if self.state.is_focused
&& self.state.is_pasting.is_none()
&& !self.state.keyboard_modifiers.is_command_pressed()
&& !self.state.keyboard_modifiers.command()
&& !c.is_control() =>
{
let mut editor =
@ -450,7 +450,7 @@ where
if platform::is_jump_modifier_pressed(modifiers)
&& !self.is_secure
{
if modifiers.shift {
if modifiers.shift() {
self.state
.cursor
.select_left_by_words(&self.value);
@ -459,7 +459,7 @@ where
.cursor
.move_left_by_words(&self.value);
}
} else if modifiers.shift {
} else if modifiers.shift() {
self.state.cursor.select_left(&self.value)
} else {
self.state.cursor.move_left(&self.value);
@ -469,7 +469,7 @@ where
if platform::is_jump_modifier_pressed(modifiers)
&& !self.is_secure
{
if modifiers.shift {
if modifiers.shift() {
self.state
.cursor
.select_right_by_words(&self.value);
@ -478,14 +478,14 @@ where
.cursor
.move_right_by_words(&self.value);
}
} else if modifiers.shift {
} else if modifiers.shift() {
self.state.cursor.select_right(&self.value)
} else {
self.state.cursor.move_right(&self.value);
}
}
keyboard::KeyCode::Home => {
if modifiers.shift {
if modifiers.shift() {
self.state.cursor.select_range(
self.state.cursor.start(&self.value),
0,
@ -495,7 +495,7 @@ where
}
}
keyboard::KeyCode::End => {
if modifiers.shift {
if modifiers.shift() {
self.state.cursor.select_range(
self.state.cursor.start(&self.value),
self.value.len(),
@ -505,10 +505,7 @@ where
}
}
keyboard::KeyCode::C
if self
.state
.keyboard_modifiers
.is_command_pressed() =>
if self.state.keyboard_modifiers.command() =>
{
match self.state.cursor.selection(&self.value) {
Some((start, end)) => {
@ -520,10 +517,7 @@ where
}
}
keyboard::KeyCode::X
if self
.state
.keyboard_modifiers
.is_command_pressed() =>
if self.state.keyboard_modifiers.command() =>
{
match self.state.cursor.selection(&self.value) {
Some((start, end)) => {
@ -545,7 +539,7 @@ where
messages.push(message);
}
keyboard::KeyCode::V => {
if self.state.keyboard_modifiers.is_command_pressed() {
if self.state.keyboard_modifiers.command() {
let content = match self.state.is_pasting.take() {
Some(content) => content,
None => {
@ -576,10 +570,7 @@ where
}
}
keyboard::KeyCode::A
if self
.state
.keyboard_modifiers
.is_command_pressed() =>
if self.state.keyboard_modifiers.command() =>
{
self.state.cursor.select_all(&self.value);
}
@ -858,9 +849,9 @@ mod platform {
pub fn is_jump_modifier_pressed(modifiers: keyboard::Modifiers) -> bool {
if cfg!(target_os = "macos") {
modifiers.alt
modifiers.alt()
} else {
modifiers.control
modifiers.control()
}
}
}

View file

@ -165,10 +165,10 @@ fn hotkey(hotkey: keyboard::Hotkey) -> winit::window::Hotkey {
use winit::event::ModifiersState;
let mut modifiers = ModifiersState::empty();
modifiers.set(ModifiersState::CTRL, hotkey.modifiers.control);
modifiers.set(ModifiersState::SHIFT, hotkey.modifiers.shift);
modifiers.set(ModifiersState::ALT, hotkey.modifiers.alt);
modifiers.set(ModifiersState::LOGO, hotkey.modifiers.logo);
modifiers.set(ModifiersState::CTRL, hotkey.modifiers.control());
modifiers.set(ModifiersState::SHIFT, hotkey.modifiers.shift());
modifiers.set(ModifiersState::ALT, hotkey.modifiers.alt());
modifiers.set(ModifiersState::LOGO, hotkey.modifiers.logo());
winit::window::Hotkey::new(modifiers, to_virtual_keycode(hotkey.key))
}
@ -249,12 +249,14 @@ pub fn mouse_button(mouse_button: winit::event::MouseButton) -> mouse::Button {
pub fn modifiers(
modifiers: winit::event::ModifiersState,
) -> keyboard::Modifiers {
keyboard::Modifiers {
shift: modifiers.shift(),
control: modifiers.ctrl(),
alt: modifiers.alt(),
logo: modifiers.logo(),
}
let mut result = keyboard::Modifiers::empty();
result.set(keyboard::Modifiers::SHIFT, modifiers.shift());
result.set(keyboard::Modifiers::CTRL, modifiers.ctrl());
result.set(keyboard::Modifiers::ALT, modifiers.alt());
result.set(keyboard::Modifiers::LOGO, modifiers.logo());
result
}
/// Converts a physical cursor position to a logical `Point`.