|
|
1.1 root 1: #include "samterm.h"
2:
3: uchar *name[MAXFILES]; /* first byte is ' ' or '\'': modified state */
4: Text *text[MAXFILES]; /* pointer to Text associated with file */
5: ushort tag[MAXFILES]; /* text[i].tag, even if text[i] not defined */
6: int nname;
7: char *genmenu3();
8: char *genmenu2();
9: char *genmenu2c();
10: Text *sweeptext();
11: /* enum Menu2 -- until we fix the C compile to treat enums like ints */
12: #define Cut 0
13: #define Paste 1
14: #define Snarf 2
15: #define Look 3
16: #define Exch 4
17: #define Search 5
18: #define NMENU2 Search
19: #define Send Search
20: #define Scroll 6
21: #define NMENU2C 7
22:
23: /* enum Menu3 */
24: #define New 0
25: #define Xerox 1
26: #define Reshape 2
27: #define Close 3
28: #define Write 4
29: #define NMENU3 5
30:
31: char *menu2str[]={
32: "cut",
33: "paste",
34: "snarf",
35: "look",
36: "<mux>",
37: 0, /* storage for last pattern */
38: };
39: char *menu3str[]={
40: "new",
41: "xerox",
42: "reshape",
43: "close",
44: "write",
45: };
46: Menu menu2={0, genmenu2};
47: Menu menu2c={0, genmenu2c};
48: Menu menu3={0, genmenu3};
49: menu2hit()
50: {
51: register Text *t=(Text *)which->user1;
52: register w=which-t->l;
53: switch(menuhit(t==&cmd? &menu2c : &menu2, 2)){
54: case Cut:
55: if(!lock && !t->lock)
56: cut(t, w, 1);
57: break;
58: case Paste:
59: if(!lock && !t->lock)
60: paste(t, w);
61: break;
62: case Snarf:
63: if(!lock && !t->lock)
64: snarf(t, w);
65: break;
66: case Exch:
67: outT0(Tstartsnarf);
68: setlock();
69: break;
70: case Look:
71: outTsll(Tlook, t->tag, which->p0, which->p1);
72: break;
73: case Search:
74: outcmd();
75: if(t==&cmd)
76: outTsll(Tsend, 0 /*ignored*/, which->p0, which->p1);
77: else
78: outT0(Tsearch);
79: break;
80: case Scroll:
81: if(cmd.l[w].user0^=1)
82: center(&cmd.l[w], t->rasp.nbytes);
83: break;
84: }
85: }
86: menu3hit()
87: {
88: Rectangle r;
89: register Flayer *l;
90: register m, i;
91: register Text *t;
92: switch(m=menuhit(&menu3, 3)){
93: case -1:
94: break;
95: case New:
96: sweeptext(1, 0);
97: break;
98: case Xerox:
99: case Reshape:
100: cursswitch(&bullseye);
101: buttons(Down);
102: if(button3() && (l=flwhich(mouse.xy)) && getr(&r, 1))
103: duplicate(l, r, l->f.font, m==Reshape);
104: else
105: cursswitch(cursor);
106: buttons(Up);
107: break;
108: case Close:
109: cursswitch(&bullseye);
110: buttons(Down);
111: if(button3() && (l=flwhich(mouse.xy)) && !lock){
112: t=(Text *)l->user1;
113: if(t!=&cmd || t->nwin>1){
114: if(t->nwin>1)
115: Sclose(l);
116: else
117: outTs(Tclose, t->tag);
118: }
119: }
120: cursswitch(cursor);
121: buttons(Up);
122: break;
123: case Write:
124: cursswitch(&bullseye);
125: buttons(Down);
126: if(button3() && (l=flwhich(mouse.xy)))
127: outTs(Twrite, ((Text *)l->user1)->tag);
128: cursswitch(cursor);
129: buttons(Up);
130: break;
131: default:
132: if(t=text[m-NMENU3]){
133: i=t->front;
134: if(t->nwin==0 || t->l[i].textfn==0)
135: return; /* not ready yet; try again later */
136: if(t->nwin>1 && which==&t->l[i])
137: do
138: if(++i==NL)
139: i=0;
140: while(i!=t->front && t->l[i].textfn==0);
141: current(&t->l[i]);
142: }else
143: sweeptext(0, tag[m-NMENU3]);
144: break;
145: }
146: }
147: Text *
148: sweeptext(new, tag)
149: {
150: Rectangle r;
151: register Text *t;
152: if(getr(&r, 1) && (t=(Text *)alloc(sizeof(Text)))){
153: current((Flayer *)0);
154: flnew(&t->l[0], gettext, 0, (char *)t);
155: flinit(&t->l[0], r, &defont);
156: t->nwin=1;
157: rinit(&t->rasp);
158: if(new)
159: startnewfile(Tstartnewfile, t);
160: else{
161: rinit(&t->rasp);
162: t->tag=tag;
163: startfile(t);
164: }
165: return t;
166: }
167: return 0;
168: }
169: whichmenu(tg)
170: register tg;
171: {
172: register i;
173: for(i=0; i<nname; i++)
174: if(tag[i]==tg)
175: return i;
176: return -1;
177: }
178: menuins(n, s, t, m, tg)
179: uchar *s;
180: Text *t;
181: {
182: register i;
183: if(nname==MAXFILES)
184: panic("menuins");
185: for(i=nname; i>n; --i)
186: name[i]=name[i-1], text[i]=text[i-1], tag[i]=tag[i-1];
187: text[n]=t;
188: tag[n]=tg;
189: name[n]=ALLOC(strlen(s)+2);
190: name[n][0]=m;
191: copystr(s, name[n]+1);
192: nname++;
193: /* ehg's hack, implemented by rob: make this guy pop up under menu */
194: /* non-jerq implementers: delete the rest of this procedure */
195: #define MENULINES 16
196: if((n+=NMENU3)<16)
197: menu3.prevtop=0;
198: else if(n>nname+NMENU3-MENULINES){
199: menu3.prevtop=nname+NMENU3-MENULINES;
200: }else
201: menu3.prevtop=n-MENULINES/2;
202: menu3.prevhit=n-menu3.prevtop;
203: }
204: menudel(n){
205: register i;
206: if(nname==0 || n>=nname || text[n])
207: panic("menudel");
208: free(name[n]);
209: --nname;
210: for(i=n; i<nname; i++)
211: name[i]=name[i+1], text[i]=text[i+1], tag[i]=tag[i+1];
212: }
213: setpat(s)
214: register char *s;
215: {
216: static char pat[17];
217: pat[0]='/';
218: strcpy(pat+1, s); /* host guarantees it fits */
219: menu2str[Search]=pat;
220: }
221: static uchar buf[64]={' ', ' ', ' ', ' '};
222: char *
223: paren(s)
224: register char *s;
225: {
226: register uchar *t=buf;
227: *t++='(';
228: do; while(*t++= *s++);
229: t[-1]=')';
230: *t=0;
231: return (char *)buf;
232: }
233: char *
234: genmenu2(n)
235: register n;
236: {
237: register Text *t=(Text *)which->user1;
238: register char *p;
239: if(n>=NMENU2+(menu2str[Search]!=0))
240: return 0;
241: p=menu2str[n];
242: if(!lock && !t->lock || n==Search || n==Look)
243: return p;
244: return paren(p);
245: }
246: char *
247: genmenu2c(n)
248: register n;
249: {
250: register Text *t=(Text *)which->user1;
251: register char *p;
252: if(n>=NMENU2C)
253: return 0;
254: if(n==Scroll)
255: p=which->user0? "noscroll" : "scroll";
256: else if(n==Send)
257: p="send";
258: else
259: p=menu2str[n];
260: if(!lock && !t->lock)
261: return p;
262: return paren(p);
263: }
264: char *
265: genmenu3(n)
266: register n;
267: {
268: register Text *t;
269: register i;
270: if(n>=(int)NMENU3+nname)
271: return 0;
272: if(n<(int)NMENU3)
273: return menu3str[n];
274: n-=(int)NMENU3;
275: if(n==0) /* unless we've been fooled, this is cmd */
276: return (char *)&name[n][1];
277: t=text[n];
278: buf[0]=name[n][0];
279: buf[1]='-';
280: buf[2]=' ';
281: buf[3]=' ';
282: if(t){
283: if(t->nwin==1)
284: buf[1]='+';
285: else if(t->nwin>1)
286: buf[1]='*';
287: if(work && t==(Text *)work->user1)
288: buf[2]='.';
289: }
290: if((i=strlen(name[n]+1))>sizeof buf-4-2){
291: int c, k;
292: k=sizeof buf/2;
293: c=name[n][k];
294: name[n][k]=0;
295: copystr(name[n]+1, buf+4);
296: name[n][k]=c;
297: copystr((uchar *)"...", buf+4+k-1);
298: copystr(name[n]+1+i-(sizeof buf-4-k-4), buf+4+k+2);
299: }else
300: copystr(name[n]+1, buf+4);
301: i=strlen(buf);
302: buf[i++]='\240';
303: buf[i]=0;
304: return (char *)buf;
305: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.