summaryrefslogtreecommitdiff
path: root/xlib.c
diff options
context:
space:
mode:
authorRich Felker <dalias@aerifal.cx>2006-10-25 04:52:48 +0000
committerRich Felker <dalias@aerifal.cx>2006-10-25 04:52:48 +0000
commit734da46346f62d0af0feed2ffd74c47e06de7157 (patch)
tree2b55dfcb62ba3fbce2a65367dda5111a399b8485 /xlib.c
parent9b7a5f39380ca50f0efbb30689cd3ca97bac3920 (diff)
major changes to input handling in preparation for pasting, which will
require support for large blocks of input: output which cannot be written to the tty (pty) is no longer discarded. instead, the display module is responsible for keeping the buffer alive until it has been entirely consumed. one simple (and smart) way to ensure this is to refuse to process events that could generate new input text as long as there is unwritten data. this works as long as there is an earlier layer of buffering (for fbcon, kernel; for x11, xlib). a direct-on-x-protocol display implementation will have to do its own buffer management. this architecture allows pasting to be performed direct from a buffer owned by the display module, which could reside in static or shared memory, or even as a memory-mapped file. it also facilitates reuse of the code in non-tty-connected settings.
Diffstat (limited to 'xlib.c')
-rw-r--r--xlib.c48
1 files changed, 22 insertions, 26 deletions
diff --git a/xlib.c b/xlib.c
index f30597b..3bbd41f 100644
--- a/xlib.c
+++ b/xlib.c
@@ -217,14 +217,13 @@ void uudisp_next_event(struct uudisp *d, void *fds)
int status;
int i, n;
int y1, y2;
+ long mask = -1;
- d->inlen = 0;
- d->intext = d->inbuf;
+ if (d->inlen) mask &= ~KeyPressMask;
if (!FD_ISSET(p->fd, (fd_set *)fds)) return;
- while (XPending(p->display)) {
- XNextEvent(p->display, &ev);
+ while (XCheckMaskEvent(p->display, mask, &ev)) {
if (XFilterEvent(&ev, 0)) continue;
switch (ev.type) {
case FocusIn:
@@ -244,6 +243,7 @@ void uudisp_next_event(struct uudisp *d, void *fds)
resize_window(d, ev.xconfigure.width, ev.xconfigure.height);
break;
case KeyPress:
+ d->intext = d->inbuf;
if (p->ic) {
r = XmbLookupString(p->ic, (void *)&ev, tmp, sizeof(tmp), &ks, &status);
switch(status) {
@@ -260,7 +260,7 @@ void uudisp_next_event(struct uudisp *d, void *fds)
} else r = XLookupString((void *)&ev, tmp, sizeof(tmp), &ks, 0);
if (r>=sizeof(tmp)) continue;
tmp[r] = 0;
- if ((ev.xkey.state & Mod1Mask) && l) {
+ if (ev.xkey.state & Mod1Mask) {
*s++ = '\033';
l--;
}
@@ -270,40 +270,36 @@ void uudisp_next_event(struct uudisp *d, void *fds)
memcpy(s, keys[i].s, keys[i].l);
s += keys[i].l;
l -= keys[i].l;
- continue;
- }
- if ((ev.xkey.state & ControlMask) && ks == XK_minus && l) {
+ } else if ((ev.xkey.state & ControlMask)
+ && ks == XK_minus && l) {
*s++ = '_' & 0x1f;
l--;
- continue;
- }
- if ((ev.xkey.state & ControlMask) && (ks == XK_2 || ks == XK_space) && l) {
+ } else if ((ev.xkey.state & ControlMask)
+ && (ks == XK_2 || ks == XK_space) && l) {
*s++ = 0;
l--;
+ } else if (!r) {
continue;
- }
- if (!r) continue;
-
- if (p->ic) {
+ } else if (p->ic) {
if (r > l) continue;
memcpy(s, tmp, r);
s += r;
l -= r;
- continue;
- }
-
- /* Deal with Latin-1 crap.. */
- for (i=0; i<=r; i++) wtmp[i] = tmp[i];
- r = wcstombs(mbtmp, wtmp, sizeof mbtmp);
- if ((int)r > 0 && r <= l) {
- memcpy(s, mbtmp, r);
- s += r;
- l -= r;
+ } else {
+ /* Deal with Latin-1 crap.. */
+ for (i=0; i<=r; i++) wtmp[i] = tmp[i];
+ r = wcstombs(mbtmp, wtmp, sizeof mbtmp);
+ if ((int)r > 0 && r <= l) {
+ memcpy(s, mbtmp, r);
+ s += r;
+ l -= r;
+ }
}
+ d->inlen = s - d->inbuf;
+ mask &= ~KeyPressMask;
break;
}
}
- d->inlen = s - d->inbuf;
}
void uudisp_close(struct uudisp *d)