sites

public wiki contents of suckless.org
git clone git://git.suckless.org/sites
Log | Files | Refs

dwm-fancybarclickable-6.1.diff (6638B)


      1 diff --git a/config.def.h b/config.def.h
      2 index 875885b..05865bb 100644
      3 --- a/config.def.h
      4 +++ b/config.def.h
      5 @@ -97,6 +97,7 @@ static Button buttons[] = {
      6  	/* click                event mask      button          function        argument */
      7  	{ ClkLtSymbol,          0,              Button1,        setlayout,      {0} },
      8  	{ ClkLtSymbol,          0,              Button3,        setlayout,      {.v = &layouts[2]} },
      9 +	{ ClkWinTitle,          0,              Button1,        focusonclick,   {0} },
     10  	{ ClkWinTitle,          0,              Button2,        zoom,           {0} },
     11  	{ ClkStatusText,        0,              Button2,        spawn,          {.v = termcmd } },
     12  	{ ClkClientWin,         MODKEY,         Button1,        movemouse,      {0} },
     13 diff --git a/dwm.c b/dwm.c
     14 index f896170..cc2a4f2 100644
     15 --- a/dwm.c
     16 +++ b/dwm.c
     17 @@ -129,6 +129,8 @@ struct Monitor {
     18  	Monitor *next;
     19  	Window barwin;
     20  	const Layout *lt[2];
     21 +	int titlebarbegin;
     22 +	int titlebarend;
     23  };
     24  
     25  typedef struct {
     26 @@ -163,9 +165,11 @@ static void detachstack(Client *c);
     27  static Monitor *dirtomon(int dir);
     28  static void drawbar(Monitor *m);
     29  static void drawbars(void);
     30 +static void drawline(int x, int y);
     31  static void enternotify(XEvent *e);
     32  static void expose(XEvent *e);
     33  static void focus(Client *c);
     34 +static void focusonclick(const Arg *arg);
     35  static void focusin(XEvent *e);
     36  static void focusmon(const Arg *arg);
     37  static void focusstack(const Arg *arg);
     38 @@ -432,10 +436,12 @@ buttonpress(XEvent *e) {
     39  		}
     40  		else if(ev->x < x + blw)
     41  			click = ClkLtSymbol;
     42 -		else if(ev->x > selmon->ww - TEXTW(stext))
     43 +		else if(ev->x > selmon->titlebarend)
     44  			click = ClkStatusText;
     45 -		else
     46 +		else {
     47 +			arg.ui = ev->x;
     48  			click = ClkWinTitle;
     49 +	}
     50  	}
     51  	else if((c = wintoclient(ev->window))) {
     52  		focus(c);
     53 @@ -444,7 +450,7 @@ buttonpress(XEvent *e) {
     54  	for(i = 0; i < LENGTH(buttons); i++)
     55  		if(click == buttons[i].click && buttons[i].func && buttons[i].button == ev->button
     56  		&& CLEANMASK(buttons[i].mask) == CLEANMASK(ev->state))
     57 -			buttons[i].func(click == ClkTagBar && buttons[i].arg.i == 0 ? &arg : &buttons[i].arg);
     58 +			buttons[i].func((click == ClkTagBar || click == ClkWinTitle) && buttons[i].arg.i == 0 ? &arg : &buttons[i].arg);
     59  }
     60  
     61  void
     62 @@ -692,11 +698,14 @@ dirtomon(int dir) {
     63  
     64  void
     65  drawbar(Monitor *m) {
     66 -	int x, xx, w;
     67 -	unsigned int i, occ = 0, urg = 0;
     68 -	Client *c;
     69 +	int x, xx, w, ow, mw = 0, extra, tw, a = 0, s = 0;
     70 +	char posbuf[10];
     71 +	unsigned int i, occ = 0, urg = 0, n = 0;
     72 +	Client *c, *firstvis, *lastvis = NULL;
     73  
     74  	for(c = m->clients; c; c = c->next) {
     75 +	if(ISVISIBLE(c))
     76 +		n++;
     77  		occ |= c->tags;
     78  		if(c->isurgent)
     79  			urg |= c->tags;
     80 @@ -716,32 +725,109 @@ drawbar(Monitor *m) {
     81  	x += w;
     82  	xx = x;
     83  	if(m == selmon) { /* status is only drawn on selected monitor */
     84 -		w = TEXTW(stext);
     85 +	if(m->lt[m->sellt]->arrange == monocle){
     86 +		x = xx;
     87 +		for(c = nexttiled(m->clients), a = 0, s = 0; c; c = nexttiled(c->next), a++) {
     88 +			if(c == m->stack)
     89 +				s = a;
     90 +		}
     91 +		if(!s && a)
     92 +			s = a;
     93 +		snprintf(posbuf, LENGTH(posbuf), "[%d/%d]", s, a);
     94 +		w = TEXTW(posbuf);
     95 +		drw_text(drw, x, 0, w, bh, posbuf, 0);
     96 +		xx = x + w;
     97 +	}
     98 +
     99 +	/* char *buf = stext, *ptr = buf;
    100 +	while (*ptr) {
    101 +		for (i = 0; *ptr < 0; i++, ptr++);
    102 +			w 2+= drw_font_getexts_width(drw->font, buf, i);
    103 +			w += TEXTW(buf);
    104 +			buf=++ptr;
    105 +	} */
    106 +	w = TEXTW(stext);
    107 +
    108  		x = m->ww - w;
    109  		if(x < xx) {
    110  			x = xx;
    111  			w = m->ww - xx;
    112  		}
    113 +	m->titlebarend=x;
    114  		drw_text(drw, x, 0, w, bh, stext, 0);
    115  	}
    116 -	else
    117 +	else {
    118  		x = m->ww;
    119 -	if((w = x - xx) > bh) {
    120 -		x = xx;
    121 -		if(m->sel) {
    122 -			drw_setscheme(drw, m == selmon ? &scheme[SchemeSel] : &scheme[SchemeNorm]);
    123 -			drw_text(drw, x, 0, w, bh, m->sel->name, 0);
    124 -			drw_rect(drw, x, 0, w, bh, m->sel->isfixed, m->sel->isfloating, 0);
    125 -		}
    126 -		else {
    127 +		m->titlebarbegin=x;
    128 +	}
    129 +	for(c = m->clients; c && !ISVISIBLE(c); c = c->next);
    130 +	firstvis = c;
    131 +
    132 +	drw_setscheme(drw, m == selmon ? &scheme[SchemeSel] : &scheme[SchemeNorm]);
    133 +	w = x - xx;
    134 +	x = xx;
    135 +
    136 +	if(n > 0) {
    137 +		mw = w / n;
    138 +		extra = 0;
    139 +		i = 0;
    140 +
    141 +		while(c) {
    142 +			lastvis = c;
    143 +			tw = TEXTW(c->name);
    144 +			if(tw < mw) extra += (mw - tw); else i++;
    145 +			for(c = c->next; c && !ISVISIBLE(c); c = c->next);
    146 +		}
    147 +
    148 +	if(i > 0) mw += extra / i;
    149 +
    150 +	c = firstvis;
    151 +	xx = x;
    152 +	}
    153 +	m->titlebarbegin=x;
    154 +	while(w > bh) {
    155 +		if(c) {
    156 +			ow = w;
    157 +			tw = TEXTW(c->name);
    158 +			w = MIN(ow, tw);
    159 +
    160 +			if(w > mw) w = mw;
    161 +			if(c == lastvis) w = ow;
    162 +
    163 +			drw_text(drw, x, 0, w, bh, c->name, False);
    164 +			if(c != firstvis) drawline(x, 0);
    165 +			drw_rect(drw, x, 0, w, bh, m->sel->isfixed, m->sel->isfloating, True);
    166 +
    167 +			x += w;
    168 +			w = ow - w;
    169 +			for(c = c->next; c && !ISVISIBLE(c); c = c->next);
    170 +		} else {
    171  			drw_setscheme(drw, &scheme[SchemeNorm]);
    172  			drw_text(drw, x, 0, w, bh, NULL, 0);
    173 +			break;
    174  		}
    175  	}
    176 +
    177 +	if(m == selmon && m->sel && ISVISIBLE(m->sel)) {
    178 +		drw_text(drw, x, 0, w, bh, m->sel->name, True);
    179 +		drw_rect(drw, x, 0, w, bh, m->sel->isfixed, m->sel->isfloating, True);
    180 +	}
    181 +
    182  	drw_map(drw, m->barwin, 0, 0, m->ww, bh);
    183  }
    184  
    185  void
    186 +drawline(int x, int y) {
    187 +	XGCValues gcv;
    188 +
    189 +	gcv.foreground = drw->scheme->fg->rgb;
    190 +
    191 +	XChangeGC(dpy, drw->gc, GCForeground, &gcv);
    192 +	XDrawLine(dpy, drw->drawable, drw->gc, x, y, x, y + (drw->font->ascent + drw->font->descent + 2));
    193 +}
    194 +
    195 +void
    196  drawbars(void) {
    197  	Monitor *m;
    198  
    199 @@ -804,6 +890,51 @@ focus(Client *c) {
    200  }
    201  
    202  void
    203 +focusonclick(const Arg *arg) {
    204 +	int x, w, mw = 0, tw, n = 0, i = 0, extra = 0;
    205 +	Monitor *m = selmon;
    206 +	Client *c, *firstvis;
    207 +
    208 +	for(c = m->clients; c && !ISVISIBLE(c); c = c->next);
    209 +	firstvis = c;
    210 +
    211 +	for(c = m->clients; c; c = c->next)
    212 +		if (ISVISIBLE(c))
    213 +			n++;
    214 +
    215 +	if(n > 0) {
    216 +		mw = (m->titlebarend - m->titlebarbegin) / n;
    217 +		c = firstvis;
    218 +		while(c) {
    219 +			tw = TEXTW(c->name);
    220 +			if(tw < mw) extra += (mw - tw); else i++;
    221 +			for(c = c->next; c && !ISVISIBLE(c); c = c->next);
    222 +		}
    223 +		if(i > 0) mw += extra / i;
    224 +	}
    225 +
    226 +	x=m->titlebarbegin;
    227 +
    228 +	c = firstvis;
    229 +	while(x < m->titlebarend) {
    230 +		if(c) {
    231 +			w=MIN(TEXTW(c->name), mw);
    232 +			if (x < arg->i && x+w > arg->i) {
    233 +				focus(c);
    234 +				restack(selmon);
    235 +				break;
    236 +			} else {
    237 +				x+=w;
    238 +			}
    239 +
    240 +			for(c = c->next; c && !ISVISIBLE(c); c = c->next);
    241 +		} else {
    242 +			break;
    243 +		}
    244 +	}
    245 +}
    246 +
    247 +void
    248  focusin(XEvent *e) { /* there are some broken focus acquiring clients */
    249  	XFocusChangeEvent *ev = &e->xfocus;
    250  
    251 @@ -1221,8 +1352,7 @@ propertynotify(XEvent *e) {
    252  		}
    253  		if(ev->atom == XA_WM_NAME || ev->atom == netatom[NetWMName]) {
    254  			updatetitle(c);
    255 -			if(c == c->mon->sel)
    256 -				drawbar(c->mon);
    257 +			drawbar(c->mon);
    258  		}
    259  		if(ev->atom == netatom[NetWMWindowType])
    260  			updatewindowtype(c);