source: ldm/trunk/fuentes/wwm/screen.c @ 516

Last change on this file since 516 was 516, checked in by mabarracus, 5 years ago

Copy trusty code

File size: 7.5 KB
Line 
1#include <X11/Xlib.h>
2#include <X11/Xutil.h>
3#include <X11/keysym.h>
4#include <X11/Xproto.h>
5#include <X11/cursorfont.h>
6#include <stdlib.h>
7#include "wwm.h"
8
9void
10draw_outline(Client *c)
11{
12    Window root = ROOTWINDOW;
13    static int gc_initialized = 0;
14    static GC invert_gc;
15
16    if (!gc_initialized) {
17        XGCValues gv;
18
19        gc_initialized++;
20        gv.function = GXinvert;
21        gv.subwindow_mode = IncludeInferiors;
22        gv.line_width = DEF_BW; /* opt_bw */
23
24        invert_gc = XCreateGC(display, root,
25                              GCFunction | GCSubwindowMode | GCLineWidth, &gv);
26    }
27
28    XDrawRectangle(display, root, invert_gc, c->x - c->border,
29                   c->y - c->border, c->width + c->border,
30                   c->height + c->border);
31}
32
33void
34get_mouse_position(int *x, int *y)
35{
36    Window root = ROOTWINDOW;
37    Window dw1, dw2;
38    int t1, t2;
39    unsigned int t3;
40
41    XQueryPointer(display, root, &dw1, &dw2, x, y, &t1, &t2, &t3);
42}
43
44void
45recalculate_sweep(Client *c, int x1, int y1, int x2, int y2)
46{
47    int basex, basey;
48
49    c->width = (int) abs(x1 - x2);
50    c->height = (int) abs(y1 - y2);
51
52    if (c->size->flags & PResizeInc) {
53        basex = (c->size->flags & PBaseSize) ? c->size->base_width :
54                (c->size->flags & PMinSize) ? c->size->min_width : 0;
55        basey = (c->size->flags & PBaseSize) ? c->size->base_height :
56                (c->size->flags & PMinSize) ? c->size->min_height : 0;
57        c->width -= (c->width - basex) % c->size->width_inc;
58        c->height -= (c->height - basey) % c->size->height_inc;
59    }
60
61    if (c->size->flags & PMinSize) {
62        if (c->width < c->size->min_width)
63            c->width = c->size->min_width;
64        if (c->height < c->size->min_height)
65            c->height = c->size->min_height;
66    }
67
68    if (c->size->flags & PMaxSize) {
69        if (c->width > c->size->max_width)
70            c->width = c->size->max_width;
71        if (c->height > c->size->max_height)
72            c->height = c->size->max_height;
73    }
74
75    c->x = (x1 <= x2) ? x1 : x1 - c->width;
76    c->y = (y1 <= y2) ? y1 : y1 - c->height;
77}
78
79void
80sweep(Client *c)
81{
82    Window root = ROOTWINDOW;
83    static int resize_cursor_initialized = 0;
84    static Cursor resize_curs;
85    XEvent ev;
86    int old_cx = c->x;
87    int old_cy = c->y;
88
89    if (!resize_cursor_initialized) {
90        resize_cursor_initialized++;
91        resize_curs = XCreateFontCursor(display, XC_plus);
92    }
93
94    if (!grab(root, MouseMask, resize_curs))
95        return;
96
97    XGrabServer(display);
98
99    draw_outline(c);
100
101    XWarpPointer(display, None, c->window, 0, 0, 0, 0, c->width, c->height);
102
103    for (;;) {
104        XMaskEvent(display, MouseMask, &ev);
105        switch (ev.type) {
106            case MotionNotify:
107                draw_outline(c);    /* clear */
108                XUngrabServer(display);
109                recalculate_sweep(c, old_cx, old_cy,
110                                  ev.xmotion.x, ev.xmotion.y);
111                XSync(display, False);
112                XGrabServer(display);
113                draw_outline(c);
114                break;
115            case ButtonRelease:
116                draw_outline(c);    /* clear */
117                XUngrabServer(display);
118                XUngrabPointer(display, CurrentTime);
119                return;
120        }
121    }
122}
123
124void
125drag(Client *c)
126{
127    Window root = ROOTWINDOW;
128    static int drag_cursor_initialized = 0;
129    static Cursor drag_curs;
130    XEvent ev;
131    int x1, y1;
132    int old_cx = c->x;
133    int old_cy = c->y;
134
135    if (!drag_cursor_initialized) {
136        drag_cursor_initialized++;
137        drag_curs = XCreateFontCursor(display, XC_fleur);
138    }
139
140    if (!grab(root, MouseMask, drag_curs))
141        return;
142    get_mouse_position(&x1, &y1);
143    XGrabServer(display);
144    draw_outline(c);
145    for (;;) {
146        XMaskEvent(display, MouseMask, &ev);
147        switch (ev.type) {
148            case MotionNotify:
149                draw_outline(c);    /* clear */
150                XUngrabServer(display);
151                c->x = old_cx + (ev.xmotion.x - x1);
152                c->y = old_cy + (ev.xmotion.y - y1);
153                XSync(display, False);
154                XGrabServer(display);
155                draw_outline(c);
156                break;
157            case ButtonRelease:
158                draw_outline(c);    /* clear */
159                XUngrabServer(display);
160                XUngrabPointer(display, CurrentTime);
161                return;
162            default:
163                break;
164        }
165    }
166}
167
168void
169move(Client *c, int set)
170{
171    if (!set)
172        drag(c);
173
174    XMoveWindow(display, c->parent, c->x - c->border, c->y - c->border);
175    send_config(c);
176    XRaiseWindow(display, c->parent);
177}
178
179void
180resize(Client *c, int set)
181{
182    if (!set)
183        sweep(c);
184
185    XMoveResizeWindow(display, c->parent, c->x - c->border,
186                      c->y - c->border, c->width + (c->border * 2),
187                      c->height + (c->border * 2));
188    XMoveResizeWindow(display, c->window, c->border, c->border,
189                      c->width, c->height);
190    send_config(c);
191    XRaiseWindow(display, c->parent);
192}
193
194void
195maximise_horiz(Client *c)
196{
197    if (c->oldw) {
198        c->x = c->oldx;
199        c->width = c->oldw;
200        c->oldw = 0;
201    } else {
202        c->oldx = c->x;
203        c->oldw = c->width;
204        recalculate_sweep(c, c->border, c->y,
205                          (xmax() - c->border), c->y + c->height);
206    }
207}
208
209void
210maximise_vert(Client *c)
211{
212    if (c->oldh) {
213        c->y = c->oldy;
214        c->height = c->oldh;
215        c->oldh = 0;
216    } else {
217        c->oldy = c->y;
218        c->oldh = c->height;
219        recalculate_sweep(c, c->x, c->border, c->x + c->width,
220                          (ymax() - c->border));
221    }
222}
223
224void
225hide(Client *c)
226{
227    c->ignore_unmap = 2;
228    XUnmapWindow(display, c->parent);
229    XUnmapWindow(display, c->window);
230    set_wm_state(c, IconicState);
231}
232
233void
234unhide(Client *c, int raiseit)
235{
236    c->ignore_unmap = 0;
237    XMapWindow(display, c->window);
238    raiseit ? XMapRaised(display, c->parent) : XMapWindow(display, c->parent);
239    set_wm_state(c, NormalState);
240}
241
242/*
243 * Next focuses the next client on this vdesk
244 */
245
246void
247next(Client *c)
248{
249    Client *newc;
250
251    newc = next_client_on_vdesk(( c ? c : head_client));
252
253    if (!newc)
254        return;         /* couldn't find a next on this screen */
255
256    focus_client(newc, RAISE);
257}
258
259
260/*
261 * switch_vdesk changes to a different vdesk
262 */
263
264void
265switch_vdesk(int v)
266{
267    Client *c;
268    int vcurr = vdesk_get();
269
270    if (v == vcurr)
271        return;
272
273    for (c = head_client; c; c = c->next) {
274        if (c->vdesk == vcurr) {
275            hide(c);
276        } else if (c->vdesk == v) {
277            unhide(c, NO_RAISE);
278            if (c->focus)
279                focus_client(c, RAISE);
280        }
281    }
282
283    vdesk(VDESK_SET, v);
284}
285
286void
287focus_client(Client *c, int raiseit)
288{
289    Client *cp;
290
291    for (cp = head_client; cp; cp = cp->next)
292        if ((cp->vdesk == vdesk_get() || cp->vdesk == LOCKED) && cp->focus)
293            unfocus_client(cp);
294    unhide(c, raiseit);
295    XSetInputFocus(display, c->window, RevertToPointerRoot, CurrentTime);
296    XSetWindowBackground(display, c->parent,
297                         (c->vdesk == LOCKED) ? fc.pixel : fg.pixel);
298    XClearWindow(display, c->parent);
299    XGrabButton(display, AnyButton, WMMODMASK, c->parent, False,
300                ButtonMask, GrabModeAsync, GrabModeSync, None, None);
301    c->focus = 1;
302    current = c;
303}
304
305
306void
307unfocus_client(Client *c)
308{
309    XSetInputFocus(display, PointerRoot, RevertToPointerRoot, CurrentTime);
310    XSetWindowBackground(display, c->parent, bg.pixel);
311    XClearWindow(display, c->parent);
312    c->focus = 0;
313    current = NULL;
314}
Note: See TracBrowser for help on using the repository browser.