~ctwm/ctwm/trunk

614.1.23 by Maxime Soulé
Some geometries can be relative to a monitor
1
/*
2
 * Copyright notice...
3
 */
4
614.2.1 by Matthew Fuller
Bring new files into compliance with header ordering, by including
5
#include "ctwm.h"
614.1.23 by Maxime Soulé
Some geometries can be relative to a monitor
6
7
#include <string.h>
8
#include <X11/Xlib.h>
9
#include <X11/Xutil.h>
10
11
#include "r_layout.h"
12
#include "r_area.h"
614.2.1 by Matthew Fuller
Bring new files into compliance with header ordering, by including
13
#include "xparsegeometry.h"
614.1.23 by Maxime Soulé
Some geometries can be relative to a monitor
14
15
614.1.33 by Matthew Fuller
Doc up RLayoutXParseGeometry.
16
/**
17
 * Parse an X Geometry out to get the positions and sizes.
18
 *
19
 * This generally wraps and replaces our uses of XParseGeometry in order
20
 * to allow positioning relative to a XRANDR output name.  This allows
21
 * specifying a geometry relative to a particular monitor, rather than on
22
 * the whole composite multi-screen output meta-display.
23
 */
24
int
25
RLayoutXParseGeometry(RLayout *layout, const char *geometry, int *x, int *y,
26
                      unsigned int *width, unsigned int *height)
614.1.23 by Maxime Soulé
Some geometries can be relative to a monitor
27
{
28
	char *sep;
29
614.1.33 by Matthew Fuller
Doc up RLayoutXParseGeometry.
30
	// Got something that looks like a display?
614.1.23 by Maxime Soulé
Some geometries can be relative to a monitor
31
	sep = strchr(geometry, ':');
32
	if(sep != NULL) {
614.1.24 by Maxime Soulé
Icon{Region,Manager{s,Geometry} accept monitor relative geometries
33
		RArea mon = RLayoutGetAreaByName(layout, geometry, sep - geometry);
34
		if(RAreaIsValid(&mon)) {
614.1.33 by Matthew Fuller
Doc up RLayoutXParseGeometry.
35
			// Yep, one of our monitors; figure the placement on our
36
			// whole root where that part of this monitor lies.
614.1.24 by Maxime Soulé
Icon{Region,Manager{s,Geometry} accept monitor relative geometries
37
			int mask = XParseGeometry(sep + 1, x, y, width, height);
38
			RArea big = RLayoutBigArea(layout);
39
40
			if(mask & XValue) {
41
				if(mask & XNegative) {
42
					*x -= big.width - mon.width - (mon.x - big.x);
43
				}
44
				else {
45
					*x += mon.x - big.x;
46
				}
47
			}
48
49
			if(mask & YValue) {
50
				if(mask & YNegative) {
51
					*y -= big.height - mon.height - (mon.y - big.y);
52
				}
53
				else {
54
					*y += mon.y - big.y;
55
				}
56
			}
57
58
			return mask;
614.1.23 by Maxime Soulé
Some geometries can be relative to a monitor
59
		}
60
61
		// Name not found, keep the geometry part as-is
62
		geometry = sep + 1;
63
	}
64
65
	return XParseGeometry(geometry, x, y, width, height);
66
}