int term_width = 0;
int font_adjusted = 0;
unsigned int mod_key = MODKEY;
+bool warp_focus = false;
bool warp_pointer = false;
-unsigned int mouse_button_move = XCB_BUTTON_INDEX_1;
-unsigned int mouse_button_resize = XCB_BUTTON_INDEX_3;
+bool workspace_clamp = false;
/* dmenu search */
struct swm_region *search_r;
#define SWM_Q_TRANSSZ (1<<1) /* transiend window size too small */
#define SWM_Q_ANYWHERE (1<<2) /* don't position this window */
#define SWM_Q_XTERM_FONTADJ (1<<3) /* adjust xterm fonts when resizing */
-#define SWM_Q_FULLSCREEN (1<<4) /* remove border */
+#define SWM_Q_FULLSCREEN (1<<4) /* remove border when fullscreen */
#define SWM_Q_FOCUSPREV (1<<5) /* focus on caller */
#define SWM_Q_NOFOCUSONMAP (1<<6) /* Don't focus on window when mapped. */
#define SWM_Q_FOCUSONMAP_SINGLE (1<<7) /* Only focus if single win of type. */
#define SWM_Q_IGNOREPID (1<<9) /* Ignore PID when determining ws. */
#define SWM_Q_IGNORESPAWNWS (1<<10) /* Ignore _SWM_WS when managing win. */
#define SWM_Q_NOFOCUSCYCLE (1<<11) /* Remove from normal focus cycle. */
+#define SWM_Q_MINIMALBORDER (1<<12) /* Remove border when floating/unfocused */
};
TAILQ_HEAD(quirk_list, quirk);
struct quirk_list quirks = TAILQ_HEAD_INITIALIZER(quirks);
void check_conn(void);
void clear_keys(void);
int clear_maximized(struct workspace *);
+void clear_quirks(void);
+void clear_spawns(void);
void clientmessage(xcb_client_message_event_t *);
void client_msg(struct ws_win *, xcb_atom_t, xcb_timestamp_t);
int conf_load(const char *, int);
int setconfbinding(const char *, const char *, int);
int setconfcolor(const char *, const char *, int);
int setconfmodkey(const char *, const char *, int);
-int setconfmousebuttonmove(const char *, const char *, int);
-int setconfmousebuttonresize(const char *, const char *, int);
int setconfquirk(const char *, const char *, int);
int setconfregion(const char *, const char *, int);
int setconfspawn(const char *, const char *, int);
void updatenumlockmask(void);
void update_floater(struct ws_win *);
void update_modkey(unsigned int);
-unsigned char update_mousebutton(unsigned char, unsigned int);
void update_win_stacking(struct ws_win *);
void update_window(struct ws_win *);
void update_window_color(struct ws_win *);
if (win->ws->always_raise)
raise_window(win);
+ /* Update border width */
+ if (win->bordered && (win->quirks & SWM_Q_MINIMALBORDER) &&
+ FLOATING(win)) {
+ win->bordered = 0;
+ X(win) += border_width;
+ Y(win) += border_width;
+ update_window(win);
+ }
+
xcb_change_property(conn, XCB_PROP_MODE_REPLACE, win->s->root,
ewmh[_NET_ACTIVE_WINDOW].atom, XCB_ATOM_WINDOW, 32, 1, &none);
&cfw->s->c[(MAXIMIZED(cfw) ?
SWM_S_COLOR_UNFOCUS_MAXIMIZED :
SWM_S_COLOR_UNFOCUS)].pixel);
+
+ /* Update border width */
+ if (cfw->bordered &&
+ (cfw->quirks & SWM_Q_MINIMALBORDER) &&
+ FLOATING(cfw)) {
+ cfw->bordered = 0;
+ X(cfw) += border_width;
+ Y(cfw) += border_width;
+ update_window(cfw);
+ }
} else {
unfocus_win(cfw);
}
&win->id);
}
- if (cfw != win)
+ if (cfw != win) {
/* Update window border even if workspace is hidden. */
update_window_color(win);
+ /* Update border width */
+ if (!win->bordered && WS_FOCUSED(win->ws) &&
+ (win->quirks & SWM_Q_MINIMALBORDER) && FLOATING(win)) {
+ win->bordered = 1;
+ X(win) -= border_width;
+ Y(win) -= border_width;
+ update_window(win);
+ }
+ }
+
out:
bar_draw();
if (new_ws == old_ws)
return;
+ other_r = new_ws->r;
+ if (other_r && workspace_clamp) {
+ DNPRINTF(SWM_D_WS, "switchws: ws clamped.\n");
+
+ if (warp_focus) {
+ DNPRINTF(SWM_D_WS, "switchws: warping focus to region "
+ "with ws %d.\n", wsid);
+ focus_region(other_r);
+ center_pointer(other_r);
+ focus_flush();
+ }
+ return;
+ }
+
if ((win = old_ws->focus) != NULL) {
update_window_color(win);
&none);
}
- other_r = new_ws->r;
- if (other_r == NULL) {
- /* the other workspace is hidden, hide this one */
- old_ws->r = NULL;
- unmap_old = true;
- } else {
+ if (other_r) {
/* the other ws is visible in another region, exchange them */
other_r->ws_prior = new_ws;
other_r->ws = old_ws;
old_ws->r = other_r;
+ } else {
+ /* the other workspace is hidden, hide this one */
+ old_ws->r = NULL;
+ unmap_old = true;
}
+
this_r->ws_prior = old_ws;
this_r->ws = new_ws;
new_ws->r = this_r;
if (r != ws->old_r)
load_float_geom(win);
- if ((win->quirks & SWM_Q_FULLSCREEN) &&
- WIDTH(win) >= WIDTH(r) && HEIGHT(win) >= HEIGHT(r)) {
- /* Remove border for FULLSCREEN quirk. */
+ if (((win->quirks & SWM_Q_FULLSCREEN) &&
+ WIDTH(win) >= WIDTH(r) && HEIGHT(win) >= HEIGHT(r)) ||
+ ((!WS_FOCUSED(win->ws) || win->ws->focus != win) &&
+ (win->quirks & SWM_Q_MINIMALBORDER))) {
+ /* Remove border */
win->bordered = false;
} else if (!MANUAL(win)) {
if (TRANS(win) && (win->quirks & SWM_Q_TRANSSZ)) {
int num_screens, i;
num_screens = get_screen_count();
- for (i = 0; i < num_screens; ++i)
- xcb_change_property(conn, XCB_PROP_MODE_REPLACE,
- screens[i].root, ewmh[_NET_CURRENT_DESKTOP].atom,
- XCB_ATOM_CARDINAL, 32, 1, &screens[i].r_focus->ws->idx);
+ for (i = 0; i < num_screens; ++i) {
+ if (screens[i].r_focus)
+ xcb_change_property(conn, XCB_PROP_MODE_REPLACE,
+ screens[i].root, ewmh[_NET_CURRENT_DESKTOP].atom,
+ XCB_ATOM_CARDINAL, 32, 1,
+ &screens[i].r_focus->ws->idx);
+ }
}
void
buttons[i].mask = mod;
}
-unsigned char
-update_mousebutton(unsigned char type, unsigned int but)
-{
- int i;
-
- switch (type) {
- case 0:
- mouse_button_move = but;
- break;
- case 1:
- mouse_button_resize = but;
- break;
- }
-
- for (i = 0; i < LENGTH(buttons); i++) {
- if (buttons[i].func == move)
- buttons[i].button = mouse_button_move;
-
- if (buttons[i].func == resize)
- buttons[i].button = mouse_button_resize;
- }
-
- return(1);
-}
-
int
spawn_expand(struct swm_region *r, union arg *args, const char *spawn_name,
char ***ret_args)
DNPRINTF(SWM_D_SPAWN, "spawn_remove: leave\n");
}
+void
+clear_spawns(void)
+{
+ struct spawn_prog *sp;
+
+ while ((sp = TAILQ_FIRST(&spawns)) != NULL) {
+ spawn_remove(sp);
+ }
+}
+
struct spawn_prog*
spawn_find(const char *name)
{
"IGNOREPID",
"IGNORESPAWNWS",
"NOFOCUSCYCLE",
+ "MINIMALBORDER",
};
/* SWM_Q_DELIM: retain '|' for back compat for now (2009-08-11) */
free(qp);
}
+void
+clear_quirks(void)
+{
+ struct quirk *qp;
+
+ while ((qp = TAILQ_FIRST(&quirks)) != NULL) {
+ quirk_remove(qp);
+ }
+}
+
void
quirk_replace(struct quirk *qp, const char *class, const char *instance,
const char *name, uint32_t quirk, int ws)
SWM_S_URGENT_COLLAPSE,
SWM_S_URGENT_ENABLED,
SWM_S_VERBOSE_LAYOUT,
+ SWM_S_WARP_FOCUS,
SWM_S_WARP_POINTER,
SWM_S_WINDOW_CLASS_ENABLED,
SWM_S_WINDOW_INSTANCE_ENABLED,
SWM_S_WINDOW_NAME_ENABLED,
+ SWM_S_WORKSPACE_CLAMP,
SWM_S_WORKSPACE_LIMIT,
SWM_S_WORKSPACE_NAME,
};
layouts[i].l_string = plain_stacker;
}
break;
+ case SWM_S_WARP_FOCUS:
+ warp_focus = (atoi(value) != 0);
+ break;
case SWM_S_WARP_POINTER:
warp_pointer = (atoi(value) != 0);
break;
case SWM_S_WINDOW_NAME_ENABLED:
window_name_enabled = (atoi(value) != 0);
break;
+ case SWM_S_WORKSPACE_CLAMP:
+ workspace_clamp = (atoi(value) != 0);
+ break;
case SWM_S_WORKSPACE_LIMIT:
workspace_limit = atoi(value);
if (workspace_limit > SWM_WS_MAX)
return (0);
}
-int
-setconfmousebuttonmove(const char *selector, const char *value, int flags)
-{
- /* suppress unused warnings since vars are needed */
- (void)selector;
- (void)flags;
-
- if (strncasecmp(value, "But1", strlen("But1")) == 0) {
- if (!update_mousebutton(0, XCB_BUTTON_INDEX_1))
- return (1);
- } else if (strncasecmp(value, "But2", strlen("But2")) == 0) {
- if (!update_mousebutton(0, XCB_BUTTON_INDEX_2))
- return (1);
- } else if (strncasecmp(value, "But3", strlen("But3")) == 0) {
- if (!update_mousebutton(0, XCB_BUTTON_INDEX_3))
- return (1);
- } else
- return (1);
- return (0);
-}
-
-int
-setconfmousebuttonresize(const char *selector, const char *value, int flags)
-{
- /* suppress unused warnings since vars are needed */
- (void)selector;
- (void)flags;
-
- if (strncasecmp(value, "But1", strlen("But1")) == 0) {
- if (!update_mousebutton(1, XCB_BUTTON_INDEX_1))
- return (1);
- } else if (strncasecmp(value, "But2", strlen("But2")) == 0) {
- if (!update_mousebutton(1, XCB_BUTTON_INDEX_2))
- return (1);
- } else if (strncasecmp(value, "But3", strlen("But3")) == 0) {
- if (!update_mousebutton(1, XCB_BUTTON_INDEX_3))
- return (1);
- } else
- return (1);
- return (0);
-}
-
int
setconfcolor(const char *selector, const char *value, int flags)
{
{ "layout", setlayout, 0 },
{ "maximize_hide_bar", setconfvalue, SWM_S_MAXIMIZE_HIDE_BAR },
{ "modkey", setconfmodkey, 0 },
- { "move_button", setconfmousebuttonmove, 0 },
- { "resize_button", setconfmousebuttonresize, 0 },
{ "program", setconfspawn, 0 },
{ "quirk", setconfquirk, 0 },
{ "region", setconfregion, 0 },
{ "urgent_collapse", setconfvalue, SWM_S_URGENT_COLLAPSE },
{ "urgent_enabled", setconfvalue, SWM_S_URGENT_ENABLED },
{ "verbose_layout", setconfvalue, SWM_S_VERBOSE_LAYOUT },
+ { "warp_focus", setconfvalue, SWM_S_WARP_FOCUS },
{ "warp_pointer", setconfvalue, SWM_S_WARP_POINTER },
{ "window_class_enabled", setconfvalue, SWM_S_WINDOW_CLASS_ENABLED },
{ "window_instance_enabled", setconfvalue, SWM_S_WINDOW_INSTANCE_ENABLED },
{ "window_name_enabled", setconfvalue, SWM_S_WINDOW_NAME_ENABLED },
+ { "workspace_clamp", setconfvalue, SWM_S_WORKSPACE_CLAMP },
{ "workspace_limit", setconfvalue, SWM_S_WORKSPACE_LIMIT },
{ "name", setconfvalue, SWM_S_WORKSPACE_NAME },
};
if (line)
free(line);
fclose(config);
-
- if (mouse_button_move == mouse_button_resize) {
- add_startup_exception("%s: move and resize mouse buttons match",
- filename);
- }
-
DNPRINTF(SWM_D_CONF, "conf_load: end\n");
return (0);
cursors_cleanup();
+ clear_quirks();
+ clear_spawns();
+ clear_keys();
+
teardown_ewmh();
num_screens = get_screen_count();
for (i = 0; i < num_screens; ++i) {
+ struct swm_region *r;
+ int j;
+
xcb_set_input_focus(conn, XCB_INPUT_FOCUS_POINTER_ROOT,
screens[i].root, XCB_CURRENT_TIME);
XftColorFree(display, DefaultVisual(display, i),
DefaultColormap(display, i), &search_font_color);
}
+
+ for (j = 0; j < SWM_S_COLOR_MAX; ++j) {
+ free(screens[i].c[j].name);
+ }
+
+ for (j = 0; j < SWM_WS_MAX; ++j) {
+ struct ws_win *win;
+
+ free(screens[i].ws[j].name);
+
+ while ((win = TAILQ_FIRST(&screens[i].ws[j].winlist)) != NULL) {
+ TAILQ_REMOVE(&screens[i].ws[j].winlist, win, entry);
+ free(win);
+ }
+ }
+
+ while ((r = TAILQ_FIRST(&screens[i].rl)) != NULL) {
+ TAILQ_REMOVE(&screens[i].rl, r, entry);
+ free(r->bar);
+ free(r);
+ }
+
+ while ((r = TAILQ_FIRST(&screens[i].orl)) != NULL) {
+ TAILQ_REMOVE(&screens[i].rl, r, entry);
+ free(r->bar);
+ free(r);
+ }
}
+ free(screens);
- if (bar_font_legacy)
+ free(bar_format);
+ free(bar_fonts);
+ free(clock_format);
+ free(startup_exception);
+
+ if (bar_fs)
XFreeFontSet(display, bar_fs);
- else {
+ if (bar_font_legacy == false)
XftFontClose(display, bar_font);
- }
xcb_key_symbols_free(syms);
xcb_flush(conn);