[hackers] [st] Render only once in each main loop iteration || "Roberto E. Vargas Caballero"

From: <hg_AT_suckless.org>
Date: Sun, 16 Sep 2012 12:25:53 +0200 (CEST)

changeset: 306:a8fe037b37d1
user: "Roberto E. Vargas Caballero" <k0ga_AT_shike2.com>
date: Sun Sep 16 10:48:38 2012 +0200
files: st.c
description:
Render only once in each main loop iteration
draw() runs over all lines of the screen and renders only the dirty lines,
this avoids render lines which are not modified since last draw() call. In
this moment the main loop is something like:

     - Wait something to read from file descriptors
     - Read from pseudo tty
     - Call draw() for rending
     - Read X events

This cause the problem that all the X events that have to update the screen
have to call draw() (because draw() is called before of X events handling),
so you can have multiples renderings in only one iteration, that will waste
a lot of resources.

This patch change the main loop to:

     - Wait something to read from file descriptors
     - Read from pseudo tty
     - Read X events
     - Call draw() for rending

So X events don't have to worry about rendering, because draw() is called
after them.

The only place where draw is called outside of the main loop is in redraw(),
but it is necessary for getting a good tput flash.
---
 st.c |   29 ++++++-----------------------
 1 file changed, 6 insertions(+), 23 deletions(-)
diff -r d07c4a426bc3 -r a8fe037b37d1 st.c
--- a/st.c	Sun Sep 16 10:47:21 2012 +0200
+++ b/st.c	Sun Sep 16 10:48:38 2012 +0200
_AT_@ -288,7 +288,6 @@
 static void xdraws(char *, Glyph, int, int, int, int);
 static void xhints(void);
 static void xclear(int, int, int, int);
-static void xcopy(void);
 static void xdrawcursor(void);
 static void xinit(void);
 static void xloadcols(void);
_AT_@ -635,7 +634,6 @@
 		return;
 	sel.bx = -1;
 	tsetdirt(sel.b.y, sel.e.y);
-	draw();
 }
 
 void
_AT_@ -685,8 +683,6 @@
 
 	clipboard = XInternAtom(xw.dpy, "CLIPBOARD", 0);
 	XSetSelectionOwner(xw.dpy, clipboard, xw.win, CurrentTime);
-
-	XFlush(xw.dpy);
 }
 
 void
_AT_@ -729,7 +725,6 @@
 	}
 	memcpy(&sel.tclick2, &sel.tclick1, sizeof(struct timeval));
 	gettimeofday(&sel.tclick1, NULL);
-	draw();
 }
 
 void
_AT_@ -746,7 +741,6 @@
 			int starty = MIN(oldey, sel.ey);
 			int endy = MAX(oldey, sel.ey);
 			tsetdirt(starty, endy);
-			draw();
 		}
 	}
 }
_AT_@ -2091,13 +2085,6 @@
 		XDrawLine(xw.dpy, xw.buf, dc.gc, winx, winy+1, winx+width-1, winy+1);
 }
 
-/* copy buffer pixmap to screen pixmap */
-void
-xcopy() {
-	XdbeSwapInfo swpinfo[1] = {{xw.win, XdbeCopied}};
-	XdbeSwapBuffers(xw.dpy, swpinfo, 1);
-}
-
 void
 xdrawcursor(void) {
 	static int oldx = 0;
_AT_@ -2118,8 +2105,6 @@
 	} else
 		xclear(oldx, oldy, oldx, oldy);
 
-	xcopy();
-
 	/* draw the new one */
 	if(!(term.c.state & CURSOR_HIDE)) {
 		if(!(xw.state & WIN_FOCUSED))
_AT_@ -2132,8 +2117,6 @@
 		xdraws(g.c, g, term.c.x, term.c.y, 1, sl);
 		oldx = term.c.x, oldy = term.c.y;
 	}
-
-	xcopy();
 }
 
 void
_AT_@ -2152,8 +2135,10 @@
 
 void
 draw() {
+	XdbeSwapInfo swpinfo[1] = {{xw.win, XdbeCopied}};
+
 	drawregion(0, 0, term.col, term.row);
-	xcopy();
+	XdbeSwapBuffers(xw.dpy, swpinfo, 1);
 }
 
 void
_AT_@ -2208,7 +2193,6 @@
 		if(!e->count)
 			xw.state &= ~WIN_REDRAW;
 	}
-	xcopy();
 }
 
 void
_AT_@ -2241,7 +2225,6 @@
 		xseturgency(0);
 	} else
 		xw.state &= ~WIN_FOCUSED;
-	draw();
 }
 
 char*
_AT_@ -2317,7 +2300,6 @@
 		} else if(e->xclient.data.l[1] == XEMBED_FOCUS_OUT) {
 			xw.state &= ~WIN_FOCUSED;
 		}
-		draw();
 	}
 }
 
_AT_@ -2358,8 +2340,6 @@
 		if(FD_ISSET(cmdfd, &rfd))
 			ttyread();
 
-		draw();
-
 		while(XPending(xw.dpy)) {
 			XNextEvent(xw.dpy, &ev);
 			if(XFilterEvent(&ev, xw.win))
_AT_@ -2367,6 +2347,9 @@
 			if(handler[ev.type])
 				(handler[ev.type])(&ev);
 		}
+
+		draw();
+		XFlush(xw.dpy);
 	}
 }
 
Received on Sun Sep 16 2012 - 12:25:53 CEST

This archive was generated by hypermail 2.3.0 : Sun Sep 16 2012 - 12:36:09 CEST