added several other stuff
							parent
							
								
									2de59d0f09
								
							
						
					
					
						commit
						439e15d09f
					
				
							
								
								
									
										4
									
								
								Makefile
								
								
								
								
							
							
						
						
									
										4
									
								
								Makefile
								
								
								
								
							|  | @ -3,11 +3,11 @@ | |||
| 
 | ||||
| include config.mk | ||||
| 
 | ||||
| WMSRC = wm.c draw.c util.c | ||||
| WMSRC = bar.c client.c draw.c event.c util.c wm.c | ||||
| WMOBJ = ${WMSRC:.c=.o} | ||||
| MENSRC = menu.c draw.c util.c | ||||
| MENOBJ = ${MENSRC:.c=.o} | ||||
| MAN = gridwm.1 | ||||
| MAN1 = gridwm.1 gridmenu.1 | ||||
| BIN = gridwm gridmenu      | ||||
| 
 | ||||
| all: config gridwm gridmenu | ||||
|  |  | |||
|  | @ -0,0 +1,18 @@ | |||
| /*
 | ||||
|  * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> | ||||
|  * See LICENSE file for license details. | ||||
|  */ | ||||
| 
 | ||||
| #include "wm.h" | ||||
| 
 | ||||
| void | ||||
| draw_bar() | ||||
| { | ||||
| 	brush.rect = barrect; | ||||
| 	brush.rect.x = brush.rect.y = 0; | ||||
| 	draw(dpy, &brush, False, 0); | ||||
| 
 | ||||
| 	XCopyArea(dpy, brush.drawable, barwin, brush.gc, 0, 0, barrect.width, | ||||
| 			barrect.height, 0, 0); | ||||
| 	XFlush(dpy); | ||||
| } | ||||
|  | @ -0,0 +1,89 @@ | |||
| /*
 | ||||
|  * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> | ||||
|  * See LICENSE file for license details. | ||||
|  */ | ||||
| 
 | ||||
| #include <string.h> | ||||
| #include <X11/Xatom.h> | ||||
| 
 | ||||
| #include "util.h" | ||||
| #include "wm.h" | ||||
| 
 | ||||
| static void | ||||
| update_client_name(Client *c) | ||||
| { | ||||
| 	XTextProperty name; | ||||
| 	int n; | ||||
| 	char **list = 0; | ||||
| 
 | ||||
| 	name.nitems = 0; | ||||
| 	c->name[0] = 0; | ||||
| 	XGetTextProperty(dpy, c->win, &name, net_atom[NetWMName]); | ||||
| 	if(!name.nitems) | ||||
| 		XGetWMName(dpy, c->win, &name); | ||||
| 	if(!name.nitems) | ||||
| 		return; | ||||
| 	if(name.encoding == XA_STRING) | ||||
| 		strncpy(c->name, (char *)name.value, sizeof(c->name)); | ||||
| 	else { | ||||
| 		if(XmbTextPropertyToTextList(dpy, &name, &list, &n) >= Success | ||||
| 				&& n > 0 && *list) | ||||
| 		{ | ||||
| 			strncpy(c->name, *list, sizeof(c->name)); | ||||
| 			XFreeStringList(list); | ||||
| 		} | ||||
| 	} | ||||
| 	XFree(name.value); | ||||
| } | ||||
| 
 | ||||
| Client * | ||||
| create_client(Window w, XWindowAttributes *wa) | ||||
| { | ||||
| 	Client *c; | ||||
| 	XSetWindowAttributes twa; | ||||
| 	long msize; | ||||
| 
 | ||||
| 	c = emallocz(sizeof(Client)); | ||||
| 	c->win = w; | ||||
| 	c->r[RFloat].x = wa->x; | ||||
| 	c->r[RFloat].y = wa->y; | ||||
| 	c->r[RFloat].width = wa->width; | ||||
| 	c->r[RFloat].height = wa->height; | ||||
| 	c->border = wa->border_width; | ||||
| 	XSetWindowBorderWidth(dpy, c->win, 0); | ||||
| 	c->proto = win_proto(c->win); | ||||
| 	XGetTransientForHint(dpy, c->win, &c->trans); | ||||
| 	if(!XGetWMNormalHints(dpy, c->win, &c->size, &msize) || !c->size.flags) | ||||
| 		c->size.flags = PSize; | ||||
| 	c->fixedsize = | ||||
| 		(c->size.flags & PMinSize && c->size.flags & PMaxSize | ||||
| 		 && c->size.min_width == c->size.max_width | ||||
| 		 && c->size.min_height == c->size.max_height); | ||||
| 	XAddToSaveSet(dpy, c->win); | ||||
| 	update_client_name(c); | ||||
| 	twa.override_redirect = 1; | ||||
| 	twa.background_pixmap = ParentRelative; | ||||
| 	twa.event_mask = ExposureMask; | ||||
| 
 | ||||
| 	c->title = XCreateWindow(dpy, root, c->r[RFloat].x, c->r[RFloat].y, | ||||
| 			c->r[RFloat].width, barrect.height, 0, | ||||
| 			DefaultDepth(dpy, screen), CopyFromParent, | ||||
| 			DefaultVisual(dpy, screen), | ||||
| 			CWOverrideRedirect | CWBackPixmap | CWEventMask, &twa); | ||||
| 	XFlush(dpy); | ||||
| 
 | ||||
| #if 0 | ||||
| 	for(t=&client, i=0; *t; t=&(*t)->next, i++); | ||||
| 	c->next = *t; /* *t == nil */ | ||||
| 	*t = c; | ||||
| #endif | ||||
| 	return c; | ||||
| } | ||||
| 
 | ||||
| void | ||||
| manage(Client *c) | ||||
| { | ||||
| 	XMapRaised(dpy, c->win); | ||||
| 	XSetInputFocus(dpy, c->win, RevertToPointerRoot, CurrentTime); | ||||
| 	XFlush(dpy); | ||||
| } | ||||
							
								
								
									
										4
									
								
								config.h
								
								
								
								
							
							
						
						
									
										4
									
								
								config.h
								
								
								
								
							|  | @ -4,6 +4,6 @@ | |||
|  */ | ||||
| 
 | ||||
| #define FONT		"-*-terminus-medium-*-*-*-14-*-*-*-*-*-iso10646-*" | ||||
| #define FGCOLOR		"#000000" | ||||
| #define BGCOLOR		"#ffaa00" | ||||
| #define BGCOLOR		"#000000" | ||||
| #define FGCOLOR		"#ffaa00" | ||||
| #define BORDERCOLOR	"#000000" | ||||
|  |  | |||
							
								
								
									
										6
									
								
								draw.c
								
								
								
								
							
							
						
						
									
										6
									
								
								draw.c
								
								
								
								
							|  | @ -162,3 +162,9 @@ loadfont(Display *dpy, Fnt *font, const char *fontstr) | |||
| 	} | ||||
| 	font->height = font->ascent + font->descent; | ||||
| } | ||||
| 
 | ||||
| unsigned int | ||||
| labelheight(Fnt *font) | ||||
| { | ||||
| 	return font->height + 4; | ||||
| } | ||||
|  |  | |||
							
								
								
									
										1
									
								
								draw.h
								
								
								
								
							
							
						
						
									
										1
									
								
								draw.h
								
								
								
								
							|  | @ -33,3 +33,4 @@ extern void loadcolors(Display *dpy, int screen, Brush *b, | |||
| extern void loadfont(Display *dpy, Fnt *font, const char *fontstr); | ||||
| extern unsigned int textwidth_l(Fnt *font, char *text, unsigned int len); | ||||
| extern unsigned int textwidth(Fnt *font, char *text); | ||||
| extern unsigned int labelheight(Fnt *font); | ||||
|  |  | |||
|  | @ -0,0 +1,264 @@ | |||
| /*
 | ||||
|  * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> | ||||
|  * See LICENSE file for license details. | ||||
|  */ | ||||
| 
 | ||||
| #include <fcntl.h> | ||||
| #include <stdlib.h> | ||||
| #include <string.h> | ||||
| #include <X11/keysym.h> | ||||
| 
 | ||||
| #include "wm.h" | ||||
| 
 | ||||
| /* local functions */ | ||||
| static void configurerequest(XEvent *e); | ||||
| static void destroynotify(XEvent *e); | ||||
| static void enternotify(XEvent *e); | ||||
| static void leavenotify(XEvent *e); | ||||
| static void expose(XEvent *e); | ||||
| static void keypress(XEvent *e); | ||||
| static void keymapnotify(XEvent *e); | ||||
| static void maprequest(XEvent *e); | ||||
| static void propertynotify(XEvent *e); | ||||
| static void unmapnotify(XEvent *e); | ||||
| 
 | ||||
| void (*handler[LASTEvent]) (XEvent *) = { | ||||
| 	[ConfigureRequest] = configurerequest, | ||||
| 	[DestroyNotify] = destroynotify, | ||||
| 	[EnterNotify] = enternotify, | ||||
| 	[LeaveNotify] = leavenotify, | ||||
| 	[Expose] = expose, | ||||
| 	[KeyPress] = keypress, | ||||
| 	[KeymapNotify] = keymapnotify, | ||||
| 	[MapRequest] = maprequest, | ||||
| 	[PropertyNotify] = propertynotify, | ||||
| 	[UnmapNotify] = unmapnotify | ||||
| }; | ||||
| 
 | ||||
| unsigned int | ||||
| flush_masked_events(long even_mask) | ||||
| { | ||||
| 	XEvent ev; | ||||
| 	unsigned int n = 0; | ||||
| 	while(XCheckMaskEvent(dpy, even_mask, &ev)) n++; | ||||
| 	return n; | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| configurerequest(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	XConfigureRequestEvent *ev = &e->xconfigurerequest; | ||||
| 	XWindowChanges wc; | ||||
| 	XRectangle *frect; | ||||
| 	Client *c; | ||||
| 
 | ||||
| 	c = client_of_win(ev->window); | ||||
| 	ev->value_mask &= ~CWSibling; | ||||
| 	if(c) { | ||||
| 		gravitate_client(c, True); | ||||
| 
 | ||||
| 		if(ev->value_mask & CWX) | ||||
| 			c->rect.x = ev->x; | ||||
| 		if(ev->value_mask & CWY) | ||||
| 			c->rect.y = ev->y; | ||||
| 		if(ev->value_mask & CWWidth) | ||||
| 			c->rect.width = ev->width; | ||||
| 		if(ev->value_mask & CWHeight) | ||||
| 			c->rect.height = ev->height; | ||||
| 		if(ev->value_mask & CWBorderWidth) | ||||
| 			c->border = ev->border_width; | ||||
| 
 | ||||
| 		gravitate_client(c, False); | ||||
| 
 | ||||
| 		if(c->frame) { | ||||
| 			if(c->sel->area->floating) | ||||
| 				frect=&c->sel->rect; | ||||
| 			else | ||||
| 				frect=&c->sel->revert; | ||||
| 
 | ||||
| 			if(c->rect.width >= screen->rect.width && c->rect.height >= screen->rect.height) { | ||||
| 				frect->y = wc.y = -height_of_bar(); | ||||
| 				frect->x = wc.x = -def.border; | ||||
| 			} | ||||
| 			else { | ||||
| 				frect->y = wc.y = c->rect.y - height_of_bar(); | ||||
| 				frect->x = wc.x = c->rect.x - def.border; | ||||
| 			} | ||||
| 			frect->width = wc.width = c->rect.width + 2 * def.border; | ||||
| 			frect->height = wc.height = c->rect.height + def.border | ||||
| 				+ height_of_bar(); | ||||
| 			wc.border_width = 1; | ||||
| 			wc.sibling = None; | ||||
| 			wc.stack_mode = ev->detail; | ||||
| 			if(c->sel->area->view != screen->sel) | ||||
| 				wc.x += 2 * screen->rect.width; | ||||
| 			if(c->sel->area->floating) { | ||||
| 				XConfigureWindow(dpy, c->framewin, ev->value_mask, &wc); | ||||
| 				configure_client(c); | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	wc.x = ev->x; | ||||
| 	wc.y = ev->y; | ||||
| 	wc.width = ev->width; | ||||
| 	wc.height = ev->height; | ||||
| 
 | ||||
| 	if(c && c->frame) { | ||||
| 		wc.x = def.border; | ||||
| 		wc.y = height_of_bar(); | ||||
| 		wc.width = c->sel->rect.width - 2 * def.border; | ||||
| 		wc.height = c->sel->rect.height - def.border - height_of_bar(); | ||||
| 	} | ||||
| 
 | ||||
| 	wc.border_width = 0; | ||||
| 	wc.sibling = None; | ||||
| 	wc.stack_mode = Above; | ||||
| 	ev->value_mask &= ~CWStackMode; | ||||
| 	ev->value_mask |= CWBorderWidth; | ||||
| 	XConfigureWindow(dpy, ev->window, ev->value_mask, &wc); | ||||
| 
 | ||||
| 	XFlush(dpy); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| destroynotify(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	Client *c; | ||||
| 	XDestroyWindowEvent *ev = &e->xdestroywindow; | ||||
| 
 | ||||
| 	if((c = client_of_win(ev->window))) | ||||
| 		destroy_client(c); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| enternotify(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	XCrossingEvent *ev = &e->xcrossing; | ||||
| 	Client *c; | ||||
| 
 | ||||
| 	if(ev->mode != NotifyNormal || ev->detail == NotifyInferior) | ||||
| 		return; | ||||
| 
 | ||||
| 	if((c = client_of_win(ev->window))) { | ||||
| 		Frame *f = c->sel; | ||||
| 		Area *a = f->area; | ||||
| 		if(a->mode == Colmax) | ||||
| 			c = a->sel->client; | ||||
| 		focus(c, False); | ||||
| 	} | ||||
| 	else if(ev->window == root) { | ||||
| 		sel_screen = True; | ||||
| 		draw_frames(); | ||||
| 	} | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| leavenotify(XEvent *e) | ||||
| { | ||||
| 	XCrossingEvent *ev = &e->xcrossing; | ||||
| 
 | ||||
| 	if((ev->window == root) && !ev->same_screen) { | ||||
| 		sel_screen = True; | ||||
| 		/*draw_frames();*/ | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| expose(XEvent *e) | ||||
| { | ||||
| 	XExposeEvent *ev = &e->xexpose; | ||||
| 
 | ||||
| 	if(ev->count == 0) { | ||||
| 		if(ev->window == barwin) | ||||
| 			draw_bar(); | ||||
| 	} | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| keypress(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	XKeyEvent *ev = &e->xkey; | ||||
| 	KeySym k = 0; | ||||
| 	char buf[32]; | ||||
| 	int n; | ||||
| 	static Frame *f; | ||||
| 
 | ||||
| 
 | ||||
| 	ev->state &= valid_mask; | ||||
| 	if((f = frame_of_win(ev->window))) { | ||||
| 		buf[0] = 0; | ||||
| 		n = XLookupString(ev, buf, sizeof(buf), &k, 0); | ||||
| 		if(IsFunctionKey(k) || IsKeypadKey(k) || IsMiscFunctionKey(k) | ||||
| 				|| IsPFKey(k) || IsPrivateKeypadKey(k)) | ||||
| 			return; | ||||
| 		buf[n] = 0; | ||||
| 		blitz_kpress_input(&f->tagbar, ev->state, k, buf); | ||||
| 	} | ||||
| 	else | ||||
| 		key(root, ev->state, (KeyCode) ev->keycode); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| keymapnotify(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	update_keys(); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| maprequest(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	XMapRequestEvent *ev = &e->xmaprequest; | ||||
| 	static XWindowAttributes wa; | ||||
| 
 | ||||
| 	if(!XGetWindowAttributes(dpy, ev->window, &wa)) | ||||
| 		return; | ||||
| 
 | ||||
| 	if(wa.override_redirect) { | ||||
| 		XSelectInput(dpy, ev->window, | ||||
| 				(StructureNotifyMask | PropertyChangeMask)); | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	if(!client_of_win(ev->window)) | ||||
| 		manage_client(create_client(ev->window, &wa)); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| propertynotify(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	XPropertyEvent *ev = &e->xproperty; | ||||
| 	Client *c; | ||||
| 
 | ||||
| 	if(ev->state == PropertyDelete) | ||||
| 		return; /* ignore */ | ||||
| 
 | ||||
| 	if((c = client_of_win(ev->window))) | ||||
| 		prop_client(c, ev); | ||||
| #endif | ||||
| } | ||||
| 
 | ||||
| static void | ||||
| unmapnotify(XEvent *e) | ||||
| { | ||||
| #if 0 | ||||
| 	Client *c; | ||||
| 	XUnmapEvent *ev = &e->xunmap; | ||||
| 
 | ||||
| 	if((c = client_of_win(ev->window))) | ||||
| 		destroy_client(c); | ||||
| #endif | ||||
| } | ||||
							
								
								
									
										9
									
								
								menu.c
								
								
								
								
							
							
						
						
									
										9
									
								
								menu.c
								
								
								
								
							|  | @ -53,7 +53,7 @@ static const int seek = 30;		/* 30px */ | |||
| 
 | ||||
| static Brush brush = {0}; | ||||
| 
 | ||||
| static void draw_menu(void); | ||||
| static void draw_menu(); | ||||
| static void kpress(XKeyEvent * e); | ||||
| 
 | ||||
| static char version[] = "gridmenu - " VERSION ", (C)opyright MMVI Anselm R. Garbe\n"; | ||||
|  | @ -397,11 +397,10 @@ main(int argc, char *argv[]) | |||
| 
 | ||||
| 	wa.override_redirect = 1; | ||||
| 	wa.background_pixmap = ParentRelative; | ||||
| 	wa.event_mask = ExposureMask | ButtonPressMask | KeyPressMask | ||||
| 		| SubstructureRedirectMask | SubstructureNotifyMask; | ||||
| 	wa.event_mask = ExposureMask | ButtonPressMask | KeyPressMask; | ||||
| 
 | ||||
| 	rect.width = DisplayWidth(dpy, screen); | ||||
| 	rect.height = brush.font.height + 4; | ||||
| 	rect.height = labelheight(&brush.font); | ||||
| 	rect.y = DisplayHeight(dpy, screen) - rect.height; | ||||
| 	rect.x = 0; | ||||
| 
 | ||||
|  | @ -413,7 +412,7 @@ main(int argc, char *argv[]) | |||
| 	XFlush(dpy); | ||||
| 
 | ||||
| 	/* pixmap */ | ||||
| 	brush.gc = XCreateGC(dpy, win, 0, 0); | ||||
| 	brush.gc = XCreateGC(dpy, root, 0, 0); | ||||
| 	brush.drawable = XCreatePixmap(dpy, win, rect.width, rect.height, | ||||
| 			DefaultDepth(dpy, screen)); | ||||
| 	XFlush(dpy); | ||||
|  |  | |||
							
								
								
									
										23
									
								
								util.c
								
								
								
								
							
							
						
						
									
										23
									
								
								util.c
								
								
								
								
							|  | @ -7,6 +7,11 @@ | |||
| #include <stdio.h> | ||||
| #include <stdlib.h> | ||||
| #include <string.h> | ||||
| #include <sys/types.h> | ||||
| #include <sys/wait.h> | ||||
| #include <unistd.h> | ||||
| 
 | ||||
| #include "util.h" | ||||
| 
 | ||||
| void | ||||
| error(char *errstr, ...) { | ||||
|  | @ -75,3 +80,21 @@ swap(void **p1, void **p2) | |||
| 	*p1 = *p2; | ||||
| 	*p2 = tmp; | ||||
| } | ||||
| 
 | ||||
| void | ||||
| spawn(Display *dpy, const char *shell, const char *cmd) | ||||
| { | ||||
| 	if(!cmd || !shell) | ||||
| 		return; | ||||
| 	if(fork() == 0) { | ||||
| 		if(fork() == 0) { | ||||
| 			if(dpy) | ||||
| 				close(ConnectionNumber(dpy)); | ||||
| 			execl(shell, shell, "-c", cmd, (const char *)0); | ||||
| 			fprintf(stderr, "gridwm: execl %s", shell); | ||||
| 			perror(" failed"); | ||||
| 		} | ||||
| 		exit (0); | ||||
| 	} | ||||
| 	wait(0); | ||||
| } | ||||
|  |  | |||
							
								
								
									
										6
									
								
								util.h
								
								
								
								
							
							
						
						
									
										6
									
								
								util.h
								
								
								
								
							|  | @ -2,6 +2,7 @@ | |||
|  * (C)opyright MMVI Anselm R. Garbe <garbeam at gmail dot com> | ||||
|  * See LICENSE file for license details. | ||||
|  */ | ||||
| #include <X11/Xlib.h> | ||||
| 
 | ||||
| extern void error(char *errstr, ...); | ||||
| extern void *emallocz(unsigned int size); | ||||
|  | @ -12,5 +13,6 @@ extern char *estrdup(const char *str); | |||
| 		if(!(a)) \ | ||||
| 			failed_assert(#a, __FILE__, __LINE__); \ | ||||
| 	} while (0) | ||||
| void failed_assert(char *a, char *file, int line); | ||||
| void swap(void **p1, void **p2); | ||||
| extern void failed_assert(char *a, char *file, int line); | ||||
| extern void swap(void **p1, void **p2); | ||||
| extern void spawn(Display *dpy, const char *shell, const char *cmd); | ||||
|  |  | |||
							
								
								
									
										51
									
								
								wm.c
								
								
								
								
							
							
						
						
									
										51
									
								
								wm.c
								
								
								
								
							|  | @ -15,15 +15,15 @@ | |||
| 
 | ||||
| /* X structs */ | ||||
| Display *dpy; | ||||
| Window root; | ||||
| XRectangle rect; | ||||
| Pixmap pmap; | ||||
| Atom wm_atom[WMLast]; | ||||
| Atom net_atom[NetLast]; | ||||
| Window root, barwin; | ||||
| Atom wm_atom[WMLast], net_atom[NetLast]; | ||||
| Cursor cursor[CurLast]; | ||||
| XRectangle rect, barrect; | ||||
| Bool running = True; | ||||
| 
 | ||||
| char *bartext, *shell; | ||||
| int screen, sel_screen; | ||||
| unsigned int kmask, numlock_mask; | ||||
| unsigned int lock_mask, numlock_mask; | ||||
| 
 | ||||
| /* draw structs */ | ||||
| Brush brush = {0}; | ||||
|  | @ -166,7 +166,7 @@ init_lock_keys() | |||
| 	} | ||||
| 	XFreeModifiermap(modmap); | ||||
| 
 | ||||
| 	kmask = 255 & ~(numlock_mask | LockMask); | ||||
| 	lock_mask = 255 & ~(numlock_mask | LockMask); | ||||
| } | ||||
| 
 | ||||
| static void | ||||
|  | @ -187,6 +187,7 @@ main(int argc, char *argv[]) | |||
| 	XSetWindowAttributes wa; | ||||
| 	unsigned int mask; | ||||
| 	Window w; | ||||
| 	XEvent ev; | ||||
| 
 | ||||
| 	/* command line args */ | ||||
| 	for(i = 1; (i < argc) && (argv[i][0] == '-'); i++) { | ||||
|  | @ -218,6 +219,9 @@ main(int argc, char *argv[]) | |||
| 	if(other_wm_running) | ||||
| 		error("gridwm: another window manager is already running\n"); | ||||
| 
 | ||||
| 	if(!(shell = getenv("SHELL"))) | ||||
| 		shell = "/bin/sh"; | ||||
| 
 | ||||
| 	rect.x = rect.y = 0; | ||||
| 	rect.width = DisplayWidth(dpy, screen); | ||||
| 	rect.height = DisplayHeight(dpy, screen); | ||||
|  | @ -244,19 +248,42 @@ main(int argc, char *argv[]) | |||
| 
 | ||||
| 	init_lock_keys(); | ||||
| 
 | ||||
| 	pmap = XCreatePixmap(dpy, root, rect.width, rect.height, | ||||
| 	brush.drawable = XCreatePixmap(dpy, root, rect.width, rect.height, | ||||
| 			DefaultDepth(dpy, screen)); | ||||
| 
 | ||||
| 	wa.event_mask = SubstructureRedirectMask | EnterWindowMask | LeaveWindowMask; | ||||
| 	wa.cursor = cursor[CurNormal]; | ||||
| 	XChangeWindowAttributes(dpy, root, CWEventMask | CWCursor, &wa); | ||||
| 	brush.gc = XCreateGC(dpy, root, 0, 0); | ||||
| 
 | ||||
| 	/* style */ | ||||
| 	loadcolors(dpy, screen, &brush, BGCOLOR, FGCOLOR, BORDERCOLOR); | ||||
| 	loadfont(dpy, &brush.font, FONT); | ||||
| 
 | ||||
| 	wa.override_redirect = 1; | ||||
| 	wa.background_pixmap = ParentRelative; | ||||
| 	wa.event_mask = ExposureMask; | ||||
| 
 | ||||
| 	barrect = rect; | ||||
| 	barrect.height = labelheight(&brush.font); | ||||
| 	barrect.y = rect.height - barrect.height; | ||||
| 	barwin = XCreateWindow(dpy, root, barrect.x, barrect.y, | ||||
| 			barrect.width, barrect.height, 0, DefaultDepth(dpy, screen), | ||||
| 			CopyFromParent, DefaultVisual(dpy, screen), | ||||
| 			CWOverrideRedirect | CWBackPixmap | CWEventMask, &wa); | ||||
| 	bartext = 0; | ||||
| 	XDefineCursor(dpy, barwin, cursor[CurNormal]); | ||||
| 	XMapRaised(dpy, barwin); | ||||
| 	draw_bar(); | ||||
| 
 | ||||
| 	wa.event_mask = SubstructureRedirectMask | EnterWindowMask | LeaveWindowMask; | ||||
| 	wa.cursor = cursor[CurNormal]; | ||||
| 	XChangeWindowAttributes(dpy, root, CWEventMask | CWCursor, &wa); | ||||
| 
 | ||||
| 	scan_wins(); | ||||
| 
 | ||||
| 	while(running) { | ||||
| 		XNextEvent(dpy, &ev); | ||||
| 		if(handler[ev.type]) | ||||
| 			(handler[ev.type]) (&ev); /* call handler */ | ||||
| 	} | ||||
| 
 | ||||
| 	cleanup(); | ||||
| 	XCloseDisplay(dpy); | ||||
| 
 | ||||
|  |  | |||
							
								
								
									
										40
									
								
								wm.h
								
								
								
								
							
							
						
						
									
										40
									
								
								wm.h
								
								
								
								
							|  | @ -9,16 +9,14 @@ | |||
| 
 | ||||
| #include <X11/Xutil.h> | ||||
| 
 | ||||
| /* WM atoms */ | ||||
| /* atoms */ | ||||
| enum { WMState, WMProtocols, WMDelete, WMLast }; | ||||
| 
 | ||||
| /* NET atoms */ | ||||
| enum { NetSupported, NetWMName, NetLast }; | ||||
| 
 | ||||
| /* Cursor */ | ||||
| /* cursor */ | ||||
| enum { CurNormal, CurResize, CurMove, CurInput, CurLast }; | ||||
| 
 | ||||
| /* Rects */ | ||||
| /* rects */ | ||||
| enum { RFloat, RGrid, RLast }; | ||||
| 
 | ||||
| typedef struct Client Client; | ||||
|  | @ -28,35 +26,45 @@ struct Client { | |||
| 	Tag *tag; | ||||
| 	char name[256]; | ||||
| 	int proto; | ||||
| 	unsigned int border; | ||||
| 	Bool fixedsize; | ||||
| 	Window win; | ||||
| 	Window trans; | ||||
| 	Window title; | ||||
| 	GC gc; | ||||
| 	XSizeHints size; | ||||
| 	XRectangle r[RLast]; | ||||
| 	Client *next; | ||||
| 	Client *tnext; | ||||
| 	Client *tprev; | ||||
| 	Client *snext; | ||||
| }; | ||||
| 
 | ||||
| struct Tag { | ||||
| 	char name[256]; | ||||
| 	Client *clients; | ||||
| 	Client *sel; | ||||
| 	Client *stack; | ||||
| 	XRectangle r; | ||||
| 	Tag *next; | ||||
| 	Tag *cnext; | ||||
| }; | ||||
| 
 | ||||
| extern Display *dpy; | ||||
| extern Window root; | ||||
| extern XRectangle rect; | ||||
| extern Atom wm_atom[WMLast]; | ||||
| extern Atom net_atom[NetLast]; | ||||
| extern Window root, barwin; | ||||
| extern Atom wm_atom[WMLast], net_atom[NetLast]; | ||||
| extern Cursor cursor[CurLast]; | ||||
| extern Pixmap pmap; | ||||
| extern XRectangle rect, barrect; | ||||
| extern Bool running; | ||||
| extern void (*handler[LASTEvent]) (XEvent *); | ||||
| 
 | ||||
| extern int screen, sel_screen; | ||||
| extern unsigned int kmask, numlock_mask; | ||||
| extern unsigned int lock_mask, numlock_mask; | ||||
| extern char *bartext, *shell; | ||||
| 
 | ||||
| extern Brush brush; | ||||
| 
 | ||||
| /* bar.c */ | ||||
| extern void draw_bar(); | ||||
| 
 | ||||
| /* client.c */ | ||||
| extern Client *create_client(Window w, XWindowAttributes *wa); | ||||
| extern void manage(Client *c); | ||||
| 
 | ||||
| /* wm.c */ | ||||
| extern int win_proto(Window w); | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue