DLS takeover
[unix-history] / usr / src / local / ditroff / ditroff.old.okeeffe / gremlin.aed / gremlin / main.c
CommitLineData
70170e36 1/* @(#)main.c 1.2 %G%
e21828bb
DS
2 *
3 * Copyright -C- 1982 Barry S. Roitblat
4 *
5 *
6 * This is the main routine for the gremlin picture editor.
7 */
8
9
10#include "gremlin.h"
11#include "grem2.h"
12#include <signal.h>
13#include <sgtty.h>
14#include <sys/types.h>
15#include <sys/stat.h>
16
17/* imports from config.c */
18
19extern char GMapFile[];
20
21/* database imports */
22
23extern ELT *DBInit(), *DBRead();
24extern POINT *PTInit(), *PTMakePoint();
25
26/* imports from menu.c */
27
28extern MNInterpretCursor();
29extern MNIcon(), MNInitMenu(), MNDisplayMenu();
30
31/* graphics imports */
32extern GRInit(), GRClose();
33extern GRSetGrid(), GRDisplayGrid(), GRBlankGrid();
34extern GRDisableTablet(), GREnableTablet();
35extern GRSetMap(), GRsetwmask();
36extern artmode;
37
38/* imports from undodb.c */
39
40extern UNForget();
41extern UNELT *unlist, *unback;
42
43/* imports from long.c */
44
45extern char *Editfile;
46extern CP(), LGCommand();
47extern LGQuit();
48
49/* imports from short.c */
50
51extern SHCommand();
52extern SHRedis();
53extern SHUpdate();
54
55/* other */
56
57extern char *FindAED();
58
59/* Forward references within this file: */
60
61extern OnStop(), OnCommand();
62
63/* Imports from textio.c: */
64
65extern TxInit(), TxRedisplay(), TxClose(), TxPutMsg(), TxMsgOK();
66extern TxLine(), TxPutString();
67extern char TxGetChar();
68extern short inline;
69extern TxPutString();
70extern TXFIELD TAlign, TAdjust, TBrush, TFont, TGravity, TCSize;
71extern TXFIELD TEdit, TJustmode;
72
73
74/* Library routines: */
75
76extern char *malloc(), *sprintf(), *strcat(), *strcpy();
77
78#ifdef SIGTINT
79static int lintrup = LINTRUP; /* Constant for local mode bit */
80#endif SIGTINT
81
82/* Declaration of Globals */
83
84ELT *PICTURE, *cset, arhead;
85int CBRUSH, CFONT, CSIZE, CJUST, Gridsize, Gridon, Orientation;
86int Alignment, SEQ, Adjustment, GravityOn, Consume, CHANGED;
87float PX, PY, Lastx, Lasty;
88POINT *POINTLIST, *BACKPOINT, MENPOINT[NUSER];
89ELT *MEN[NUSER];
90char cmdbuf[400];
91int SEARCH = TRUE;
92int jmodes = 16;
93char *textpos[] = {"bl", "bc", "br", "cl", "cc", "cr", "tl", "tc", "tr",
94 "lb", "cb", "rb", "lc", "rc", "lt", "ct", "rt" };
95char *dispmode[] = {"BL", "BR", "CC", "XX", "XX", "XX", "XX", "XX",
96 "XX", "XX", "TL", "TC", "TR", "CL", "CR", "BC" };
97int textmode[] = { 0, 15, 1, 13, 2, 14, 10, 11, 12,
98 0, 15, 1, 13, 14, 10, 11, 12 };
99
100/* symbolic types, brushes, etc. */
101
102char *lines[] = { "broken", "dashed", "dotted",
103 "medium", "narrow", "thick", NULL };
104int lnum[] = { 2, 4, 1, 6, 5, 3 };
105char types[] = { 'l', 'r', 'c', 'v', 'a', 'u', '\0' };
106char *fonts[] = { "Bold", "Italics", "Roman", "Special",
107 "bold", "italics", "roman", "special", NULL };
108int fnum[] = { 3, 2, 1, 4, 3, 2, 1, 4 };
109
110error(s)
111char *s;
112/*
113 * This routine prints an error message and sets the Consume flag
114 * so that points are not cleared.
115 */
116{
117 putchar('\7');
118 TxPutMsg(s);
119 Consume = FALSE;
120}
121
70170e36 122
e21828bb
DS
123main(argc, argv)
124int argc;
125char *argv[];
126{
127 FILE *fp, *POpen(), *fopen(),*grtty, *tablet, *map, *startup;
128 POINT *p1, pos;
129 int x1, y1, x2, y2, i, j;
130 int button, cux, cuy;
131 char colours[768], msg[50], sw, *arg, *file;
132 char *ptr, *display, *type, *getenv(), home[100];
133 char *path = ".";
134 struct stat buf;
135 ino_t inode;
136
137 display = FindAED();
138 if (display == NULL) display = "/dev/null";
139 Orientation = 1;
140 file = NULL;
141
142 /* Parse the command line. */
143
144 argc -= 1; argv++; /* Skip program name. */
145 while (argc > 0)
146 {
147 argc -= 1;
148 arg = *argv++;
149 if (arg[0] != '-') file = arg;
150 else
151 {
152 sw = *++arg;
153 switch (sw)
154 {
155 case 'g':
156 if (*++arg == '\0')
157 if (argc-- > 0) arg = *argv++;
158 if (argc < 0) error("usage: gremlin -g <display name>");
159 display = arg;
160 if (*display != '/') display = strcat("/dev/", arg);
161 break;
162 case 'p':
163 if (*++arg == '\0')
164 if (argc-- > 0) arg = *argv++;
165 if (argc < 0) error("usage: gremlin -g <path>");
166 path = arg;
167 SEARCH = TRUE;
168 break;
169 case 'h':
170 Orientation = 0;
171 break;
172 case 'v':
173 Orientation = 1;
174 break;
175 default:
176 (void) sprintf(msg, "unknown switch: %c", sw);
177 error(msg);
178 }
179 }
180 }
181
182 PSetPath(path);
183 map = fopen(GMapFile, "r");
184 for (i=0; i<768; ++i) /* read in color map */
185 {
186 (void) fscanf(map,"%o",&j);
187 colours[i] = j&0377;
188 };
189
190 /* Open the display, and call all of the initialization routines.
191 * Initialize all of the globals defined in this file.
192 */
193 type = getenv("TERM");
194 TxInit(type);
195
196 /* Ignore quit signals, catch interrupts and stops. */
197
198 sigset(SIGINT, SIG_IGN);
199 sigset(SIGTSTP, OnStop);
200 sigset(SIGTTIN, OnStop);
201 sigset(SIGTTOU, OnStop);
202
203#ifdef SIGTINT
204 sigset(SIGTINT, OnCommand);
205 sighold(SIGTINT);
206#endif SIGTINT
207
208 grtty = fopen(display,"w");
209 if (grtty == NULL)
210 {
211 error("couldn't open display");
212 LGQuit(display);
213 };
214 tablet = fopen(display,"r");
215 if (tablet == NULL) tablet = fopen("/dev/null", "r");
216 GRInit(grtty,0);
217 GRSetMap(colours);
218
219#ifdef SIGTINT
220 (void) ioctl(fileno(stdin), TIOCLBIS, (char *) &lintrup);
221#endif SIGTINT
222
223 TxRedisplay(); /* display text screen */
224
225 CBRUSH = 6;
226 CFONT = 1;
227 CSIZE = 1;
228 CJUST = 0;
229 Gridon = FALSE;
230 Adjustment = NOADJ;
231 Alignment = 4;
232 artmode = FALSE;
233 SEQ = 0;
234 GravityOn = FALSE;
235 CHANGED = FALSE;
236 POINTLIST = PTInit();
237 BACKPOINT = PTInit();
238 unlist = unback = nullun;
239 p1 = PTInit(); /* initialize arrowhead template */
240 (void) PTMakePoint(0.0, 0.0, &p1);
241 (void) PTMakePoint(-5.0, 3.0, &p1);
242 (void) PTMakePoint(-3.0, 0.0, &p1);
243 (void) PTMakePoint(-5.0, -3.0, &p1);
244 (void) PTMakePoint(0.0, 0.0, &p1);
245 arhead.type = VECTOR;
246 arhead.ptlist = p1;
247 arhead.brushf = 0; /* brush filled in when used */
248 arhead.size = 0;
249 arhead.textpt = malloc(1);
250 *(arhead.textpt) = '\0';
251
252 PICTURE = DBInit(); /* initialize picture databse */
253 cset = DBInit(); /* and current set */
254 for (i=0; i<4; ++i) /* and user symbols */
255 MEN[i] = DBInit();
256 Editfile = malloc(100);
257 if (file == NULL)
258 *Editfile = '\0';
259 else
260 {
261 (void) strcpy(Editfile, file);
262 fp = POpen(Editfile, (char **) NULL, SEARCH);
263 if (fp == NULL) error("(creating new file)");
264 else PICTURE = DBRead(Editfile,&Orientation, &pos);
265 }
266 unlist = unback = nullun;
267 TxPutString(&TEdit, Editfile);
268 TxPutMsg(" Gremlin - Version 2.3 (1982)");
269 MNIcon();
270 MNInitMenu(Orientation); /* Initialize Menu */
271 SHUpdate(); /* Display menu and picture, if any */
272
273 if (Orientation == 0) /* initialize grid */
274 {
275 x1 = y1 = 0;
276 x2 = 511;
277 y2 = 395;
278 }
279 else
280 {
281 x1 = 116;
282 y1 = 0;
283 x2 = 511;
284 y2 = 483;
285 };
286 Gridsize = 16;
287 GRSetGrid(x1, y1, x2, y2, Gridsize);
288
289 /* read start-up file */
290 /* look in home directory */
291 sprintf(home,"%s/.gremlinrc",getenv("HOME"));
292 startup = fopen(home, "r");
293 if (startup != NULL)
294 {
295 fstat(startup, &buf);
296 inode = buf.st_ino;
297 ptr = fgets(cmdbuf, 400, startup);
298 while (ptr != NULL)
299 {
300 for (i=0; (cmdbuf[i] != '\n'); ++i)
301 if (i > 399) break;
302 cmdbuf[i] = '\0'; /* remove trailing carriage return */
303 if (cmdbuf[0] == ':') LGCommand(&(cmdbuf[1]));
304 else SHCommand(&(cmdbuf[0]));
305 ptr = fgets(cmdbuf, 400, startup);
306 } /* end while */
307 } /* end if startup */
308 else inode = 0;
309
310 /* look in current directory */
311 startup = fopen(".gremlinrc", "r");
312 if (startup != NULL)
313 {
314 fstat(startup, &buf);
315 if (buf.st_ino != inode) /* This isn't the same file as above */
316 {
317 ptr = fgets(cmdbuf, 400, startup);
318 while (ptr != NULL)
319 {
320 for (i=0; (cmdbuf[i] != '\n'); ++i)
321 if (i > 399) break;
322 cmdbuf[i] = '\0'; /* remove trailing carriage return */
323 if (cmdbuf[0] == ':') LGCommand(&(cmdbuf[1]));
324 else SHCommand(&(cmdbuf[0]));
325 ptr = fgets(cmdbuf, 400, startup);
326 } /* end while */
327 } /* end if buf */
328 } /* end if startup */
329
330 while ( TRUE ) /* Exits through the 'quit' command */
331 {
332 Consume = TRUE;
333 UNForget();
334
335#ifdef SIGTINT
336 GREnableTablet();
337 /* Allow keyboard interrupts while waiting
338 * for cursor input.
339 */
340 sigrelse(SIGTINT);
341 button = GRGetButton(tablet, &cux, &cuy);
342 /* Ignore keyboard interrupts while processing commands.
343 */
344 sighold(SIGTINT);
345 GRDisableTablet();
346 TxMsgOK();
347 MNInterpretCursor(button, cux, cuy);
348 if (Consume) CP();
349#else SIGTINT
350 i = 1 << fileno(stdin);
351 GREnableTablet();
352 i |= (1 << fileno(tablet));
353 (void) select(20, &i, 0, 10000000);
354 if (i & (1 << fileno(stdin)))
355 {
356 TxMsgOK();
357 OnCommand();
358 }
359 else
360 {
361 if ((button = GRGetButton(tablet, &cux, &cuy)) != -4)
362 {
363 GRDisableTablet();
364 TxMsgOK();
365 MNInterpretCursor(button, cux, cuy);
366 if (Consume) CP();
367 }
368 }
369#endif SIGTINT
370
371 } /* end while */
372
373} /* end main */
374
70170e36 375
e21828bb
DS
376OnStop(signo)
377int signo;
378
379/*-----------------------------------------------------------------------------
380 * This procedure handles stop signals.
381 *
382 * Results: None.
383 *
384 * Side Effects:
385 * The text display is reset, we wait to get restarted, then
386 * redisplay text.
387 *-----------------------------------------------------------------------------
388 */
389
390{
391 TxClose();
392 sigset(signo, SIG_DFL);
393 (void) kill(0, signo);
394 sigset(signo, OnStop);
395 SHRedis();
396}
397
70170e36 398
e21828bb
DS
399OnCommand()
400
401/*-----------------------------------------------------------------------------
402 * This routine responds to interrupts from the command terminal and
403 * then processes commands as long as there is input.
404 *
405 * Results: None.
406 *
407 * Side Effects:
408 * Whatever is done by the commands.
409 *-----------------------------------------------------------------------------
410 */
411
412{
413
414#ifdef SIGTINT
415 long charcount;
416#else SIGTINT
417 int i;
418#endif SIGTINT
419
420 static char cmd, lastcmd;
421 int repeat;
422
423 GRDisableTablet();
424
425#ifdef SIGTINT
426 (void) ioctl(fileno(stdin), TIOCLBIC, (char *) &lintrup);
427#endif SIGTINT
428
429
430 while (TRUE)
431 {
432
433 /* If there is no more input, then reenable the signal and return */
434
435
436#ifdef SIGTINT
437 (void) ioctl(fileno(stdin), FIONREAD, (char *) &charcount);
438 if (charcount == 0)
439 {
440 GREnableTablet();
441 (void) ioctl(fileno(stdin), TIOCLBIS, (char *) &lintrup);
442 return;
443 }
444#else SIGTINT
445 i = 1 << fileno(stdin);
446 if (select(20, &i, 0, 0) <= 0)
447 {
448 GREnableTablet();
449 return;
450 }
451#endif SIGTINT
452
453
454 /* Read the command and call the long or short command routine */
455
456 cmd = TxGetChar();
457 if (cmd == '.')
458 {
459 repeat = TRUE;
460 cmd = lastcmd;
461 }
462 else
463 {
464 repeat = FALSE;
465 lastcmd = cmd;
466 }
467 if (cmd == ':')
468 {
469 if (!repeat) TxGetLine(":",cmdbuf,400);
470 LGCommand(cmdbuf);
471 }
472 else
473 {
474 TxLine(inline);
70170e36 475 if (cmd != '\') putchar(cmd);
e21828bb
DS
476 (void) fflush(stdout);
477 SHCommand(&cmd);
478 }
479 TxLine(inline);
480 printf(" ");
481 TxLine(inline);
482 if (Consume) CP();
483 Consume = TRUE;
484 UNForget();
485 }
486}
487