Add key shortcut support, use key bindings to determine menu text
This commit is contained in:
parent
b2998f4317
commit
91e3d3e05a
3 changed files with 116 additions and 19 deletions
69
src/config.rs
Normal file
69
src/config.rs
Normal file
|
|
@ -0,0 +1,69 @@
|
||||||
|
use cosmic::iced::keyboard::{KeyCode, Modifiers};
|
||||||
|
use std::{collections::HashMap, fmt};
|
||||||
|
|
||||||
|
use crate::{fl, Message};
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)]
|
||||||
|
pub struct KeyBind {
|
||||||
|
pub modifiers: Modifiers,
|
||||||
|
pub key_code: KeyCode,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl KeyBind {
|
||||||
|
//TODO: load from config
|
||||||
|
pub fn load() -> HashMap<KeyBind, Message> {
|
||||||
|
let mut keybinds = HashMap::new();
|
||||||
|
|
||||||
|
macro_rules! bind {
|
||||||
|
($modifiers:ident, $key_code:ident, $message:ident) => {{
|
||||||
|
keybinds.insert(
|
||||||
|
KeyBind {
|
||||||
|
modifiers: Modifiers::$modifiers,
|
||||||
|
key_code: KeyCode::$key_code,
|
||||||
|
},
|
||||||
|
Message::$message,
|
||||||
|
);
|
||||||
|
}};
|
||||||
|
}
|
||||||
|
|
||||||
|
bind!(CTRL, N, New);
|
||||||
|
bind!(CTRL, O, OpenFileDialog);
|
||||||
|
bind!(CTRL, S, Save);
|
||||||
|
|
||||||
|
keybinds
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl fmt::Display for KeyBind {
|
||||||
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||||
|
if self.modifiers.logo() {
|
||||||
|
write!(f, "Super + ")?;
|
||||||
|
}
|
||||||
|
if self.modifiers.control() {
|
||||||
|
write!(f, "Ctrl + ")?;
|
||||||
|
}
|
||||||
|
if self.modifiers.alt() {
|
||||||
|
write!(f, "Alt + ")?;
|
||||||
|
}
|
||||||
|
if self.modifiers.shift() {
|
||||||
|
write!(f, "Shift + ")?;
|
||||||
|
}
|
||||||
|
write!(f, "{:?}", self.key_code)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Debug)]
|
||||||
|
pub struct Config {
|
||||||
|
pub wrap: bool,
|
||||||
|
pub keybinds: HashMap<KeyBind, Message>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Config {
|
||||||
|
//TODO: load from cosmic-config
|
||||||
|
pub fn load() -> Self {
|
||||||
|
Self {
|
||||||
|
wrap: false,
|
||||||
|
keybinds: KeyBind::load(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
41
src/main.rs
41
src/main.rs
|
|
@ -4,6 +4,7 @@ use cosmic::{
|
||||||
app::{message, Command, Core, Settings},
|
app::{message, Command, Core, Settings},
|
||||||
executor,
|
executor,
|
||||||
iced::{
|
iced::{
|
||||||
|
event, keyboard, subscription,
|
||||||
widget::{row, text},
|
widget::{row, text},
|
||||||
Alignment, Length, Limits,
|
Alignment, Length, Limits,
|
||||||
},
|
},
|
||||||
|
|
@ -18,6 +19,9 @@ use std::{
|
||||||
sync::Mutex,
|
sync::Mutex,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use config::{Config, KeyBind};
|
||||||
|
mod config;
|
||||||
|
|
||||||
mod localize;
|
mod localize;
|
||||||
|
|
||||||
use self::menu::menu_bar;
|
use self::menu::menu_bar;
|
||||||
|
|
@ -50,18 +54,6 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
|
||||||
pub struct Config {
|
|
||||||
wrap: bool,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Config {
|
|
||||||
//TODO: load from cosmic-config
|
|
||||||
pub fn new() -> Self {
|
|
||||||
Self { wrap: false }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub struct App {
|
pub struct App {
|
||||||
core: Core,
|
core: Core,
|
||||||
nav_model: segmented_button::SingleSelectModel,
|
nav_model: segmented_button::SingleSelectModel,
|
||||||
|
|
@ -70,8 +62,9 @@ pub struct App {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[allow(dead_code)]
|
#[allow(dead_code)]
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug, Eq, PartialEq)]
|
||||||
pub enum Message {
|
pub enum Message {
|
||||||
|
KeyBind(KeyBind),
|
||||||
New,
|
New,
|
||||||
OpenFileDialog,
|
OpenFileDialog,
|
||||||
OpenFile(PathBuf),
|
OpenFile(PathBuf),
|
||||||
|
|
@ -289,7 +282,7 @@ impl cosmic::Application for App {
|
||||||
core,
|
core,
|
||||||
nav_model: nav_bar::Model::builder().build(),
|
nav_model: nav_bar::Model::builder().build(),
|
||||||
tab_model: segmented_button::Model::builder().build(),
|
tab_model: segmented_button::Model::builder().build(),
|
||||||
config: Config::new(),
|
config: Config::load(),
|
||||||
};
|
};
|
||||||
|
|
||||||
for arg in env::args().skip(1) {
|
for arg in env::args().skip(1) {
|
||||||
|
|
@ -383,6 +376,13 @@ impl cosmic::Application for App {
|
||||||
|
|
||||||
fn update(&mut self, message: Message) -> Command<Message> {
|
fn update(&mut self, message: Message) -> Command<Message> {
|
||||||
match message {
|
match message {
|
||||||
|
Message::KeyBind(key_bind) => {
|
||||||
|
for (config_key_bind, config_message) in self.config.keybinds.iter() {
|
||||||
|
if config_key_bind == &key_bind {
|
||||||
|
return self.update(config_message.clone());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Message::New => {
|
Message::New => {
|
||||||
self.open_tab(None);
|
self.open_tab(None);
|
||||||
return self.update_title();
|
return self.update_title();
|
||||||
|
|
@ -541,4 +541,17 @@ impl cosmic::Application for App {
|
||||||
//content.explain(cosmic::iced::Color::WHITE)
|
//content.explain(cosmic::iced::Color::WHITE)
|
||||||
content
|
content
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn subscription(&self) -> subscription::Subscription<Message> {
|
||||||
|
subscription::events_with(|event, status| match event {
|
||||||
|
event::Event::Keyboard(keyboard::Event::KeyPressed {
|
||||||
|
modifiers,
|
||||||
|
key_code,
|
||||||
|
}) => Some(Message::KeyBind(KeyBind {
|
||||||
|
modifiers,
|
||||||
|
key_code,
|
||||||
|
})),
|
||||||
|
_ => None,
|
||||||
|
})
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
25
src/menu.rs
25
src/menu.rs
|
|
@ -39,8 +39,23 @@ pub fn menu_bar<'a>(config: &Config) -> Element<'a, Message> {
|
||||||
let menu_folder =
|
let menu_folder =
|
||||||
|label| menu_button!(widget::text(label), horizontal_space(Length::Fill), ">");
|
|label| menu_button!(widget::text(label), horizontal_space(Length::Fill), ">");
|
||||||
|
|
||||||
let menu_item =
|
let menu_item = |label, message| {
|
||||||
|label, message| MenuTree::new(menu_button!(widget::text(label)).on_press(message));
|
let mut key = String::new();
|
||||||
|
for (config_key_bind, config_message) in config.keybinds.iter() {
|
||||||
|
if config_message == &message {
|
||||||
|
key = config_key_bind.to_string();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
MenuTree::new(
|
||||||
|
menu_button!(
|
||||||
|
widget::text(label),
|
||||||
|
horizontal_space(Length::Fill),
|
||||||
|
widget::text(key)
|
||||||
|
)
|
||||||
|
.on_press(message),
|
||||||
|
)
|
||||||
|
};
|
||||||
|
|
||||||
let menu_key = |label, key, message| {
|
let menu_key = |label, key, message| {
|
||||||
MenuTree::new(
|
MenuTree::new(
|
||||||
|
|
@ -53,16 +68,16 @@ pub fn menu_bar<'a>(config: &Config) -> Element<'a, Message> {
|
||||||
MenuTree::with_children(
|
MenuTree::with_children(
|
||||||
menu_root(fl!("file")),
|
menu_root(fl!("file")),
|
||||||
vec![
|
vec![
|
||||||
menu_key(fl!("new-file"), "Ctrl + N", Message::New),
|
menu_item(fl!("new-file"), Message::New),
|
||||||
menu_key(fl!("new-window"), "Ctrl + Shift + N", Message::Todo),
|
menu_key(fl!("new-window"), "Ctrl + Shift + N", Message::Todo),
|
||||||
MenuTree::new(horizontal_rule(1)),
|
MenuTree::new(horizontal_rule(1)),
|
||||||
menu_key(fl!("open-file"), "Ctrl + O", Message::OpenFileDialog),
|
menu_item(fl!("open-file"), Message::OpenFileDialog),
|
||||||
MenuTree::with_children(
|
MenuTree::with_children(
|
||||||
menu_folder(fl!("open-recent")),
|
menu_folder(fl!("open-recent")),
|
||||||
vec![menu_item(fl!("todo"), Message::Todo)],
|
vec![menu_item(fl!("todo"), Message::Todo)],
|
||||||
),
|
),
|
||||||
MenuTree::new(horizontal_rule(1)),
|
MenuTree::new(horizontal_rule(1)),
|
||||||
menu_key(fl!("save"), "Ctrl + S", Message::Save),
|
menu_item(fl!("save"), Message::Save),
|
||||||
menu_key(fl!("save-as"), "Ctrl + Shift + S", Message::Todo),
|
menu_key(fl!("save-as"), "Ctrl + Shift + S", Message::Todo),
|
||||||
MenuTree::new(horizontal_rule(1)),
|
MenuTree::new(horizontal_rule(1)),
|
||||||
menu_item(fl!("revert-all-changes"), Message::Todo),
|
menu_item(fl!("revert-all-changes"), Message::Todo),
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue