Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions config.c
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,7 @@ void init_default_style(struct mako_style *style) {

style->actions = true;
style->default_timeout = 0;
style->hover_to_dismiss_timeout = 0;
style->ignore_timeout = false;

style->colors.background = 0x285577FF;
Expand Down Expand Up @@ -306,6 +307,11 @@ bool apply_style(struct mako_style *target, const struct mako_style *style) {
target->spec.default_timeout = true;
}

if (style->spec.hover_to_dismiss_timeout) {
target->hover_to_dismiss_timeout = style->hover_to_dismiss_timeout;
target->spec.hover_to_dismiss_timeout = true;
}

if (style->spec.ignore_timeout) {
target->ignore_timeout = style->ignore_timeout;
target->spec.ignore_timeout = true;
Expand Down Expand Up @@ -421,6 +427,7 @@ bool apply_superset_style(
target->spec.icons = true;
target->spec.max_icon_size = true;
target->spec.default_timeout = true;
target->spec.hover_to_dismiss_timeout = true;
target->spec.markup = true;
target->spec.actions = true;
target->spec.history = true;
Expand Down Expand Up @@ -468,6 +475,8 @@ bool apply_superset_style(
target->max_icon_size = max(style->max_icon_size, target->max_icon_size);
target->default_timeout =
max(style->default_timeout, target->default_timeout);
target->hover_to_dismiss_timeout =
max(style->hover_to_dismiss_timeout, target->hover_to_dismiss_timeout);

target->markup |= style->markup;
target->actions |= style->actions;
Expand Down Expand Up @@ -639,6 +648,9 @@ static bool apply_style_option(struct mako_style *style, const char *name,
} else if (strcmp(name, "default-timeout") == 0) {
return spec->default_timeout =
parse_int_ge(value, &style->default_timeout, 0);
} else if (strcmp(name, "hover-to-dismiss-timeout") == 0) {
return spec->hover_to_dismiss_timeout =
parse_int_ge(value, &style->hover_to_dismiss_timeout, 0);
} else if (strcmp(name, "ignore-timeout") == 0) {
return spec->ignore_timeout =
parse_boolean(value, &style->ignore_timeout);
Expand Down Expand Up @@ -920,6 +932,7 @@ int parse_config_arguments(struct mako_config *config, int argc, char **argv) {
{"max-history", required_argument, 0, 0},
{"history", required_argument, 0, 0},
{"default-timeout", required_argument, 0, 0},
{"hover-to-dismiss-timeout", required_argument, 0, 0},
{"ignore-timeout", required_argument, 0, 0},
{"output", required_argument, 0, 0},
{"layer", required_argument, 0, 0},
Expand Down
1 change: 1 addition & 0 deletions contrib/completions/bash/mako
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ _mako()
'--history'
'--sort'
'--default-timeout'
'--hover-to-dismiss-timeout'
'--ignore-timeout'
'--output'
'--layer'
Expand Down
1 change: 1 addition & 0 deletions contrib/completions/fish/mako.fish
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@ complete -c mako -l max-history -d 'Max size of history buffer' -x
complete -c mako -l history -d 'Add expired notifications to history' -xa "1 0"
complete -c mako -l sort -d 'Set notification sorting method' -x
complete -c mako -l default-timeout -d 'Notification timeout in ms' -x
complete -c mako -l hover-to-dismiss-timeout -d 'Default hover-to-dismiss timeout in milliseconds.' -x
complete -c mako -l ignore-timeout -d 'Enable notification timeout or not' -xa "1 0"
complete -c mako -l output -d 'Show notifications on this output' -xa '(complete_outputs)'
complete -c mako -l layer -d 'Show notifications on this layer' -x
Expand Down
1 change: 1 addition & 0 deletions contrib/completions/zsh/_mako
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ _arguments \
'--max-history[Max size of history buffer.]:historical notifications:' \
'--history[Add expired notification to history.]:history:' \
'--default-timeout[Default timeout in milliseconds.]:timeout (ms):' \
'--hover-to-dismiss-timeout[Default hover-to-dismiss timeout in milliseconds.]:timeout (ms):' \
'--ignore-timeout[If set, mako will ignore the expire timeout sent by notifications and use the one provided by default-timeout instead.]:Use default timeout:(0 1)' \
'--output[Show notifications on this output.]:name:' \
'--layer[Arrange notifications at this layer.]:layer:(background bottom top overlay)' \
Expand Down
6 changes: 6 additions & 0 deletions doc/mako.5.scd
Original file line number Diff line number Diff line change
Expand Up @@ -268,6 +268,12 @@ Default when grouped: (%g) <b>%s</b>\\n%b

Default: 0

*hover-to-dismiss-timeout*=_timeout_
Set the default hover-to-dismiss timeout to _timeout_ in milliseconds. To disable the
timeout, set it to zero.

Default: 0

*ignore-timeout*=0|1
If set, mako will ignore the expire timeout sent by notifications and use
the one provided by _default-timeout_ instead.
Expand Down
3 changes: 2 additions & 1 deletion include/config.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ enum mako_icon_location {
// structs are also mirrored.
struct mako_style_spec {
bool width, height, outer_margin, margin, padding, border_size, border_radius, font,
markup, format, text_alignment, actions, default_timeout, ignore_timeout,
markup, format, text_alignment, actions, default_timeout, hover_to_dismiss_timeout, ignore_timeout,
icons, max_icon_size, icon_path, icon_border_radius, group_criteria_spec, invisible, history,
icon_location, max_visible, layer, output, anchor;
struct {
Expand Down Expand Up @@ -76,6 +76,7 @@ struct mako_style {

bool actions;
int default_timeout; // in ms
int hover_to_dismiss_timeout; // in ms
bool ignore_timeout;

struct {
Expand Down
1 change: 1 addition & 0 deletions include/mako.h
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ struct mako_surface {
struct mako_state {
struct mako_config config;
struct mako_event_loop event_loop;
struct mako_timer *hover_dismiss_timer;

sd_bus *bus;
sd_bus_slot *xdg_slot, *mako_slot;
Expand Down
1 change: 1 addition & 0 deletions include/notification.h
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,7 @@ struct mako_binding_context {
typedef char *(*mako_format_func_t)(char variable, bool *markup, void *data);

bool hotspot_at(struct mako_hotspot *hotspot, int32_t x, int32_t y);
bool hotspot_at_offset(struct mako_hotspot *hotspot, int32_t x, int32_t y, int32_t offset);

void reset_notification(struct mako_notification *notif);
struct mako_notification *create_notification(struct mako_state *state);
Expand Down
1 change: 1 addition & 0 deletions main.c
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@ static const char usage[] =
" and/or priority in ascending(+) or\n"
" descending(-) order.\n"
" --default-timeout <timeout> Default timeout in milliseconds.\n"
" --hover-to-dismiss-timeout <timeout> Default hover-to-dismiss timeout in milliseconds.\n"
" --ignore-timeout <0|1> Enable/disable notification timeout.\n"
" --output <name> Show notifications on this output.\n"
" --layer <layer> Arrange notifications at this layer.\n"
Expand Down
7 changes: 7 additions & 0 deletions notification.c
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,13 @@ bool hotspot_at(struct mako_hotspot *hotspot, int32_t x, int32_t y) {
y < hotspot->y + hotspot->height;
}

bool hotspot_at_offset(struct mako_hotspot *hotspot, int32_t x, int32_t y, int32_t offset) {
return x >= hotspot->x - offset &&
y >= hotspot->y - offset &&
x < hotspot->x + hotspot->width + offset &&
y < hotspot->y + hotspot->height + offset;
}

void reset_notification(struct mako_notification *notif) {
struct mako_action *action, *tmp;
wl_list_for_each_safe(action, tmp, &notif->actions, link) {
Expand Down
32 changes: 32 additions & 0 deletions wayland.c
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,11 @@ static void pointer_handle_enter(void *data, struct wl_pointer *wl_pointer,
struct mako_seat *seat = data;
struct mako_state *state = seat->state;

if (state->hover_dismiss_timer != NULL) {
destroy_timer(state->hover_dismiss_timer);
state->hover_dismiss_timer = NULL;
}

seat->pointer.x = wl_fixed_to_int(surface_x);
seat->pointer.y = wl_fixed_to_int(surface_y);
seat->pointer.surface = get_surface(state, wl_surface);
Expand Down Expand Up @@ -231,9 +236,36 @@ static void pointer_handle_enter(void *data, struct wl_pointer *wl_pointer,
}
}

static void handle_notification_hover_dismiss_timer(void *data) {
struct mako_notification *notif = data;
struct mako_surface *surface = notif->surface;

if (notif->state->hover_dismiss_timer != NULL) {
notif->state->hover_dismiss_timer = NULL;
}

close_notification(notif, MAKO_NOTIFICATION_CLOSE_EXPIRED, true);
set_dirty(surface);
}

static void pointer_handle_leave(void *data, struct wl_pointer *wl_pointer,
uint32_t serial, struct wl_surface *wl_surface) {
struct mako_seat *seat = data;
struct mako_state *state = seat->state;
struct mako_style *style = &state->config.superstyle;

struct mako_notification *notif;
wl_list_for_each(notif, &state->notifications, link) {
if (style->hover_to_dismiss_timeout > 0) {
if (hotspot_at_offset(&notif->hotspot, seat->pointer.x, seat->pointer.y, 10)) {
notif->state->hover_dismiss_timer = add_event_loop_timer(
&notif->state->event_loop, style->hover_to_dismiss_timeout,
handle_notification_hover_dismiss_timer, notif);
break;
}
}
}

seat->pointer.surface = NULL;
}

Expand Down