aboutsummaryrefslogtreecommitdiff
path: root/src/cmd/proof/screen.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/cmd/proof/screen.c')
-rw-r--r--src/cmd/proof/screen.c315
1 files changed, 315 insertions, 0 deletions
diff --git a/src/cmd/proof/screen.c b/src/cmd/proof/screen.c
new file mode 100644
index 00000000..dccfe01d
--- /dev/null
+++ b/src/cmd/proof/screen.c
@@ -0,0 +1,315 @@
+#include <u.h>
+#include <libc.h>
+#include <draw.h>
+#include <cursor.h>
+#include <event.h>
+#include <bio.h>
+#include "proof.h"
+
+static int checkmouse(void);
+/* static int buttondown(void); */
+static char *getmousestr(void);
+static char *getkbdstr(int);
+
+extern Cursor blot;
+extern char *track;
+
+Mouse mouse;
+
+void
+mapscreen(void)
+{
+ if(initdraw(0, 0, "proof") < 0){
+ fprint(2, "proof: initdraw failed: %r\n");
+ exits("initdraw");
+ }
+ einit(Ekeyboard|Emouse);
+}
+
+void
+clearscreen(void)
+{
+ draw(screen, screen->r, display->black, nil, ZP);
+}
+
+void
+screenprint(char *fmt, ...)
+{
+ char buf[100];
+ Point p;
+ va_list args;
+
+ va_start(args, fmt);
+ vseprint(buf, &buf[sizeof buf], fmt, args);
+ va_end(args);
+ p = Pt(screen->clipr.min.x+40, screen->clipr.max.y-40);
+ string(screen, p, display->black, ZP, font, buf);
+}
+
+#define Viewkey 0xb2
+#define etimer(x, y) 0
+
+char *
+getcmdstr(void)
+{
+ Event ev;
+ int e;
+ static ulong timekey = 0;
+ ulong tracktm = 0;
+ Dir *dir;
+
+ if(track){
+ if(timekey == 0)
+ timekey = etimer(0, 5000);
+ dir = dirstat(track);
+ if(dir != nil){
+ tracktm = dir->mtime;
+ free(dir);
+ }
+ }
+ for (;;) {
+ e = event(&ev);
+ if(resized){
+ resized = 0;
+ return "p";
+ }
+ if ((e & Emouse) && ev.mouse.buttons) {
+ mouse = ev.mouse;
+ return getmousestr();
+ } else if (e & Ekeyboard)
+ return getkbdstr(ev.kbdc); /* sadly, no way to unget */
+ else if (e & timekey) {
+ if((dir = dirstat(track)) != nil){
+ if(tracktm < dir->mtime){
+ free(dir);
+ return "q";
+ }
+ free(dir);
+ }
+ }
+ }
+ return nil;
+}
+
+static char *
+getkbdstr(int c0)
+{
+ static char buf[100];
+ char *p;
+ int c;
+
+ if (c0 == '\n')
+ return "";
+ buf[0] = c0;
+ buf[1] = 0;
+ screenprint("%s", buf);
+ for (p = buf+1; (c = ekbd()) != '\n' && c != '\r' && c != -1 && c != Viewkey; ) {
+ if (c == '\b' && p > buf) {
+ *--p = ' ';
+ } else {
+ *p++ = c;
+ *p = 0;
+ }
+ screenprint("%s", buf);
+ }
+ *p = 0;
+ return buf;
+}
+
+
+#define button3(b) ((b) & 4)
+#define button2(b) ((b) & 2)
+#define button1(b) ((b) & 1)
+#define button23(b) ((b) & 6)
+#define button123(b) ((b) & 7)
+
+#define butcvt(b) (1 << ((b) - 1))
+
+#if 0
+static int buttondown(void) /* report state of buttons, if any */
+{
+ if (!ecanmouse()) /* no event pending */
+ return 0;
+ mouse = emouse(); /* something, but it could be motion */
+ return mouse.buttons & 7;
+}
+#endif
+
+int waitdown(void) /* wait until some button is down */
+{
+ while (!(mouse.buttons & 7))
+ mouse = emouse();
+ return mouse.buttons & 7;
+}
+
+int waitup(void)
+{
+ while (mouse.buttons & 7)
+ mouse = emouse();
+ return mouse.buttons & 7;
+}
+
+char *m3[] = { "next", "prev", "page n", "again", "bigger", "smaller", "pan", "quit?", 0 };
+char *m2[] = { 0 };
+
+enum { Next = 0, Prev, Page, Again, Bigger, Smaller, Pan, Quit };
+
+Menu mbut3 = { m3, 0, 0 };
+Menu mbut2 = { m2, 0, 0 };
+
+int last_hit;
+int last_but;
+
+char *pan(void)
+{
+ Point dd, xy, lastxy, min, max;
+
+ esetcursor(&blot);
+ waitdown();
+ xy = mouse.xy;
+ do{
+ lastxy = mouse.xy;
+ mouse = emouse();
+ dd = subpt(mouse.xy, lastxy);
+ min = addpt(screen->clipr.min, dd);
+ max = addpt(screen->clipr.max, dd);
+ draw(screen, rectaddpt(screen->r, subpt(mouse.xy, lastxy)),
+ screen, nil, screen->r.min);
+ if(mouse.xy.x < lastxy.x) /* moved left, clear right */
+ draw(screen, Rect(max.x, screen->r.min.y, screen->r.max.x, screen->r.max.y),
+ display->white, nil, ZP);
+ else /* moved right, clear left*/
+ draw(screen, Rect(screen->r.min.x, screen->r.min.y, min.x, screen->r.max.y),
+ display->white, nil, ZP);
+ if(mouse.xy.y < lastxy.y) /* moved up, clear down */
+ draw(screen, Rect(screen->r.min.x, max.y, screen->r.max.x, screen->r.max.y),
+ display->white, nil, ZP);
+ else /* moved down, clear up */
+ draw(screen, Rect(screen->r.min.x, screen->r.min.y, screen->r.max.x, min.y),
+ display->white, nil, ZP);
+ flushimage(display, 1);
+ }while(mouse.buttons);
+
+ xyoffset = addpt(xyoffset, subpt(mouse.xy, xy));
+
+ esetcursor(0);
+ return "p";
+}
+
+static char *getmousestr(void)
+{
+ static char buf[20];
+
+ checkmouse();
+ if (last_but == 1)
+ return "p"; /* repaint after panning */
+ if (last_but == 2) {
+ return "c";
+ } else if (last_but == 3) {
+ switch (last_hit) {
+ case Next:
+ return "";
+ case Prev:
+ return "-1";
+ case Page:
+ screenprint("page? ");
+ return "c";
+ case Again:
+ return "p";
+ case Bigger:
+ sprint(buf, "m%g", mag * 1.1);
+ return buf;
+ case Smaller:
+ sprint(buf, "m%g", mag / 1.1);
+ return buf;
+ case Pan:
+ return pan();
+ case Quit:
+ return "q";
+ default:
+ return "c";
+ }
+ } else { /* button 1 or bail out */
+ return "c";
+ }
+}
+
+static int
+checkmouse(void) /* return button touched if any */
+{
+ int c, b;
+ char *p;
+ extern int confirm(int);
+
+ b = waitdown();
+ last_but = 0;
+ last_hit = -1;
+ c = 0;
+ if (button3(b)) {
+ last_hit = emenuhit(3, &mouse, &mbut3);
+ last_but = 3;
+ } else if (button2(b)) {
+ last_hit = emenuhit(2, &mouse, &mbut2);
+ last_but = 2;
+ } else { /* button1() */
+ pan();
+ last_but = 1;
+ }
+ waitup();
+ if (last_but == 3 && last_hit >= 0) {
+ p = m3[last_hit];
+ c = p[strlen(p) - 1];
+ }
+ if (c == '?' && !confirm(last_but))
+ last_hit = -1;
+ return last_but;
+}
+
+Cursor deadmouse = {
+ { 0, 0}, /* offset */
+ { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x0C, 0x00, 0x82, 0x04, 0x41,
+ 0xFF, 0xE1, 0x5F, 0xF1, 0x3F, 0xFE, 0x17, 0xF0,
+ 0x03, 0xE0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, },
+ { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x0C, 0x00, 0x82, 0x04, 0x41,
+ 0xFF, 0xE1, 0x5F, 0xF1, 0x3F, 0xFE, 0x17, 0xF0,
+ 0x03, 0xE0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, }
+};
+
+Cursor blot ={
+ { 0, 0 },
+ { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, },
+ { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
+ 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, }
+};
+
+Cursor skull ={
+ { 0, 0 },
+ { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0x03,
+ 0xE7, 0xE7, 0x3F, 0xFC, 0x0F, 0xF0, 0x0D, 0xB0,
+ 0x07, 0xE0, 0x06, 0x60, 0x37, 0xEC, 0xE4, 0x27,
+ 0xC3, 0xC3, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, },
+ { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0x03,
+ 0xE7, 0xE7, 0x3F, 0xFC, 0x0F, 0xF0, 0x0D, 0xB0,
+ 0x07, 0xE0, 0x06, 0x60, 0x37, 0xEC, 0xE4, 0x27,
+ 0xC3, 0xC3, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, }
+};
+
+int
+confirm(int but) /* ask for confirmation if menu item ends with '?' */
+{
+ int c;
+ static int but_cvt[8] = { 0, 1, 2, 0, 3, 0, 0, 0 };
+
+ esetcursor(&skull);
+ c = waitdown();
+ waitup();
+ esetcursor(0);
+ return but == but_cvt[c];
+}