X-Git-Url: https://code.delx.au/spectrwm/blobdiff_plain/bc124ae0b25f4cb24b860eb1ed62ea93917474da..HEAD:/spectrwm.c diff --git a/spectrwm.c b/spectrwm.c index fbddb8a..285bac9 100644 --- a/spectrwm.c +++ b/spectrwm.c @@ -69,6 +69,7 @@ #include #include #include +#include #include #include #include @@ -534,7 +535,7 @@ struct workspace { struct ws_win *focus; /* may be NULL */ struct ws_win *focus_prev; /* may be NULL */ struct ws_win *focus_pending; /* may be NULL */ - struct ws_win *raised; /* may be NULL */ + struct ws_win *focus_raise; /* may be NULL */ struct swm_region *r; /* may be NULL */ struct swm_region *old_r; /* may be NULL */ struct ws_win_list winlist; /* list of windows in ws */ @@ -824,6 +825,7 @@ enum actionid { FN_FOCUS_NEXT, FN_FOCUS_PREV, FN_FOCUS_URGENT, + FN_FULLSCREEN_TOGGLE, FN_MAXIMIZE_TOGGLE, FN_HEIGHT_GROW, FN_HEIGHT_SHRINK, @@ -846,6 +848,8 @@ enum actionid { FN_MVRG_7, FN_MVRG_8, FN_MVRG_9, + KF_MVRG_NEXT, + KF_MVRG_PREV, FN_MVWS_1, FN_MVWS_2, FN_MVWS_3, @@ -868,11 +872,9 @@ enum actionid { FN_MVWS_20, FN_MVWS_21, FN_MVWS_22, - KF_MVWS_NEXT, - KF_MVWS_PREV, FN_NAME_WORKSPACE, FN_QUIT, - FN_RAISE_FOCUSED, + FN_RAISE, FN_RAISE_TOGGLE, FN_RESIZE, FN_RESIZE_CENTERED, @@ -1061,6 +1063,7 @@ void focusout(xcb_focus_out_event_t *); void focusrg(struct binding *, struct swm_region *, union arg *); void fontset_init(void); void free_window(struct ws_win *); +void fullscreen_toggle(struct binding *, struct swm_region *, union arg *); xcb_atom_t get_atom_from_string(const char *); #ifdef SWM_DEBUG char *get_atom_name(xcb_atom_t); @@ -1136,7 +1139,7 @@ void quirk_remove(struct quirk *); void quirk_replace(struct quirk *, const char *, const char *, const char *, uint32_t, int); void quit(struct binding *, struct swm_region *, union arg *); -void raise_focused(struct binding *, struct swm_region *, union arg *); +void raise_focus(struct binding *, struct swm_region *, union arg *); void raise_toggle(struct binding *, struct swm_region *, union arg *); void raise_window(struct ws_win *); void region_containment(struct ws_win *, struct swm_region *, int); @@ -1159,8 +1162,8 @@ void search_win(struct binding *, struct swm_region *, union arg *); void search_win_cleanup(void); void search_workspace(struct binding *, struct swm_region *, union arg *); void send_to_rg(struct binding *, struct swm_region *, union arg *); +void send_to_rg_relative(struct binding *, struct swm_region *, union arg *); void send_to_ws(struct binding *, struct swm_region *, union arg *); -void send_to_ws_relative(struct binding *, struct swm_region *, union arg *); void set_region(struct swm_region *); int setautorun(const char *, const char *, int); void setbinding(uint16_t, enum binding_type, uint32_t, enum actionid, @@ -2416,7 +2419,7 @@ bar_urgent(char *s, size_t sz) strlcat(s, "- ", sz); } } - if(urgent_collapse && s[0]) + if (urgent_collapse && s[0]) s[strlen(s) - 1] = 0; } @@ -3710,7 +3713,16 @@ spawn(int ws_idx, union arg *args, bool close_fd) close(xcb_get_file_descriptor(conn)); - setenv("LD_PRELOAD", SWM_LIB, 1); + if ((ret = getenv("LD_PRELOAD"))) { + if (asprintf(&ret, "%s:%s", SWM_LIB, ret) == -1) { + warn("spawn: asprintf LD_PRELOAD"); + _exit(1); + } + setenv("LD_PRELOAD", ret, 1); + free(ret); + } else { + setenv("LD_PRELOAD", SWM_LIB, 1); + } if (asprintf(&ret, "%d", ws_idx) == -1) { warn("spawn: asprintf SWM_WS"); @@ -3776,8 +3788,8 @@ kill_refs(struct ws_win *win) ws->focus_prev = NULL; if (win == ws->focus_pending) ws->focus_pending = NULL; - if (win == ws->raised) - ws->raised = NULL; + if (win == ws->focus_raise) + ws->focus_raise = NULL; if (TRANS(win)) TAILQ_FOREACH(w, &ws->winlist, entry) @@ -3863,7 +3875,7 @@ unfocus_win(struct ws_win *win) if (win->ws->focus == win) { win->ws->focus = NULL; win->ws->focus_prev = win; - if(win->ws->raised == win && !FLOATING(win)) { + if (win->ws->focus_raise == win && !FLOATING(win)) { update_win_stacking(win); } } @@ -4133,6 +4145,10 @@ set_region(struct swm_region *r) r->s->r_focus = r; + /* Update the focus window frame on the now unfocused region. */ + if (rf && rf->ws->focus) + draw_frame(rf->ws->focus); + ewmh_update_current_desktop(); } @@ -5638,10 +5654,10 @@ send_to_ws(struct binding *bp, struct swm_region *r, union arg *args) /* Transfer focused window to region-relative workspace and focus. */ void -send_to_ws_relative(struct binding *bp, struct swm_region *r, union arg *args) +send_to_rg_relative(struct binding *bp, struct swm_region *r, union arg *args) { - union arg args_abs; - struct swm_region *r_other; + union arg args_abs; + struct swm_region *r_other; if (args->id == 1) { r_other = TAILQ_NEXT(r, entry); @@ -5768,7 +5784,7 @@ pressbutton(struct binding *bp, struct swm_region *r, union arg *args) } void -raise_focused(struct binding *bp, struct swm_region *r, union arg *args) +raise_focus(struct binding *bp, struct swm_region *r, union arg *args) { struct ws_win *win; uint32_t val; @@ -5781,7 +5797,7 @@ raise_focused(struct binding *bp, struct swm_region *r, union arg *args) return; win = r->ws->focus; - r->ws->raised = win; + r->ws->focus_raise = win; raise_window(win); /* Temporarily override stacking order also in the stack */ @@ -6174,7 +6190,7 @@ ewmh_update_desktop_names(void) ++len; } - if((name_list = calloc(len, sizeof(char))) == NULL) + if ((name_list = calloc(len, sizeof(char))) == NULL) err(1, "update_desktop_names: calloc: failed to " "allocate memory."); @@ -6552,6 +6568,32 @@ floating_toggle(struct binding *bp, struct swm_region *r, union arg *args) DNPRINTF(SWM_D_MISC, "floating_toggle: done\n"); } +void +fullscreen_toggle(struct binding *bp, struct swm_region *r, union arg *args) +{ + struct ws_win *w = r->ws->focus; + + /* suppress unused warning since var is needed */ + (void)bp; + (void)args; + + if (w == NULL) + return; + + DNPRINTF(SWM_D_MISC, "fullscreen_toggle: win %#x\n", w->id); + + ewmh_apply_flags(w, w->ewmh_flags ^ EWMH_F_FULLSCREEN); + ewmh_update_wm_state(w); + + stack(r); + + if (w == w->ws->focus) + focus_win(w); + + center_pointer(r); + focus_flush(); + DNPRINTF(SWM_D_MISC, "fullscreen_toggle: done\n"); +} void region_containment(struct ws_win *win, struct swm_region *r, int opts) { @@ -7338,6 +7380,7 @@ struct action { { "focus_next", focus, 0, {.id = SWM_ARG_ID_FOCUSNEXT} }, { "focus_prev", focus, 0, {.id = SWM_ARG_ID_FOCUSPREV} }, { "focus_urgent", focus, 0, {.id = SWM_ARG_ID_FOCUSURGENT} }, + { "fullscreen_toggle", fullscreen_toggle, 0, {0} }, { "maximize_toggle", maximize_toggle,0, {0} }, { "height_grow", resize, 0, {.id = SWM_ARG_ID_HEIGHTGROW} }, { "height_shrink", resize, 0, {.id = SWM_ARG_ID_HEIGHTSHRINK} }, @@ -7360,6 +7403,8 @@ struct action { { "mvrg_7", send_to_rg, 0, {.id = 6} }, { "mvrg_8", send_to_rg, 0, {.id = 7} }, { "mvrg_9", send_to_rg, 0, {.id = 8} }, + { "mvrg_next", send_to_rg_relative, 0, {.id = 1} }, + { "mvrg_prev", send_to_rg_relative, 0, {.id = -1} }, { "mvws_1", send_to_ws, 0, {.id = 0} }, { "mvws_2", send_to_ws, 0, {.id = 1} }, { "mvws_3", send_to_ws, 0, {.id = 2} }, @@ -7382,11 +7427,9 @@ struct action { { "mvws_20", send_to_ws, 0, {.id = 19} }, { "mvws_21", send_to_ws, 0, {.id = 20} }, { "mvws_22", send_to_ws, 0, {.id = 21} }, - { "mvws_next", send_to_ws_relative, 0, {.id = 1} }, - { "mvws_prev", send_to_ws_relative, 0, {.id = -1} }, { "name_workspace", name_workspace, 0, {0} }, { "quit", quit, 0, {0} }, - { "raise_focused", raise_focused, 0, {0} }, + { "raise", raise_focus, 0, {0} }, { "raise_toggle", raise_toggle, 0, {0} }, { "resize", resize, FN_F_NOREPLAY, {.id = SWM_ARG_ID_DONTCENTER} }, { "resize_centered", resize, FN_F_NOREPLAY, {.id = SWM_ARG_ID_CENTER} }, @@ -8124,6 +8167,7 @@ setup_keybindings(void) BINDKEY(MODKEY, XK_k, FN_FOCUS_PREV); BINDKEY(MODSHIFT, XK_Tab, FN_FOCUS_PREV); BINDKEY(MODKEY, XK_u, FN_FOCUS_URGENT); + BINDKEY(MODSHIFT, XK_e, FN_FULLSCREEN_TOGGLE); BINDKEY(MODKEY, XK_e, FN_MAXIMIZE_TOGGLE); BINDKEY(MODSHIFT, XK_equal, FN_HEIGHT_GROW); BINDKEY(MODSHIFT, XK_minus, FN_HEIGHT_SHRINK); @@ -8169,6 +8213,7 @@ setup_keybindings(void) BINDKEY(MODSHIFT, XK_F12, FN_MVWS_22); BINDKEY(MODSHIFT, XK_slash, FN_NAME_WORKSPACE); BINDKEY(MODSHIFT, XK_q, FN_QUIT); + BINDKEY(MODKEY, XK_r, FN_RAISE); BINDKEY(MODSHIFT, XK_r, FN_RAISE_TOGGLE); BINDKEY(MODKEY, XK_q, FN_RESTART); BINDKEY(MODKEY, XK_KP_End, FN_RG_1); @@ -10377,7 +10422,7 @@ get_stack_mode_name(uint8_t mode) { char *name; - switch(mode) { + switch (mode) { case XCB_STACK_MODE_ABOVE: name = "Above"; break; @@ -11052,7 +11097,7 @@ reparentnotify(xcb_reparent_notify_event_t *e) if (win->state == SWM_WIN_STATE_REPARENTING) { win->state = SWM_WIN_STATE_REPARENTED; - if (win->ws->r) + if (win->ws->r && !ICONIC(win)) map_window(win); else unmap_window(win); @@ -11478,7 +11523,6 @@ scan_randr(int idx) int ncrtc = 0; #endif /* SWM_XRR_HAS_CRTC */ struct swm_region *r; - struct ws_win *win; int num_screens; xcb_randr_get_screen_resources_current_cookie_t src; xcb_randr_get_screen_resources_current_reply_t *srr; @@ -11553,13 +11597,8 @@ scan_randr(int idx) screen->height_in_pixels); out: - /* Cleanup unused previously visible workspaces. */ + /* The screen shouldn't focus on unused regions. */ TAILQ_FOREACH(r, &screens[idx].orl, entry) { - TAILQ_FOREACH(win, &r->ws->winlist, entry) - unmap_window(win); - r->ws->state = SWM_WS_STATE_HIDDEN; - - /* The screen shouldn't focus on an unused region. */ if (screens[idx].r_focus == r) screens[idx].r_focus = NULL; } @@ -11571,7 +11610,9 @@ void screenchange(xcb_randr_screen_change_notify_event_t *e) { struct swm_region *r; - int i, num_screens; + struct workspace *ws; + struct ws_win *win; + int i, j, num_screens; DNPRINTF(SWM_D_EVENT, "screenchange: root: %#x\n", e->root); @@ -11604,6 +11645,16 @@ screenchange(xcb_randr_screen_change_notify_event_t *e) focus_region(r); } + /* Cleanup unused previously visible workspaces. */ + for (j = 0; j < workspace_limit; j++) { + ws = &screens[i].ws[j]; + if (ws->r == NULL && ws->state != SWM_WS_STATE_HIDDEN) { + TAILQ_FOREACH(win, &ws->winlist, entry) + unmap_window(win); + ws->state = SWM_WS_STATE_HIDDEN; + } + } + focus_flush(); /* Update workspace state and bar on all regions. */ @@ -11777,7 +11828,7 @@ setup_screens(void) ws->focus = NULL; ws->focus_prev = NULL; ws->focus_pending = NULL; - ws->raised = NULL; + ws->focus_raise = NULL; ws->r = NULL; ws->old_r = NULL; ws->state = SWM_WS_STATE_HIDDEN;