|
|
1.1 root 1: /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
2: /* hack.topl.c - version 1.0.2 */
3:
4: #include "hack.h"
5: #include <stdio.h>
6: extern char *eos();
7: extern int CO;
8:
9: char toplines[BUFSZ];
10: xchar tlx, tly; /* set by pline; used by addtopl */
11:
12: struct topl {
13: struct topl *next_topl;
14: char *topl_text;
15: } *old_toplines, *last_redone_topl;
16: #define OTLMAX 20 /* max nr of old toplines remembered */
17:
18: doredotopl(){
19: if(last_redone_topl)
20: last_redone_topl = last_redone_topl->next_topl;
21: if(!last_redone_topl)
22: last_redone_topl = old_toplines;
23: if(last_redone_topl){
24: (void) strcpy(toplines, last_redone_topl->topl_text);
25: }
26: redotoplin();
27: return(0);
28: }
29:
30: redotoplin() {
31: home();
32: if(index(toplines, '\n')) cl_end();
33: putstr(toplines);
34: cl_end();
35: tlx = curx;
36: tly = cury;
37: flags.toplin = 1;
38: if(tly > 1)
39: more();
40: }
41:
42: remember_topl() {
43: register struct topl *tl;
44: register int cnt = OTLMAX;
45: if(last_redone_topl &&
46: !strcmp(toplines, last_redone_topl->topl_text)) return;
47: if(old_toplines &&
48: !strcmp(toplines, old_toplines->topl_text)) return;
49: last_redone_topl = 0;
50: tl = (struct topl *)
51: alloc((unsigned)(strlen(toplines) + sizeof(struct topl) + 1));
52: tl->next_topl = old_toplines;
53: tl->topl_text = (char *)(tl + 1);
54: (void) strcpy(tl->topl_text, toplines);
55: old_toplines = tl;
56: while(cnt && tl){
57: cnt--;
58: tl = tl->next_topl;
59: }
60: if(tl && tl->next_topl){
61: free((char *) tl->next_topl);
62: tl->next_topl = 0;
63: }
64: }
65:
66: addtopl(s) char *s; {
67: curs(tlx,tly);
68: if(tlx + strlen(s) > CO) putsym('\n');
69: putstr(s);
70: tlx = curx;
71: tly = cury;
72: flags.toplin = 1;
73: }
74:
75: xmore(s)
76: char *s; /* allowed chars besides space/return */
77: {
78: if(flags.toplin) {
79: curs(tlx, tly);
80: if(tlx + 8 > CO) putsym('\n'), tly++;
81: }
82:
83: if(flags.standout)
84: standoutbeg();
85: putstr("--More--");
86: if(flags.standout)
87: standoutend();
88:
89: xwaitforspace(s);
90: if(flags.toplin && tly > 1) {
91: home();
92: cl_end();
93: docorner(1, tly-1);
94: }
95: flags.toplin = 0;
96: }
97:
98: more(){
99: xmore("");
100: }
101:
102: cmore(s)
103: register char *s;
104: {
105: xmore(s);
106: }
107:
108: clrlin(){
109: if(flags.toplin) {
110: home();
111: cl_end();
112: if(tly > 1) docorner(1, tly-1);
113: remember_topl();
114: }
115: flags.toplin = 0;
116: }
117:
118: /*VARARGS1*/
119: pline(line,arg1,arg2,arg3,arg4,arg5,arg6)
120: register char *line,*arg1,*arg2,*arg3,*arg4,*arg5,*arg6;
121: {
122: char pbuf[BUFSZ];
123: register char *bp = pbuf, *tl;
124: register int n,n0;
125:
126: if(!line || !*line) return;
127: if(!index(line, '%')) (void) strcpy(pbuf,line); else
128: (void) sprintf(pbuf,line,arg1,arg2,arg3,arg4,arg5,arg6);
129: if(flags.toplin == 1 && !strcmp(pbuf, toplines)) return;
130: nscr(); /* %% */
131:
132: /* If there is room on the line, print message on same line */
133: /* But messages like "You die..." deserve their own line */
134: n0 = strlen(bp);
135: if(flags.toplin == 1 && tly == 1 &&
136: n0 + strlen(toplines) + 3 < CO-8 && /* leave room for --More-- */
137: strncmp(bp, "You ", 4)) {
138: (void) strcat(toplines, " ");
139: (void) strcat(toplines, bp);
140: tlx += 2;
141: addtopl(bp);
142: return;
143: }
144: if(flags.toplin == 1) more();
145: remember_topl();
146: toplines[0] = 0;
147: while(n0){
148: if(n0 >= CO){
149: /* look for appropriate cut point */
150: n0 = 0;
151: for(n = 0; n < CO; n++) if(bp[n] == ' ')
152: n0 = n;
153: if(!n0) for(n = 0; n < CO-1; n++)
154: if(!letter(bp[n])) n0 = n;
155: if(!n0) n0 = CO-2;
156: }
157: (void) strncpy((tl = eos(toplines)), bp, n0);
158: tl[n0] = 0;
159: bp += n0;
160:
161: /* remove trailing spaces, but leave one */
162: while(n0 > 1 && tl[n0-1] == ' ' && tl[n0-2] == ' ')
163: tl[--n0] = 0;
164:
165: n0 = strlen(bp);
166: if(n0 && tl[0]) (void) strcat(tl, "\n");
167: }
168: redotoplin();
169: }
170:
171: putsym(c) char c; {
172: switch(c) {
173: case '\b':
174: backsp();
175: return;
176: case '\n':
177: curx = 1;
178: cury++;
179: if(cury > tly) tly = cury;
180: break;
181: default:
182: if(curx == CO)
183: putsym('\n'); /* 1 <= curx <= CO; avoid CO */
184: else
185: curx++;
186: }
187: (void) putchar(c);
188: }
189:
190: putstr(s) register char *s; {
191: while(*s) putsym(*s++);
192: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.