Skip to content

Commit

Permalink
feat: add keyboard support for button presses
Browse files Browse the repository at this point in the history
Co-authored-by: Julian Schuler <[email protected]>
  • Loading branch information
w-lfchen and julianschuler committed Sep 3, 2024
1 parent 8661abf commit 95e1046
Showing 1 changed file with 23 additions and 11 deletions.
34 changes: 23 additions & 11 deletions crates/eww/src/widgets/widget_definitions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -38,16 +38,16 @@ use yuck::{
/// thus not connecting a new handler unless the condition is met.
macro_rules! connect_signal_handler {
($widget:ident, if $cond:expr, $connect_expr:expr) => {{
const KEY:&str = std::concat!("signal-handler:", std::line!());
unsafe {
let key = ::std::concat!("signal-handler:", ::std::line!());
let old = $widget.data::<gtk::glib::SignalHandlerId>(key);
let old = $widget.data::<gtk::glib::SignalHandlerId>(KEY);

if let Some(old) = old {
let a = old.as_ref().as_raw();
$widget.disconnect(gtk::glib::SignalHandlerId::from_glib(a));
}

$widget.set_data::<gtk::glib::SignalHandlerId>(key, $connect_expr);
$widget.set_data::<gtk::glib::SignalHandlerId>(KEY, $connect_expr);
}
}};
($widget:ident, $connect_expr:expr) => {{
Expand Down Expand Up @@ -494,7 +494,6 @@ fn build_gtk_input(bargs: &mut BuilderArgs) -> Result<gtk::Entry> {
prop(value: as_string) {
gtk_widget.set_text(&value);
},

// @prop onchange - Command to run when the text changes. The placeholder `{}` will be replaced by the value
// @prop timeout - timeout of the command. Default: "200ms"
prop(timeout: as_duration = Duration::from_millis(200), onchange: as_string) {
Expand Down Expand Up @@ -534,8 +533,15 @@ fn build_gtk_button(bargs: &mut BuilderArgs) -> Result<gtk::Button> {
// @prop onrightclick - a command that get's run when the button is rightclicked
onrightclick: as_string = ""
) {
gtk_widget.add_events(gdk::EventMask::BUTTON_PRESS_MASK);
connect_signal_handler!(gtk_widget, gtk_widget.connect_button_press_event(move |_, evt| {
// animate button upon right-/middleclick (if gtk theme supports it)
// since we do this, we can't use `connect_clicked` as that would always run `onclick` as well
connect_signal_handler!(gtk_widget, gtk_widget.connect_button_press_event(move |button, _| {
button.emit_activate();
glib::Propagation::Proceed
}));
let onclick_ = onclick.clone();
// mouse click events
connect_signal_handler!(gtk_widget, gtk_widget.connect_button_release_event(move |_, evt| {
match evt.button() {
1 => run_command(timeout, &onclick, &[] as &[&str]),
2 => run_command(timeout, &onmiddleclick, &[] as &[&str]),
Expand All @@ -544,8 +550,18 @@ fn build_gtk_button(bargs: &mut BuilderArgs) -> Result<gtk::Button> {
}
glib::Propagation::Proceed
}));
// keyboard events
connect_signal_handler!(gtk_widget, gtk_widget.connect_key_release_event(move |_, evt| {
match evt.scancode() {
// return
36 => run_command(timeout, &onclick_, &[] as &[&str]),
// space
65 => run_command(timeout, &onclick_, &[] as &[&str]),
_ => {},
}
glib::Propagation::Proceed
}));
}

});
Ok(gtk_widget)
}
Expand Down Expand Up @@ -915,9 +931,6 @@ fn build_gtk_event_box(bargs: &mut BuilderArgs) -> Result<gtk::EventBox> {
};
}));
},

// TODO the fact that we have the same code here as for button is ugly, as we want to keep consistency

prop(
// @prop timeout - timeout of the command. Default: "200ms"
timeout: as_duration = Duration::from_millis(200),
Expand All @@ -940,7 +953,6 @@ fn build_gtk_event_box(bargs: &mut BuilderArgs) -> Result<gtk::EventBox> {
}));
}
});

Ok(gtk_widget)
}

Expand Down

0 comments on commit 95e1046

Please sign in to comment.