aewl
changeset 0:491f34c11291
initial import
author | Anselm R. Garbe <garbeam@wmii.de> |
---|---|
date | Mon, 10 Jul 2006 16:38:18 +0200 |
parents | |
children | f10194d4b76d |
files | LICENSE Makefile README config.mk gridwm.1 wm.c wm.h |
diffstat | 7 files changed, 450 insertions(+), 0 deletions(-) [+] |
line diff
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/LICENSE Mon Jul 10 16:38:18 2006 +0200 1.3 @@ -0,0 +1,21 @@ 1.4 +MIT/X Consortium License 1.5 + 1.6 +(C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> 1.7 + 1.8 +Permission is hereby granted, free of charge, to any person obtaining a 1.9 +copy of this software and associated documentation files (the "Software"), 1.10 +to deal in the Software without restriction, including without limitation 1.11 +the rights to use, copy, modify, merge, publish, distribute, sublicense, 1.12 +and/or sell copies of the Software, and to permit persons to whom the 1.13 +Software is furnished to do so, subject to the following conditions: 1.14 + 1.15 +The above copyright notice and this permission notice shall be included in 1.16 +all copies or substantial portions of the Software. 1.17 + 1.18 +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1.19 +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 1.20 +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 1.21 +THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 1.22 +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 1.23 +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 1.24 +DEALINGS IN THE SOFTWARE.
2.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 2.2 +++ b/Makefile Mon Jul 10 16:38:18 2006 +0200 2.3 @@ -0,0 +1,23 @@ 2.4 +# gridwm - grid window manager 2.5 +# (C)opyright MMVI Anselm R. Garbe 2.6 + 2.7 +include config.mk 2.8 + 2.9 +SRC = wm.c 2.10 +OBJ = ${SRC:.c=.o} 2.11 + 2.12 +all: gridwm 2.13 + @echo finished 2.14 + 2.15 +.c.o: 2.16 + @echo CC $< 2.17 + @${CC} -c ${CFLAGS} $< 2.18 + 2.19 +${OBJ}: wm.h 2.20 + 2.21 +gridwm: ${OBJ} 2.22 + @echo LD $@ 2.23 + @${CC} -o $@ ${OBJ} ${X11LDFLAGS} 2.24 + 2.25 +clean: 2.26 + rm -f gridwm *.o
3.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 3.2 +++ b/README Mon Jul 10 16:38:18 2006 +0200 3.3 @@ -0,0 +1,40 @@ 3.4 +gridwm 3.5 +------ 3.6 + 3.7 +gridwm is an automatic X11 window manager which arranges all windows in a grid. 3.8 + 3.9 + 3.10 +Requirements 3.11 +------------ 3.12 +In order to build gridwm you need the Xlib header files. 3.13 + 3.14 + 3.15 +Installation 3.16 +------------ 3.17 +Edit config.mk to match your local setup. gridwm is installed into 3.18 +the /usr/local namespace by default. 3.19 + 3.20 +Afterwards enter the following command to build and install gridwm (if 3.21 +necessary as root): 3.22 + 3.23 + make clean install 3.24 + 3.25 + 3.26 +Running gridwm 3.27 +-------------- 3.28 +Add the following line to your .xinitrc to start gridwm using startx: 3.29 + 3.30 + exec gridwm 3.31 + 3.32 +In order to connect gridwm to a specific display, make sure that 3.33 +the DISPLAY environment variable is set correctly, e.g.: 3.34 + 3.35 + DISPLAY=foo.bar:1 exec wmii 3.36 + 3.37 +This will start gridwm on display :1 of the host foo.bar. 3.38 + 3.39 + 3.40 +Configuration 3.41 +------------- 3.42 +The configuration of gridwm is done by customizing the config.h 3.43 +source file.
4.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 4.2 +++ b/config.mk Mon Jul 10 16:38:18 2006 +0200 4.3 @@ -0,0 +1,29 @@ 4.4 +# Customize to fit your system 4.5 + 4.6 +# paths 4.7 +PREFIX = /usr/local 4.8 +CONFPREFIX = ${PREFIX}/etc 4.9 +MANPREFIX = ${PREFIX}/share/man 4.10 + 4.11 +X11INC = /usr/X11R6/include 4.12 +X11LIB = /usr/X11R6/lib 4.13 + 4.14 +VERSION = 0.0 4.15 + 4.16 +# includes and libs 4.17 +LIBS = -L${PREFIX}/lib -L/usr/lib -lc 4.18 +X11LIBS = -L${X11LIB} -lX11 4.19 + 4.20 +# Linux/BSD 4.21 +CFLAGS = -g -Wall -I. -I${PREFIX}/include -I/usr/include -I${X11INC} \ 4.22 + -DVERSION=\"${VERSION}\" 4.23 +LDFLAGS = -g ${LIBS} 4.24 +X11LDFLAGS = ${LDFLAGS} ${X11LIBS} 4.25 + 4.26 +# Solaris 4.27 +#CFLAGS = -fast -xtarget=ultra ${INCLUDES} -DVERSION=\"${VERSION}\" 4.28 +#LIBS += -lnsl -lsocket 4.29 + 4.30 +AR = ar cr 4.31 +CC = cc 4.32 +RANLIB = ranlib
5.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 5.2 +++ b/gridwm.1 Mon Jul 10 16:38:18 2006 +0200 5.3 @@ -0,0 +1,16 @@ 5.4 +.TH GRIDWM 1 gridwm-0.0 5.5 +.SH NAME 5.6 +gridwm \- grid window manager 5.7 +.SH SYNOPSIS 5.8 +.B gridwm 5.9 +.RB [ \-v ] 5.10 +.SH DESCRIPTION 5.11 +.SS Overview 5.12 +.B gridwm 5.13 +is an automatic window manager for X11. 5.14 +.SS Options 5.15 +.TP 5.16 +.B \-v 5.17 +prints version information to stdout, then exits. 5.18 +.SH SEE ALSO 5.19 +.BR gridmenu (1)
6.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 6.2 +++ b/wm.c Mon Jul 10 16:38:18 2006 +0200 6.3 @@ -0,0 +1,264 @@ 6.4 +/* 6.5 + * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> 6.6 + * See LICENSE file for license details. 6.7 + */ 6.8 + 6.9 +#include <stdarg.h> 6.10 +#include <stdio.h> 6.11 +#include <stdlib.h> 6.12 + 6.13 +#include <X11/cursorfont.h> 6.14 +#include <X11/Xatom.h> 6.15 +#include <X11/Xproto.h> 6.16 + 6.17 +#include "wm.h" 6.18 + 6.19 +Display *dpy; 6.20 +Window root; 6.21 +XRectangle rect; 6.22 +int screen, sel_screen; 6.23 +Atom wm_atom[WMLast]; 6.24 +Atom net_atom[NetLast]; 6.25 +Cursor cursor[CurLast]; 6.26 +unsigned int kmask, numlock_mask; 6.27 +Pixmap pmap; 6.28 + 6.29 +enum { WM_PROTOCOL_DELWIN = 1 }; 6.30 + 6.31 +static Bool other_wm_running; 6.32 +static int (*x_error_handler) (Display *, XErrorEvent *); 6.33 +static char version[] = "gridwm - " VERSION ", (C)opyright MMVI Anselm R. Garbe\n"; 6.34 + 6.35 +static void 6.36 +usage() 6.37 +{ 6.38 + fputs("usage: gridwm [-v]\n", stderr); 6.39 + exit(1); 6.40 +} 6.41 + 6.42 +void 6.43 +error(char *errstr, ...) { 6.44 + va_list ap; 6.45 + va_start(ap, errstr); 6.46 + vfprintf(stderr, errstr, ap); 6.47 + va_end(ap); 6.48 + exit(1); 6.49 +} 6.50 + 6.51 +static void 6.52 +scan_wins() 6.53 +{ 6.54 + unsigned int i, num; 6.55 + Window *wins; 6.56 + XWindowAttributes wa; 6.57 + Window d1, d2; 6.58 + 6.59 + if(XQueryTree(dpy, root, &d1, &d2, &wins, &num)) { 6.60 + for(i = 0; i < num; i++) { 6.61 + if(!XGetWindowAttributes(dpy, wins[i], &wa)) 6.62 + continue; 6.63 + if(wa.override_redirect || XGetTransientForHint(dpy, wins[i], &d1)) 6.64 + continue; 6.65 + if(wa.map_state == IsViewable) 6.66 + /*manage*/; 6.67 + } 6.68 + } 6.69 + if(wins) 6.70 + XFree(wins); 6.71 +} 6.72 + 6.73 +static int 6.74 +win_property(Window w, Atom a, Atom t, long l, unsigned char **prop) 6.75 +{ 6.76 + Atom real; 6.77 + int format; 6.78 + unsigned long res, extra; 6.79 + int status; 6.80 + 6.81 + status = XGetWindowProperty(dpy, w, a, 0L, l, False, t, &real, &format, 6.82 + &res, &extra, prop); 6.83 + 6.84 + if(status != Success || *prop == 0) { 6.85 + return 0; 6.86 + } 6.87 + if(res == 0) { 6.88 + free((void *) *prop); 6.89 + } 6.90 + return res; 6.91 +} 6.92 + 6.93 +int 6.94 +win_proto(Window w) 6.95 +{ 6.96 + Atom *protocols; 6.97 + long res; 6.98 + int protos = 0; 6.99 + int i; 6.100 + 6.101 + res = win_property(w, wm_atom[WMProtocols], XA_ATOM, 20L, 6.102 + ((unsigned char **) &protocols)); 6.103 + if(res <= 0) { 6.104 + return protos; 6.105 + } 6.106 + for(i = 0; i < res; i++) { 6.107 + if(protocols[i] == wm_atom[WMDelete]) 6.108 + protos |= WM_PROTOCOL_DELWIN; 6.109 + } 6.110 + free((char *) protocols); 6.111 + return protos; 6.112 +} 6.113 + 6.114 +/* 6.115 + * There's no way to check accesses to destroyed windows, thus 6.116 + * those cases are ignored (especially on UnmapNotify's). 6.117 + * Other types of errors call Xlib's default error handler, which 6.118 + * calls exit(). 6.119 + */ 6.120 +static int 6.121 +error_handler(Display *dpy, XErrorEvent *error) 6.122 +{ 6.123 + if(error->error_code == BadWindow 6.124 + || (error->request_code == X_SetInputFocus 6.125 + && error->error_code == BadMatch) 6.126 + || (error->request_code == X_PolyText8 6.127 + && error->error_code == BadDrawable) 6.128 + || (error->request_code == X_PolyFillRectangle 6.129 + && error->error_code == BadDrawable) 6.130 + || (error->request_code == X_PolySegment 6.131 + && error->error_code == BadDrawable) 6.132 + || (error->request_code == X_ConfigureWindow 6.133 + && error->error_code == BadMatch) 6.134 + || (error->request_code == X_GrabKey 6.135 + && error->error_code == BadAccess)) 6.136 + return 0; 6.137 + fprintf(stderr, "gridwm: fatal error: request code=%d, error code=%d\n", 6.138 + error->request_code, error->error_code); 6.139 + return x_error_handler(dpy, error); /* may call exit() */ 6.140 +} 6.141 + 6.142 +/* 6.143 + * Startup Error handler to check if another window manager 6.144 + * is already running. 6.145 + */ 6.146 +static int 6.147 +startup_error_handler(Display *dpy, XErrorEvent *error) 6.148 +{ 6.149 + other_wm_running = True; 6.150 + return -1; 6.151 +} 6.152 + 6.153 +static void 6.154 +init_lock_keys() 6.155 +{ 6.156 + XModifierKeymap *modmap; 6.157 + KeyCode numlock; 6.158 + int i; 6.159 + static int masks[] = { 6.160 + ShiftMask, LockMask, ControlMask, Mod1Mask, 6.161 + Mod2Mask, Mod3Mask, Mod4Mask, Mod5Mask 6.162 + }; 6.163 + 6.164 + numlock_mask = 0; 6.165 + modmap = XGetModifierMapping(dpy); 6.166 + numlock = XKeysymToKeycode(dpy, XStringToKeysym("Num_Lock")); 6.167 + 6.168 + if(modmap && modmap->max_keypermod > 0) { 6.169 + int max = (sizeof(masks) / sizeof(int)) * modmap->max_keypermod; 6.170 + for(i = 0; i < max; i++) 6.171 + if(numlock && (modmap->modifiermap[i] == numlock)) 6.172 + numlock_mask = masks[i / modmap->max_keypermod]; 6.173 + } 6.174 + XFreeModifiermap(modmap); 6.175 + 6.176 + kmask = 255 & ~(numlock_mask | LockMask); 6.177 +} 6.178 + 6.179 +static void 6.180 +cleanup() 6.181 +{ 6.182 + /* 6.183 + Client *c; 6.184 + for(c=client; c; c=c->next) 6.185 + reparent_client(c, root, c->sel->rect.x, c->sel->rect.y); 6.186 + XSetInputFocus(dpy, PointerRoot, RevertToPointerRoot, CurrentTime); 6.187 + */ 6.188 +} 6.189 + 6.190 +int 6.191 +main(int argc, char *argv[]) 6.192 +{ 6.193 + int i; 6.194 + XSetWindowAttributes wa; 6.195 + unsigned int mask; 6.196 + Window w; 6.197 + 6.198 + /* command line args */ 6.199 + for(i = 1; (i < argc) && (argv[i][0] == '-'); i++) { 6.200 + switch (argv[i][1]) { 6.201 + case 'v': 6.202 + fprintf(stdout, "%s", version); 6.203 + exit(0); 6.204 + break; 6.205 + default: 6.206 + usage(); 6.207 + break; 6.208 + } 6.209 + } 6.210 + 6.211 + dpy = XOpenDisplay(0); 6.212 + if(!dpy) 6.213 + error("gridwm: cannot connect X server\n"); 6.214 + 6.215 + screen = DefaultScreen(dpy); 6.216 + root = RootWindow(dpy, screen); 6.217 + 6.218 + /* check if another WM is already running */ 6.219 + other_wm_running = False; 6.220 + XSetErrorHandler(startup_error_handler); 6.221 + /* this causes an error if some other WM is running */ 6.222 + XSelectInput(dpy, root, SubstructureRedirectMask); 6.223 + XSync(dpy, False); 6.224 + 6.225 + if(other_wm_running) 6.226 + error("gridwm: another window manager is already running\n"); 6.227 + 6.228 + rect.x = rect.y = 0; 6.229 + rect.width = DisplayWidth(dpy, screen); 6.230 + rect.height = DisplayHeight(dpy, screen); 6.231 + sel_screen = XQueryPointer(dpy, root, &w, &w, &i, &i, &i, &i, &mask); 6.232 + 6.233 + XSetErrorHandler(0); 6.234 + x_error_handler = XSetErrorHandler(error_handler); 6.235 + 6.236 + /* init atoms */ 6.237 + wm_atom[WMState] = XInternAtom(dpy, "WM_STATE", False); 6.238 + wm_atom[WMProtocols] = XInternAtom(dpy, "WM_PROTOCOLS", False); 6.239 + wm_atom[WMDelete] = XInternAtom(dpy, "WM_DELETE_WINDOW", False); 6.240 + net_atom[NetSupported] = XInternAtom(dpy, "_NET_SUPPORTED", False); 6.241 + net_atom[NetWMName] = XInternAtom(dpy, "_NET_WM_NAME", False); 6.242 + 6.243 + XChangeProperty(dpy, root, net_atom[NetSupported], XA_ATOM, 32, 6.244 + PropModeReplace, (unsigned char *) net_atom, NetLast); 6.245 + 6.246 + 6.247 + /* init cursors */ 6.248 + cursor[CurNormal] = XCreateFontCursor(dpy, XC_left_ptr); 6.249 + cursor[CurResize] = XCreateFontCursor(dpy, XC_sizing); 6.250 + cursor[CurMove] = XCreateFontCursor(dpy, XC_fleur); 6.251 + 6.252 + init_lock_keys(); 6.253 + 6.254 + pmap = XCreatePixmap(dpy, root, rect.width, rect.height, 6.255 + DefaultDepth(dpy, screen)); 6.256 + 6.257 + wa.event_mask = SubstructureRedirectMask | EnterWindowMask | LeaveWindowMask; 6.258 + wa.cursor = cursor[CurNormal]; 6.259 + XChangeWindowAttributes(dpy, root, CWEventMask | CWCursor, &wa); 6.260 + 6.261 + scan_wins(); 6.262 + 6.263 + cleanup(); 6.264 + XCloseDisplay(dpy); 6.265 + 6.266 + return 0; 6.267 +}
7.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 7.2 +++ b/wm.h Mon Jul 10 16:38:18 2006 +0200 7.3 @@ -0,0 +1,57 @@ 7.4 +/* 7.5 + * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> 7.6 + * See LICENSE file for license details. 7.7 + */ 7.8 + 7.9 +#include <X11/Xlib.h> 7.10 +#include <X11/Xutil.h> 7.11 + 7.12 +/* WM atoms */ 7.13 +enum { WMState, WMProtocols, WMDelete, WMLast }; 7.14 + 7.15 +/* NET atoms */ 7.16 +enum { NetSupported, NetWMName, NetLast }; 7.17 + 7.18 +/* Cursor */ 7.19 +enum { CurNormal, CurResize, CurMove, CurInput, CurLast }; 7.20 + 7.21 +/* Rects */ 7.22 +enum { RFloat, RGrid, RLast }; 7.23 + 7.24 +typedef struct Client Client; 7.25 +typedef struct Tag Tag; 7.26 + 7.27 +struct Client { 7.28 + Tag *tag; 7.29 + char name[256]; 7.30 + int proto; 7.31 + Window win; 7.32 + Window trans; 7.33 + Window title; 7.34 + GC gc; 7.35 + XSizeHints size; 7.36 + XRectangle r[RLast]; 7.37 + Client *next; 7.38 + Client *tnext; 7.39 + Client *tprev; 7.40 +}; 7.41 + 7.42 +struct Tag { 7.43 + char name[256]; 7.44 + Client *clients; 7.45 + Client *sel; 7.46 + XRectangle r; 7.47 +}; 7.48 + 7.49 +extern Display *dpy; 7.50 +extern Window root; 7.51 +extern XRectangle rect; 7.52 +extern int screen, sel_screen; 7.53 +extern unsigned int kmask, numlock_mask; 7.54 +extern Atom wm_atom[WMLast]; 7.55 +extern Atom net_atom[NetLast]; 7.56 +extern Cursor cursor[CurLast]; 7.57 +extern Pixmap pmap; 7.58 + 7.59 +/* wm.c */ 7.60 +extern void error(char *errstr, ...);