diff options
| author | Abhinav <abhinav.prsai@gmail.com> | 2025-05-29 13:31:46 +0100 |
|---|---|---|
| committer | Abhinav <abhinav.prsai@gmail.com> | 2025-05-29 13:31:46 +0100 |
| commit | ec78d7e63c7290b1b495e8947177d52ccfdc32bb (patch) | |
| tree | 4b8cee92d515ba486dbaad25621b8a144cac17e8 /src | |
| parent | 849bdebd1336872dda37d0eb3a87aa21b18402fb (diff) | |
added proper multi-monitor support.
Diffstat (limited to 'src')
| -rw-r--r-- | src/defs.h | 3 | ||||
| -rw-r--r-- | src/parser.c | 57 | ||||
| -rw-r--r-- | src/sxwm.c | 78 |
3 files changed, 77 insertions, 61 deletions
@@ -13,6 +13,7 @@ #define OUT_IN (2 * BORDER_WIDTH) #define MF_MIN 0.05f #define MF_MAX 0.95f +#define MAX_MONITORS 32 #define MAX(a, b) ((a) > (b) ? (a) : (b)) #define MIN(a, b) ((a) < (b) ? (a) : (b)) #define LENGTH(X) (sizeof X / sizeof X[0]) @@ -81,7 +82,7 @@ typedef struct { long border_foc_col; long border_ufoc_col; long border_swap_col; - float master_width; + float master_width[MAX_MONITORS]; int motion_throttle; int resize_master_amt; int snap_distance; diff --git a/src/parser.c b/src/parser.c index 7cc59d1..0d086a2 100644 --- a/src/parser.c +++ b/src/parser.c @@ -143,22 +143,22 @@ int parser(Config *cfg) // check $XDG_CONFIG_HOME/sxwmrc, then $XDG_CONFIG_HOME/sxwm/sxwmrc, then $HOME/.config/sxwmrc const char *xdg_config_home = getenv("XDG_CONFIG_HOME"); - if (xdg_config_home) { - snprintf(path, sizeof path, "%s/sxwmrc", xdg_config_home); - if (access(path, R_OK) == 0) { - goto found; - } - - snprintf(path, sizeof path, "%s/sxwm/sxwmrc", xdg_config_home); - if (access(path, R_OK) == 0) { - goto found; - } - } - - snprintf(path, sizeof path, "%s/.config/sxwmrc", home); - if (access(path, R_OK) == 0) { - goto found; - } + if (xdg_config_home) { + snprintf(path, sizeof path, "%s/sxwmrc", xdg_config_home); + if (access(path, R_OK) == 0) { + goto found; + } + + snprintf(path, sizeof path, "%s/sxwm/sxwmrc", xdg_config_home); + if (access(path, R_OK) == 0) { + goto found; + } + } + + snprintf(path, sizeof path, "%s/.config/sxwmrc", home); + if (access(path, R_OK) == 0) { + goto found; + } snprintf(path, sizeof path, "/usr/local/share/sxwmrc"); if (access(path, R_OK) == 0) { @@ -166,11 +166,11 @@ int parser(Config *cfg) } found: - FILE *f = fopen(path, "r"); - if (!f) { - fprintf(stderr, "sxwmrc: cannot open %s\n", path); - return -1; - } + FILE *f = fopen(path, "r"); + if (!f) { + fprintf(stderr, "sxwmrc: cannot open %s\n", path); + return -1; + } char line[512]; int lineno = 0; @@ -221,7 +221,10 @@ found: cfg->border_swap_col = parse_col(rest); } else if (!strcmp(key, "master_width")) { - cfg->master_width = atoi(rest) / 100.0f; + float mf = atoi(rest) / 100.0f; + for (int i = 0; i < MAX_MONITORS; i++) { + cfg->master_width[i] = mf; + } } else if (!strcmp(key, "motion_throttle")) { cfg->motion_throttle = atoi(rest); @@ -234,14 +237,14 @@ found: } else if (!strcmp(key, "should_float")) { // should_float: binary --arg,binary2 parameter --arg,binary3 - + if (should_floatn >= 256) { fprintf(stderr, "sxwmrc:%d: too many should_float entries\n", lineno); continue; } char *win = strip(rest); - + cfg->should_float[should_floatn] = malloc(256 * sizeof(char *)); char *comma_ptr, *space_ptr; @@ -262,7 +265,6 @@ found: char *argv = strtok_r(comma, " ", &space_ptr); int i = 0; - while (argv) { printf("argv: %s\n", argv); cfg->should_float[should_floatn][i] = strdup(argv); @@ -272,15 +274,14 @@ found: should_floatn++; cfg->should_float[should_floatn] = malloc(256 * sizeof(char *)); - - } else { + } + else { fprintf(stderr, "sxwmrc:%d: too many should_float entries\n", lineno); break; } comma = strtok_r(NULL, ",", &comma_ptr); } - should_floatn++; } else if (!strcmp(key, "call") || !strcmp(key, "bind")) { @@ -170,24 +170,25 @@ Client *add_client(Window w, int ws) c->w = wa.width; c->h = wa.height; - if (focused) { - c->mon = focused->mon; - } - else { - /* need better way to determine mon */ - int cx = c->x + c->w / 2, cy = c->y + c->h / 2; - c->mon = 0; + /* set monitor based on pointer location */ + Window root_ret, child_ret; + int root_x, root_y, win_x, win_y; + unsigned int mask; + int pointer_mon = 0; + + if (XQueryPointer(dpy, root, &root_ret, &child_ret, &root_x, &root_y, &win_x, &win_y, &mask)) { for (int i = 0; i < monsn; i++) { - if (cx >= mons[i].x && cx < mons[i].x + mons[i].w && cy >= mons[i].y && cy < mons[i].y + mons[i].h) { - c->mon = i; + if (root_x >= mons[i].x && root_x < mons[i].x + mons[i].w && root_y >= mons[i].y && + root_y < mons[i].y + mons[i].h) { + pointer_mon = i; break; } } } + c->mon = pointer_mon; c->fixed = False; c->floating = False; - c->fullscreen = False; if (global_floating) { @@ -594,7 +595,8 @@ void hdl_keypress(XEvent *xev) spawn(b->action.cmd); for (int j = 0; j < 256; j++) { Bool valid = False; - for (int k = 0; user_config.should_float[j] && user_config.should_float[j][k] && b->action.cmd[k]; k++) { + for (int k = 0; + user_config.should_float[j] && user_config.should_float[j][k] && b->action.cmd[k]; k++) { if (!strcmp(b->action.cmd[k], user_config.should_float[j][k])) { valid = True; break; @@ -724,7 +726,7 @@ void hdl_map_req(XEvent *xev) return; } - /* ad client to list */ + /* add client to list */ Client *c = add_client(w, current_ws); if (!c) return; @@ -753,8 +755,7 @@ void hdl_map_req(XEvent *xev) c->w = wa.width; c->h = wa.height; - XConfigureWindow( - dpy, c->win, CWX | CWY | CWWidth | CWHeight, + XConfigureWindow(dpy, c->win, CWX | CWY | CWWidth | CWHeight, &(XWindowChanges){.x = c->x, .y = c->y, .width = c->w, .height = c->h}); } @@ -1011,7 +1012,9 @@ void init_defaults(void) default_config.border_foc_col = parse_col("#c0cbff"); default_config.border_ufoc_col = parse_col("#555555"); default_config.border_swap_col = parse_col("#fff4c0"); - default_config.master_width = 50 / 100.0f; + for (int i = 0; i < MAX_MONITORS; i++) + default_config.master_width[i] = 50 / 100.0f; + default_config.motion_throttle = 60; default_config.resize_master_amt = 5; default_config.snap_distance = 5; @@ -1131,6 +1134,7 @@ long parse_col(const char *hex) } /* return col.pixel |= 0xff << 24; */ + /* This is a fix for picom making the borders transparent. DANGEROUS */ return col.pixel; } @@ -1186,8 +1190,12 @@ void reload_config(void) void resize_master_add(void) { - if (user_config.master_width < MF_MAX - 0.001f) { - user_config.master_width += ((float)user_config.resize_master_amt / 100); + /* pick the monitor of the focused window (or 0 if none) */ + int m = focused ? focused->mon : 0; + float *mw = &user_config.master_width[m]; + + if (*mw < MF_MAX - 0.001f) { + *mw += ((float)user_config.resize_master_amt / 100); } tile(); update_borders(); @@ -1195,8 +1203,12 @@ void resize_master_add(void) void resize_master_sub(void) { - if (user_config.master_width > MF_MIN + 0.001f) { - user_config.master_width -= ((float)user_config.resize_master_amt / 100); + /* pick the monitor of the focused window (or 0 if none) */ + int m = focused ? focused->mon : 0; + float *mw = &user_config.master_width[m]; + + if (*mw > MF_MIN + 0.001f) { + *mw -= ((float)user_config.resize_master_amt / 100); } tile(); update_borders(); @@ -1310,7 +1322,7 @@ void setup(void) evtable[UnmapNotify] = hdl_unmap_ntf; scan_existing_windows(); - signal(SIGCHLD, SIG_IGN); /* Prevent child processes from becoming zombies */ + signal(SIGCHLD, SIG_IGN); /* prevent child processes from becoming zombies */ } void setup_atoms(void) @@ -1457,7 +1469,6 @@ void tile(void) for (Client *c = head; c; c = c->next) { if (!c->floating) { - c->mon = get_monitor_for(c); if (!c->fullscreen) { total_tiled_count++; } @@ -1511,7 +1522,7 @@ void tile(void) if (tile_h < 1) tile_h = 1; - float mfact = user_config.master_width; + float mfact = user_config.master_width[m]; if (mfact < MF_MIN) mfact = MF_MIN; if (mfact > MF_MAX) @@ -1585,22 +1596,21 @@ void toggle_floating(void) focused->h = wa.height; XConfigureWindow( - dpy, focused->win, - CWX | CWY | CWWidth | CWHeight, - &(XWindowChanges){ - .x = focused->x, - .y = focused->y, - .width = focused->w, - .height = focused->h - } - ); + dpy, focused->win, CWX | CWY | CWWidth | CWHeight, + &(XWindowChanges){.x = focused->x, .y = focused->y, .width = focused->w, .height = focused->h}); } } + else { + focused->mon = get_monitor_for(focused); + } + if (!focused->floating) { + focused->mon = get_monitor_for(focused); + } tile(); update_borders(); - /* Raise and refocus floating window */ + /* raise and refocus floating window */ if (focused->floating) { XRaiseWindow(dpy, focused->win); XSetInputFocus(dpy, focused->win, RevertToPointerRoot, CurrentTime); @@ -1671,6 +1681,10 @@ void toggle_fullscreen(void) else { XMoveResizeWindow(dpy, focused->win, focused->orig_x, focused->orig_y, focused->orig_w, focused->orig_h); XSetWindowBorderWidth(dpy, focused->win, user_config.border_width); + + if (!focused->floating) { + focused->mon = get_monitor_for(focused); + } tile(); update_borders(); } |
