add autohiding to the slit
Dana Jansens danakj@orodu.net
4 files changed,
61 insertions(+),
5 deletions(-)
M
openbox/event.c
→
openbox/event.c
@@ -24,6 +24,7 @@ #endif
static void event_process(XEvent *e); static void event_handle_root(XEvent *e); +static void event_handle_slit(Slit *s, XEvent *e); static void event_handle_slitapp(SlitApp *app, XEvent *e); static void event_handle_client(Client *c, XEvent *e); static void event_handle_menu(Menu *menu, XEvent *e);@@ -376,13 +377,15 @@ static void event_process(XEvent *e)
{ Window window; Client *client = NULL; + Slit *slit = NULL; SlitApp *slitapp = NULL; Menu *menu = NULL; window = event_get_window(e); if (!(client = g_hash_table_lookup(client_map, &window))) if (!(slitapp = g_hash_table_lookup(slit_app_map, &window))) - menu = g_hash_table_lookup(menu_map, &window); + if (!(slit = g_hash_table_lookup(slit_map, &window))) + menu = g_hash_table_lookup(menu_map, &window); event_set_lasttime(e); event_hack_mods(e);@@ -397,6 +400,8 @@ } else if (client)
event_handle_client(client, e); else if (slitapp) event_handle_slitapp(slitapp, e); + else if (slit) + event_handle_slit(slit, e); else if (window == ob_root) event_handle_root(e); else if (e->type == MapRequest)@@ -905,6 +910,18 @@ menu_entry_render(entry);
} break; } + } +} + +static void event_handle_slit(Slit *s, XEvent *e) +{ + switch (e->type) { + case EnterNotify: + slit_hide(s, FALSE); + break; + case LeaveNotify: + slit_hide(s, TRUE); + break; } }
M
openbox/slit.c
→
openbox/slit.c
@@ -1,10 +1,11 @@
#include "slit.h" #include "screen.h" +#include "timer.h" #include "openbox.h" #include "render/theme.h" #include "render/render.h" -#define SLIT_EVENT_MASK (EnterNotifyMask | LeaveNotifyMask) +#define SLIT_EVENT_MASK (EnterWindowMask | LeaveWindowMask) #define SLITAPP_EVENT_MASK (StructureNotifyMask) struct Slit {@@ -25,6 +26,8 @@ gboolean hidden;
Appearance *a_frame; + Timer *hide_timer; + GList *slit_apps; };@@ -50,13 +53,15 @@
for (i = 0; i < nslits; ++i) { slit[i].horz = FALSE; slit[i].hide = TRUE; - slit[i].hidden = FALSE; + slit[i].hidden = TRUE; slit[i].pos = SlitPos_TopRight; + attrib.event_mask = SLIT_EVENT_MASK; attrib.override_redirect = True; slit[i].frame = XCreateWindow(ob_display, ob_root, 0, 0, 1, 1, 0, render_depth, InputOutput, render_visual, - CWOverrideRedirect, &attrib); + CWOverrideRedirect | CWEventMask, + &attrib); slit[i].a_frame = appearance_copy(theme_a_unfocused_title); XSetWindowBorder(ob_display, slit[i].frame, theme_b_color->pixel); XSetWindowBorderWidth(ob_display, slit[i].frame, theme_bwidth);@@ -330,3 +335,35 @@ app->w = w;
app->h = h; slit_configure(app->slit); } + +static void hide_timeout(Slit *self) +{ + /* dont repeat */ + timer_stop(self->hide_timer); + self->hide_timer = NULL; + + /* hide */ + self->hidden = TRUE; + slit_configure(self); +} + +void slit_hide(Slit *self, gboolean hide) +{ + if (self->hidden == hide) + return; + if (!hide) { + /* show */ + self->hidden = FALSE; + slit_configure(self); + + /* if was hiding, stop it */ + if (self->hide_timer) { + timer_stop(self->hide_timer); + self->hide_timer = NULL; + } + } else { + g_assert(!self->hide_timer); + self->hide_timer = timer_start(3000000, + (TimeoutHandler)hide_timeout, self); + } +}
M
openbox/slit.h
→
openbox/slit.h
@@ -31,12 +31,14 @@ SlitPos_BottomLeft,
SlitPos_Left } SlitPosition; +extern GHashTable *slit_map; extern GHashTable *slit_app_map; void slit_startup(); void slit_shutdown(); void slit_configure_all(); +void slit_hide(Slit *self, gboolean hide); void slit_add(Window win, XWMHints *wmhints, XWindowAttributes *attrib);
M
openbox/timer.h
→
openbox/timer.h
@@ -7,7 +7,7 @@ /*! Data type of Timer callback */
typedef void (*TimeoutHandler)(void *data); typedef struct Timer { - /*! Milliseconds between timer firings */ + /*! Microseconds between timer firings */ long delay; /*! Callback for timer expiry */ TimeoutHandler action;