ref: 5689c790ad6e428ad640051d399f5966c995f978
parent: d68a62124bd18f9fe74efe8555ed0f00a52cd08f
author: cinap_lenrek <cinap_lenrek@felloff.net>
date: Fri Feb 1 12:33:45 EST 2019
gui-x11: implement screensize()
--- a/gui-x11/x11.c
+++ b/gui-x11/x11.c
@@ -43,7 +43,7 @@
static int plan9tox11[256]; /* Values for mapping between */
static int x11toplan9[256]; /* X11 and Plan 9 */
static GC xgccopy;
-static ulong xscreenchan;
+static ulong xscreenchan;
static Drawable xscreenid;
static XImage* xscreenimage;
static Visual *xvis;
@@ -125,7 +125,6 @@
static void xdestroy(XEvent*);
static void xselect(XEvent*, XDisplay*);
static void xproc(void*);
-static Memimage* xinitscreen(void);
static void initmap(Window);
static GC creategc(Drawable);
static void graphicscmap(XColor*);
@@ -138,6 +137,27 @@
Memimage *gscreen;
Screeninfo screen;
+static int
+shutup(XDisplay *d, XErrorEvent *e)
+{
+ char buf[200];
+ iprint("X error: error code=%d, request_code=%d, minor=%d\n", e->error_code, e->request_code, e->minor_code);
+ XGetErrorText(d, e->error_code, buf, sizeof(buf));
+ iprint("%s\n", buf);
+ USED(d);
+ USED(e);
+ return 0;
+}
+
+static int
+panicshutup(XDisplay *d)
+{
+ screenputs = 0;
+ panic("x error");
+ return -1;
+}
+
+
void
flushmemscreen(Rectangle r)
{
@@ -167,171 +187,7 @@
void
screeninit(void)
{
- _memmkcmap();
-
- gscreen = xinitscreen();
- kproc("xscreen", xproc, nil);
-
- memimageinit();
- terminit();
- qlock(&drawlock);
- flushmemscreen(gscreen->clipr);
- qunlock(&drawlock);
-}
-
-void
-screensize(Rectangle r, ulong chan)
-{
- USED(chan);
-}
-
-Memdata*
-attachscreen(Rectangle *r, ulong *chan, int *depth, int *width, int *softscreen)
-{
- *r = gscreen->clipr;
- *chan = gscreen->chan;
- *depth = gscreen->depth;
- *width = gscreen->width;
- *softscreen = 1;
-
- gscreen->data->ref++;
- return gscreen->data;
-}
-
-static int
-revbyte(int b)
-{
- int r;
-
- r = 0;
- r |= (b&0x01) << 7;
- r |= (b&0x02) << 5;
- r |= (b&0x04) << 3;
- r |= (b&0x08) << 1;
- r |= (b&0x10) >> 1;
- r |= (b&0x20) >> 3;
- r |= (b&0x40) >> 5;
- r |= (b&0x80) >> 7;
- return r;
-}
-
-void
-mouseset(Point xy)
-{
- qlock(&drawlock);
- XWarpPointer(xdisplay, None, xdrawable, 0, 0, 0, 0, xy.x, xy.y);
- XFlush(xdisplay);
- qunlock(&drawlock);
-}
-
-static XCursor xcursor;
-
-void
-setcursor(void)
-{
- XCursor xc;
- XColor fg, bg;
- Pixmap xsrc, xmask;
- int i;
- uchar src[2*16], mask[2*16];
-
- for(i=0; i<2*16; i++){
- src[i] = revbyte(cursor.set[i]);
- mask[i] = revbyte(cursor.set[i] | cursor.clr[i]);
- }
-
- qlock(&drawlock);
- fg = map[0];
- bg = map[255];
- xsrc = XCreateBitmapFromData(xdisplay, xdrawable, (char*)src, 16, 16);
- xmask = XCreateBitmapFromData(xdisplay, xdrawable, (char*)mask, 16, 16);
- xc = XCreatePixmapCursor(xdisplay, xsrc, xmask, &fg, &bg, -cursor.offset.x, -cursor.offset.y);
- if(xc != 0) {
- XDefineCursor(xdisplay, xdrawable, xc);
- if(xcursor != 0)
- XFreeCursor(xdisplay, xcursor);
- xcursor = xc;
- }
- XFreePixmap(xdisplay, xsrc);
- XFreePixmap(xdisplay, xmask);
- XFlush(xdisplay);
- qunlock(&drawlock);
-}
-
-void
-cursorarrow(void)
-{
- qlock(&drawlock);
- if(xcursor != 0){
- XFreeCursor(xdisplay, xcursor);
- xcursor = 0;
- }
- XUndefineCursor(xdisplay, xdrawable);
- XFlush(xdisplay);
- qunlock(&drawlock);
-}
-
-static void
-xproc(void *arg)
-{
- ulong mask;
- XEvent event;
-
- mask = KeyPressMask|
- KeyReleaseMask|
- ButtonPressMask|
- ButtonReleaseMask|
- PointerMotionMask|
- Button1MotionMask|
- Button2MotionMask|
- Button3MotionMask|
- Button4MotionMask|
- Button5MotionMask|
- ExposureMask|
- EnterWindowMask|
- LeaveWindowMask|
- FocusChangeMask|
- StructureNotifyMask;
-
- XSelectInput(xkmcon, xdrawable, mask);
- for(;;) {
- //XWindowEvent(xkmcon, xdrawable, mask, &event);
- XNextEvent(xkmcon, &event);
- xselect(&event, xkmcon);
- xkeyboard(&event);
- xmouse(&event);
- xresize(&event);
- xexpose(&event);
- xmapping(&event);
- xdestroy(&event);
- }
-}
-
-static int
-shutup(XDisplay *d, XErrorEvent *e)
-{
- char buf[200];
- iprint("X error: error code=%d, request_code=%d, minor=%d\n", e->error_code, e->request_code, e->minor_code);
- XGetErrorText(d, e->error_code, buf, sizeof(buf));
- iprint("%s\n", buf);
- USED(d);
- USED(e);
- return 0;
-}
-
-static int
-panicshutup(XDisplay *d)
-{
- screenputs = 0;
- panic("x error");
- return -1;
-}
-
-static Memimage*
-xinitscreen(void)
-{
- Memimage *gscreen;
- int i, xsize, ysize;
+ int i, n;
char *argv[2];
Window rootwin;
Rectangle r;
@@ -344,11 +200,9 @@
XSizeHints normalhints;
XSetWindowAttributes attrs;
XPixmapFormatValues *pfmt;
- int n;
Pixmap icon_pixmap;
- xscreenid = 0;
- xdrawable = 0;
+ memimageinit();
xdisplay = XOpenDisplay(NULL);
if(xdisplay == 0)
@@ -356,6 +210,23 @@
XSetErrorHandler(shutup);
XSetIOErrorHandler(panicshutup);
+
+ xkmcon = XOpenDisplay(NULL);
+ if(xkmcon == 0)
+ panic("XOpenDisplay: %r [DISPLAY=%s]", getenv("DISPLAY"));
+
+ XkbSetDetectableAutoRepeat(xkmcon, True, NULL);
+
+ clipboard = XInternAtom(xkmcon, "CLIPBOARD", False);
+ utf8string = XInternAtom(xkmcon, "UTF8_STRING", False);
+ targets = XInternAtom(xkmcon, "TARGETS", False);
+ text = XInternAtom(xkmcon, "TEXT", False);
+ compoundtext = XInternAtom(xkmcon, "COMPOUND_TEXT", False);
+
+ xsnarfcon = XOpenDisplay(NULL);
+ if(xsnarfcon == 0)
+ panic("XOpenDisplay: %r [DISPLAY=%s]", getenv("DISPLAY"));
+
rootscreennum = DefaultScreen(xdisplay);
rootwin = DefaultRootWindow(xdisplay);
@@ -431,17 +302,14 @@
}
r.min = ZP;
- r.max.x = WidthOfScreen(screen);
- r.max.y = HeightOfScreen(screen);
-
- xsize = Dx(r)*3/4;
- ysize = Dy(r)*3/4;
+ r.max.x = WidthOfScreen(screen)*3/4;
+ r.max.y = HeightOfScreen(screen)*3/4;
attrs.colormap = xcmap;
attrs.background_pixel = 0;
attrs.border_pixel = 0;
/* attrs.override_redirect = 1;*/ /* WM leave me alone! |CWOverrideRedirect */
- xdrawable = XCreateWindow(xdisplay, rootwin, 0, 0, xsize, ysize, 0,
+ xdrawable = XCreateWindow(xdisplay, rootwin, 0, 0, Dx(r), Dy(r), 0,
xscreendepth, InputOutput, xvis, CWBackPixel|CWBorderPixel|CWColormap, &attrs);
/* load the given bitmap data and create an X pixmap containing it. */
@@ -456,11 +324,9 @@
name.encoding = XA_STRING;
name.format = 8;
name.nitems = strlen((char*)name.value);
- normalhints.flags = USSize|PMaxSize;
- normalhints.max_width = Dx(r);
- normalhints.max_height = Dy(r);
- normalhints.width = xsize;
- normalhints.height = ysize;
+ normalhints.flags = USSize;
+ normalhints.width = Dx(r);
+ normalhints.height = Dy(r);
hints.flags = IconPixmapHint |InputHint|StateHint;
hints.input = 1;
hints.initial_state = NormalState;
@@ -486,27 +352,182 @@
XMapWindow(xdisplay, xdrawable);
XFlush(xdisplay);
- xscreenid = XCreatePixmap(xdisplay, xdrawable, Dx(r), Dy(r), xscreendepth);
- gscreen = xallocmemimage(r, xscreenchan, xscreenid, &xscreenimage);
- gscreen->clipr = Rect(0,0,xsize,ysize);
- xgccopy = creategc(xscreenid);
+ screensize(r, xscreenchan);
+ if(gscreen == nil)
+ panic("screensize failed");
- xkmcon = XOpenDisplay(NULL);
- if(xkmcon == 0)
- panic("XOpenDisplay: %r [DISPLAY=%s]", getenv("DISPLAY"));
- XkbSetDetectableAutoRepeat(xkmcon, True, NULL);
+ gscreen->clipr = r;
+ kproc("xscreen", xproc, nil);
- xsnarfcon = XOpenDisplay(NULL);
- if(xsnarfcon == 0)
- panic("XOpenDisplay: %r [DISPLAY=%s]", getenv("DISPLAY"));
+ terminit();
- clipboard = XInternAtom(xkmcon, "CLIPBOARD", False);
- utf8string = XInternAtom(xkmcon, "UTF8_STRING", False);
- targets = XInternAtom(xkmcon, "TARGETS", False);
- text = XInternAtom(xkmcon, "TEXT", False);
- compoundtext = XInternAtom(xkmcon, "COMPOUND_TEXT", False);
+ qlock(&drawlock);
+ flushmemscreen(gscreen->clipr);
+ qunlock(&drawlock);
+}
- return gscreen;
+void
+screensize(Rectangle r, ulong chan)
+{
+ Drawable pix;
+ Memimage *mi;
+ XImage *xi;
+ GC gc;
+
+ pix = XCreatePixmap(xdisplay, xdrawable, Dx(r), Dy(r), xscreendepth);
+ if(pix == 0)
+ return;
+
+ gc = creategc(pix);
+ if(gc == NULL){
+ XFreePixmap(xdisplay, pix);
+ return;
+ }
+
+ mi = xallocmemimage(r, chan, pix, &xi);
+ if(mi == nil){
+ XFreeGC(xdisplay, xgccopy);
+ XFreePixmap(xdisplay, pix);
+ return;
+ }
+
+ if(gscreen != nil){
+ xscreenimage->data = NULL; /* free'd by freememimage() */
+ XDestroyImage(xscreenimage);
+ freememimage(gscreen);
+
+ XFreeGC(xdisplay, xgccopy);
+ XFreePixmap(xdisplay, xscreenid);
+ }
+
+ xscreenimage = xi;
+ xscreenid = pix;
+ xgccopy = gc;
+
+ gscreen = mi;
+ gscreen->clipr = ZR;
+}
+
+Memdata*
+attachscreen(Rectangle *r, ulong *chan, int *depth, int *width, int *softscreen)
+{
+ *r = gscreen->clipr;
+ *chan = gscreen->chan;
+ *depth = gscreen->depth;
+ *width = gscreen->width;
+ *softscreen = 1;
+
+ gscreen->data->ref++;
+ return gscreen->data;
+}
+
+static int
+revbyte(int b)
+{
+ int r;
+
+ r = 0;
+ r |= (b&0x01) << 7;
+ r |= (b&0x02) << 5;
+ r |= (b&0x04) << 3;
+ r |= (b&0x08) << 1;
+ r |= (b&0x10) >> 1;
+ r |= (b&0x20) >> 3;
+ r |= (b&0x40) >> 5;
+ r |= (b&0x80) >> 7;
+ return r;
+}
+
+void
+mouseset(Point xy)
+{
+ qlock(&drawlock);
+ XWarpPointer(xdisplay, None, xdrawable, 0, 0, 0, 0, xy.x, xy.y);
+ XFlush(xdisplay);
+ qunlock(&drawlock);
+}
+
+static XCursor xcursor;
+
+void
+setcursor(void)
+{
+ XCursor xc;
+ XColor fg, bg;
+ Pixmap xsrc, xmask;
+ int i;
+ uchar src[2*16], mask[2*16];
+
+ for(i=0; i<2*16; i++){
+ src[i] = revbyte(cursor.set[i]);
+ mask[i] = revbyte(cursor.set[i] | cursor.clr[i]);
+ }
+
+ qlock(&drawlock);
+ fg = map[0];
+ bg = map[255];
+ xsrc = XCreateBitmapFromData(xdisplay, xdrawable, (char*)src, 16, 16);
+ xmask = XCreateBitmapFromData(xdisplay, xdrawable, (char*)mask, 16, 16);
+ xc = XCreatePixmapCursor(xdisplay, xsrc, xmask, &fg, &bg, -cursor.offset.x, -cursor.offset.y);
+ if(xc != 0) {
+ XDefineCursor(xdisplay, xdrawable, xc);
+ if(xcursor != 0)
+ XFreeCursor(xdisplay, xcursor);
+ xcursor = xc;
+ }
+ XFreePixmap(xdisplay, xsrc);
+ XFreePixmap(xdisplay, xmask);
+ XFlush(xdisplay);
+ qunlock(&drawlock);
+}
+
+void
+cursorarrow(void)
+{
+ qlock(&drawlock);
+ if(xcursor != 0){
+ XFreeCursor(xdisplay, xcursor);
+ xcursor = 0;
+ }
+ XUndefineCursor(xdisplay, xdrawable);
+ XFlush(xdisplay);
+ qunlock(&drawlock);
+}
+
+static void
+xproc(void *arg)
+{
+ ulong mask;
+ XEvent event;
+
+ mask = KeyPressMask|
+ KeyReleaseMask|
+ ButtonPressMask|
+ ButtonReleaseMask|
+ PointerMotionMask|
+ Button1MotionMask|
+ Button2MotionMask|
+ Button3MotionMask|
+ Button4MotionMask|
+ Button5MotionMask|
+ ExposureMask|
+ EnterWindowMask|
+ LeaveWindowMask|
+ FocusChangeMask|
+ StructureNotifyMask;
+
+ XSelectInput(xkmcon, xdrawable, mask);
+ for(;;) {
+ //XWindowEvent(xkmcon, xdrawable, mask, &event);
+ XNextEvent(xkmcon, &event);
+ xselect(&event, xkmcon);
+ xkeyboard(&event);
+ xmouse(&event);
+ xresize(&event);
+ xexpose(&event);
+ xmapping(&event);
+ xdestroy(&event);
+ }
}
static void