sites

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

index.md (10796B)


      1 Custom functions in config.h
      2 ============================
      3 You don't need to write complex patches to config dwm, some custom functions
      4 and sensible key and button definitions in config.h let you turn dwm into
      5 whatever you want without messing with dwm.c.
      6 
      7 Example of config.h
      8 -------------------
      9 This example is for people who prefer to control dwm with the mouse (for dwm
     10 5.1):
     11 
     12 	/* See LICENSE file for copyright and license details. */
     13 	
     14 	/* appearance */
     15 	static const char font[]            = "-*-terminus-bold-r-normal-*-14-*-*-*-*-*-*-*";
     16 	static const char normbordercolor[] = "#cccccc";
     17 	static const char normbgcolor[]     = "#eeeeee";
     18 	static const char normfgcolor[]     = "#000000";
     19 	static const char selbordercolor[]  = "#0066ff";
     20 	static const char selbgcolor[]      = "#eeeeee";
     21 	static const char selfgcolor[]      = "#0066ff";
     22 	static unsigned int borderpx        = 3;        /* border pixel of windows */
     23 	static unsigned int snap            = 32;       /* snap pixel */
     24 	static Bool showbar                 = True;     /* False means no bar */
     25 	static Bool topbar                  = True;     /* False means bottom bar */
     26 	static Bool readin                  = True;     /* False means do not read stdin */
     27 	
     28 	/* tagging */
     29 	const char tags[][MAXTAGLEN] = { "1", "2", "3", "4", "5", "w" };
     30 	
     31 	static Rule rules[] = {
     32 		/* class      instance    title       tags mask     isfloating   monitor */
     33 		{ "acme",      NULL,       NULL,       1 << 2,       False,       -1 },
     34 		{ "Acroread",  NULL,       NULL,       0,            True,        -1 },
     35 		{ "Gimp",      NULL,       NULL,       0,            True,        -1 },
     36 		{ "GQview",    NULL,       NULL,       0,            True,        -1 },
     37 		{ "MPlayer",   NULL,       NULL,       0,            True,        -1 },
     38 		{ "Navigator", NULL,       NULL,       1 << 5,       False,       -1 },
     39 	};
     40 	
     41 	/* layout(s) */
     42 	static float mfact      = 0.65;
     43 	static Bool resizehints = False;     /* False means respect size hints in tiled resizals */
     44 	
     45 	static Layout layouts[] = {
     46 		/* symbol     arrange function */
     47 		{ "[]=",      tile }, /* first entry is default */
     48 		{ "< >",      NULL }, /* no layout function means floating behavior */
     49 		{ "[ ]",      monocle },
     50 	};
     51 	
     52 	/* custom functions declarations */
     53 	static void focusstackf(const Arg *arg);
     54 	static void setltor1(const Arg *arg);
     55 	static void toggletorall(const Arg *arg);
     56 	static void togglevorall(const Arg *arg);
     57 	static void vieworprev(const Arg *arg);
     58 	static void warptosel(const Arg *arg);
     59 	static void zoomf(const Arg *arg);
     60 	
     61 	/* key definitions */
     62 	#define MODKEY Mod1Mask
     63 	#define TAGKEYS(KEY,TAG) \
     64 		{ MODKEY,                       KEY,      vieworprev,     {.ui = 1 << TAG} }, \
     65 		{ MODKEY|ControlMask,           KEY,      togglevorall,   {.ui = 1 << TAG} }, \
     66 		{ MODKEY|ShiftMask,             KEY,      tag,            {.ui = 1 << TAG} }, \
     67 		{ MODKEY|ControlMask|ShiftMask, KEY,      toggletorall,   {.ui = 1 << TAG} },
     68 	
     69 	/* helper for spawning shell commands in the pre dwm-5.0 fashion */
     70 	#define SHCMD(cmd) { .v = (const char*[]){ "/bin/sh", "-c", cmd, NULL } }
     71 	
     72 	/* commands */
     73 	static const char *dmenucmd[] = { "dmenu_run", "-fn", font, "-nb", normbgcolor, "-nf", normfgcolor, "-sb", selbgcolor, "-sf", selfgcolor, NULL };
     74 	static const char *termcmd[]  = { "uxterm", NULL };
     75 	
     76 	static Key keys[] = {
     77 		/* modifier                     key        function        argument */
     78 		{ MODKEY,                       XK_p,      spawn,          {.v = dmenucmd } },
     79 		{ MODKEY|ShiftMask,             XK_Return, spawn,          {.v = termcmd } },
     80 		{ MODKEY,                       XK_b,      togglebar,      {0} },
     81 		{ MODKEY,                       XK_j,      focusstackf,    {.i = +1 } },
     82 		{ MODKEY,                       XK_j,      warptosel,      {0} },
     83 		{ MODKEY,                       XK_k,      focusstackf,    {.i = -1 } },
     84 		{ MODKEY,                       XK_k,      warptosel,      {0} },
     85 		{ MODKEY,                       XK_h,      setmfact,       {.f = -0.05} },
     86 		{ MODKEY,                       XK_l,      setmfact,       {.f = +0.05} },
     87 		{ MODKEY,                       XK_Return, zoomf,          {0} },
     88 		{ MODKEY,                       XK_Return, warptosel,      {0} },
     89 		{ MODKEY,                       XK_Tab,    view,           {0} },
     90 		{ MODKEY|ShiftMask,             XK_c,      killclient,     {0} },
     91 		{ MODKEY,                       XK_space,  setltor1,       {.v = &layouts[0]} },
     92 		{ MODKEY|ShiftMask,             XK_space,  setltor1,       {.v = &layouts[2]} },
     93 		{ MODKEY,                       XK_0,      vieworprev,     {.ui = ~0 } },
     94 		{ MODKEY|ShiftMask,             XK_0,      tag,            {.ui = ~0 } },
     95 		TAGKEYS(                        XK_1,                      0)
     96 		TAGKEYS(                        XK_2,                      1)
     97 		TAGKEYS(                        XK_3,                      2)
     98 		TAGKEYS(                        XK_4,                      3)
     99 		TAGKEYS(                        XK_5,                      4)
    100 		TAGKEYS(                        XK_w,                      5)
    101 		{ MODKEY|ShiftMask,             XK_q,      quit,           {0} },
    102 	};
    103 	
    104 	/* button definitions */
    105 	/* click can ClkTagBar, ClkTagButton,
    106 	 * ClkLtSymbol, ClkStatusText, ClkWinTitle, ClkClientWin, or ClkRootWin */
    107 	static Button buttons[] = {
    108 		/* click                event mask      button          function        argument */
    109 		{ ClkLtSymbol,          0,              Button1,        setltor1,       {.v = &layouts[0]} },
    110 		{ ClkLtSymbol,          0,              Button2,        setmfact,       {.f = 1.65} },
    111 		{ ClkLtSymbol,          0,              Button3,        setltor1,       {.v = &layouts[2]} },
    112 		{ ClkLtSymbol,          0,              Button4,        setmfact,       {.f = +0.05} },
    113 		{ ClkLtSymbol,          0,              Button5,        setmfact,       {.f = -0.05} },
    114 		{ ClkStatusText,        0,              Button2,        spawn,          {.v = termcmd } },
    115 		{ ClkStatusText,        Button3Mask,    Button1,        killclient,     {0} },
    116 		{ ClkWinTitle,          0,              Button1,        warptosel,      {0} },
    117 		{ ClkWinTitle,          0,              Button1,        movemouse,      {0} },
    118 		{ ClkWinTitle,          0,              Button2,        zoomf,          {0} },
    119 		{ ClkWinTitle,          0,              Button3,        resizemouse,    {0} },
    120 		{ ClkWinTitle,          0,              Button4,        focusstackf,    {.i = -1 } },
    121 		{ ClkWinTitle,          0,              Button5,        focusstackf,    {.i = +1 } },
    122 		{ ClkRootWin,           0,              Button1,        warptosel,      {0} },
    123 		{ ClkRootWin,           0,              Button1,        movemouse,      {0} },
    124 		{ ClkRootWin,           0,              Button3,        resizemouse,    {0} },
    125 		{ ClkRootWin,           0,              Button4,        focusstackf,    {.i = -1 } },
    126 		{ ClkRootWin,           0,              Button5,        focusstackf,    {.i = +1 } },
    127 		{ ClkClientWin,         MODKEY,         Button1,        movemouse,      {0} },
    128 		{ ClkClientWin,         MODKEY,         Button2,        zoomf,          {0} },
    129 		{ ClkClientWin,         MODKEY,         Button3,        resizemouse,    {0} },
    130 		{ ClkTagBar,            0,              Button1,        vieworprev,     {0} },
    131 		{ ClkTagBar,            0,              Button3,        togglevorall,   {0} },
    132 		{ ClkTagBar,            0,              Button4,        focusstackf,    {.i = -1 } },
    133 		{ ClkTagBar,            0,              Button5,        focusstackf,    {.i = +1 } },
    134 		{ ClkTagBar,            Button2Mask,    Button1,        tag,            {0} },
    135 		{ ClkTagBar,            Button2Mask,    Button3,        toggletorall,   {0} },
    136 	};
    137 	
    138 	/* custom functions */
    139 	void
    140 	focusstackf(const Arg *arg) {
    141 		Client *c = NULL, *i;
    142 	
    143 		if(!sel)
    144 			return;
    145 		if(lt[sellt]->arrange) {
    146 			if (arg->i > 0) {
    147 				for(c = sel->next; c && (!ISVISIBLE(c) || c->isfloating != sel->isfloating); c = c->next);
    148 				if(!c)
    149 					for(c = clients; c && (!ISVISIBLE(c) || c->isfloating == sel->isfloating); c = c->next);
    150 			}
    151 			else {
    152 				for(i = clients; i != sel; i = i->next)
    153 					if(ISVISIBLE(i) && i->isfloating == sel->isfloating)
    154 						c = i;
    155 				if(!c)
    156 					for(i =  sel; i; i = i->next)
    157 						if(ISVISIBLE(i) && i->isfloating != sel->isfloating)
    158 							c = i;
    159 			}
    160 		}
    161 		if(c) {
    162 			focus(c);
    163 			restack();
    164 		}
    165 		else
    166 			focusstack(arg);
    167 	}
    168 	
    169 	void
    170 	setltor1(const Arg *arg) {
    171 		Arg a = {.v = &layouts[1]};
    172 	
    173 		setlayout((lt[sellt] == arg->v) ? &a : arg);
    174 	}
    175 	
    176 	void
    177 	toggletorall(const Arg *arg) {
    178 		Arg a;
    179 	
    180 		if(sel && ((arg->ui & TAGMASK) == sel->tags)) {
    181 			a.ui = ~0;
    182 			tag(&a);
    183 		}
    184 		else
    185 			toggletag(arg);
    186 	}
    187 	
    188 	void
    189 	togglevorall(const Arg *arg) {
    190 		Arg a;
    191 	
    192 		if(sel && ((arg->ui & TAGMASK) == tagset[seltags])) {
    193 			a.ui = ~0;
    194 			view(&a);
    195 		}
    196 		else
    197 			toggleview(arg);
    198 	}
    199 	
    200 	void
    201 	vieworprev(const Arg *arg) {
    202 		Arg a = {0};
    203 	
    204 		view(((arg->ui & TAGMASK) == tagset[seltags]) ? &a : arg);
    205 	}
    206 	
    207 	void
    208 	warptosel(const Arg *arg) {
    209 		XEvent ev;
    210 	
    211 		if(sel)
    212 			XWarpPointer(dpy, None, sel->win, 0, 0, 0, 0, 0, 0);
    213 		XSync(dpy, False);
    214 		while(XCheckMaskEvent(dpy, EnterWindowMask, &ev));
    215 	}
    216 	
    217 	void
    218 	zoomf(const Arg *arg) {
    219 		if(sel && (lt[sellt]->arrange != tile || sel->isfloating)) 
    220 			togglefloating(NULL);
    221 		else
    222 			zoom(NULL);
    223 	}
    224 
    225 Usage of the above configuration
    226 --------------------------------
    227 In case you want to try this configuration there are some differences with the
    228 default dwm config to be taken into account. Mouse actions will be explained
    229 later, keys have similar behaviour. There are other small changes, but the
    230 config.h file should be pretty straightforward.
    231 
    232 ### Tagging
    233 
    234 In the tag buttons:
    235 
    236 * B1: view a tag, trying to view the selected tagset will result in a change to
    237   the previous one.
    238 * B3: toggle a tag, trying to toggle the last selected tag will result in
    239   viewing all tags.
    240 * B2+B1: assign tag to the sel client.
    241 * B2+B3: toggle tag for the sel client, trying to toggle the last tag will
    242   result in assigning all tags.
    243 
    244 ### Layouts
    245 
    246 In the layout symbol:
    247 
    248 * B1: toggle between tiled and floating layout.
    249 * B3: toggle between monocle and floating layout.
    250 * Wheel: set master factor (B2 to go back to the default value).
    251 
    252 ### Focusing/Moving/Resizing
    253 
    254 in the status bar, the root window, or the selected window (with Mod pressed)
    255 
    256 * Wheel to focus prev/next client. Floating clients will just be focused after
    257   the tiled ones.
    258 * B1 to move (the pointer will be wrapped to the upper-left corner if
    259   necessary).
    260 * B3 to resize (the pointer will be wrapped to the bottom-right corner).
    261 * B2 to zoom or toggle floating status if zooming is not possible.
    262 
    263 ### Closing windows
    264 
    265 * B3+B1 in the status message.
    266 
    267 Author
    268 ------
    269 * [Jesus Galan (yiyus)](mailto:yiyu dot jgl at gmail>) (vie ago 22 19:53:32 CEST 2008)