Blame


1 cfabc3ed 2003-11-23 devnull #include "9term.h"
2 cfabc3ed 2003-11-23 devnull
3 cfabc3ed 2003-11-23 devnull Rectangle scrollr; /* scroll bar rectangle */
4 cfabc3ed 2003-11-23 devnull Rectangle lastsr; /* used for scroll bar */
5 cfabc3ed 2003-11-23 devnull int holdon; /* hold mode */
6 3fd755b7 2003-12-04 devnull int rawon; /* raw mode */
7 cfabc3ed 2003-11-23 devnull int scrolling; /* window scrolls */
8 cfabc3ed 2003-11-23 devnull int clickmsec; /* time of last click */
9 cfabc3ed 2003-11-23 devnull uint clickq0; /* point of last click */
10 cfabc3ed 2003-11-23 devnull int rcfd[2];
11 cfabc3ed 2003-11-23 devnull int rcpid;
12 cfabc3ed 2003-11-23 devnull int maxtab;
13 cfabc3ed 2003-11-23 devnull Mousectl* mc;
14 cfabc3ed 2003-11-23 devnull Keyboardctl* kc;
15 cfabc3ed 2003-11-23 devnull Channel* hostc;
16 cfabc3ed 2003-11-23 devnull Readbuf rcbuf[2];
17 cfabc3ed 2003-11-23 devnull int mainpid;
18 cfabc3ed 2003-11-23 devnull int plumbfd;
19 d3acba95 2003-12-04 devnull int button2exec;
20 cfabc3ed 2003-11-23 devnull int label(Rune*, int);
21 cfabc3ed 2003-11-23 devnull char wdir[1024];
22 21a17ff3 2003-11-25 devnull char childwdir[1024];
23 cfabc3ed 2003-11-23 devnull void hangupnote(void*, char*);
24 cfabc3ed 2003-11-23 devnull
25 cfabc3ed 2003-11-23 devnull char *menu2str[] = {
26 cfabc3ed 2003-11-23 devnull "cut",
27 cfabc3ed 2003-11-23 devnull "paste",
28 cfabc3ed 2003-11-23 devnull "snarf",
29 cfabc3ed 2003-11-23 devnull "send",
30 cfabc3ed 2003-11-23 devnull "scroll",
31 cfabc3ed 2003-11-23 devnull "plumb",
32 cfabc3ed 2003-11-23 devnull 0
33 cfabc3ed 2003-11-23 devnull };
34 cfabc3ed 2003-11-23 devnull
35 cfabc3ed 2003-11-23 devnull Image* cols[NCOL];
36 cfabc3ed 2003-11-23 devnull Image* hcols[NCOL];
37 cfabc3ed 2003-11-23 devnull Image *plumbcolor;
38 d3acba95 2003-12-04 devnull Image *execcolor;
39 cfabc3ed 2003-11-23 devnull
40 cfabc3ed 2003-11-23 devnull Menu menu2 =
41 cfabc3ed 2003-11-23 devnull {
42 cfabc3ed 2003-11-23 devnull menu2str
43 cfabc3ed 2003-11-23 devnull };
44 cfabc3ed 2003-11-23 devnull
45 cfabc3ed 2003-11-23 devnull Text t;
46 cfabc3ed 2003-11-23 devnull
47 cfabc3ed 2003-11-23 devnull Cursor whitearrow = {
48 cfabc3ed 2003-11-23 devnull {0, 0},
49 cfabc3ed 2003-11-23 devnull {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFC,
50 cfabc3ed 2003-11-23 devnull 0xFF, 0xF0, 0xFF, 0xF0, 0xFF, 0xF8, 0xFF, 0xFC,
51 cfabc3ed 2003-11-23 devnull 0xFF, 0xFE, 0xFF, 0xFF, 0xFF, 0xFE, 0xFF, 0xFC,
52 cfabc3ed 2003-11-23 devnull 0xF3, 0xF8, 0xF1, 0xF0, 0xE0, 0xE0, 0xC0, 0x40, },
53 cfabc3ed 2003-11-23 devnull {0xFF, 0xFF, 0xFF, 0xFF, 0xC0, 0x06, 0xC0, 0x1C,
54 cfabc3ed 2003-11-23 devnull 0xC0, 0x30, 0xC0, 0x30, 0xC0, 0x38, 0xC0, 0x1C,
55 cfabc3ed 2003-11-23 devnull 0xC0, 0x0E, 0xC0, 0x07, 0xCE, 0x0E, 0xDF, 0x1C,
56 cfabc3ed 2003-11-23 devnull 0xD3, 0xB8, 0xF1, 0xF0, 0xE0, 0xE0, 0xC0, 0x40, }
57 cfabc3ed 2003-11-23 devnull };
58 cfabc3ed 2003-11-23 devnull
59 cfabc3ed 2003-11-23 devnull void
60 d3acba95 2003-12-04 devnull usage(void)
61 d3acba95 2003-12-04 devnull {
62 3fd755b7 2003-12-04 devnull fprint(2, "usage: 9term [-ars] [cmd ...]\n");
63 d3acba95 2003-12-04 devnull threadexitsall("usage");
64 d3acba95 2003-12-04 devnull }
65 d3acba95 2003-12-04 devnull
66 d3acba95 2003-12-04 devnull void
67 cfabc3ed 2003-11-23 devnull threadmain(int argc, char *argv[])
68 cfabc3ed 2003-11-23 devnull {
69 cfabc3ed 2003-11-23 devnull char *p;
70 cfabc3ed 2003-11-23 devnull
71 cfabc3ed 2003-11-23 devnull rfork(RFNOTEG);
72 cfabc3ed 2003-11-23 devnull mainpid = getpid();
73 cfabc3ed 2003-11-23 devnull ARGBEGIN{
74 d3acba95 2003-12-04 devnull default:
75 d3acba95 2003-12-04 devnull usage();
76 d3acba95 2003-12-04 devnull case 'a': /* acme mode */
77 d3acba95 2003-12-04 devnull button2exec++;
78 cfabc3ed 2003-11-23 devnull break;
79 3fd755b7 2003-12-04 devnull case 'r':
80 3fd755b7 2003-12-04 devnull /* not clear this is useful */
81 3fd755b7 2003-12-04 devnull rawon = 1;
82 3fd755b7 2003-12-04 devnull break;
83 cfabc3ed 2003-11-23 devnull case 's':
84 cfabc3ed 2003-11-23 devnull scrolling++;
85 cfabc3ed 2003-11-23 devnull break;
86 cfabc3ed 2003-11-23 devnull }ARGEND
87 cfabc3ed 2003-11-23 devnull
88 cfabc3ed 2003-11-23 devnull p = getenv("tabstop");
89 cfabc3ed 2003-11-23 devnull if(p == 0)
90 cfabc3ed 2003-11-23 devnull p = getenv("TABSTOP");
91 cfabc3ed 2003-11-23 devnull if(p != 0 && maxtab <= 0)
92 cfabc3ed 2003-11-23 devnull maxtab = strtoul(p, 0, 0);
93 cfabc3ed 2003-11-23 devnull if(maxtab <= 0)
94 cfabc3ed 2003-11-23 devnull maxtab = 8;
95 cfabc3ed 2003-11-23 devnull
96 cfabc3ed 2003-11-23 devnull initdraw(nil, nil, "9term");
97 cfabc3ed 2003-11-23 devnull notify(hangupnote);
98 cfabc3ed 2003-11-23 devnull
99 cfabc3ed 2003-11-23 devnull mc = initmouse(nil, screen);
100 cfabc3ed 2003-11-23 devnull kc = initkeyboard(nil);
101 d3acba95 2003-12-04 devnull rcstart(rcfd, argc, argv);
102 cfabc3ed 2003-11-23 devnull hoststart();
103 cfabc3ed 2003-11-23 devnull plumbstart();
104 cfabc3ed 2003-11-23 devnull
105 cfabc3ed 2003-11-23 devnull t.f = mallocz(sizeof(Frame), 1);
106 cfabc3ed 2003-11-23 devnull
107 cfabc3ed 2003-11-23 devnull cols[BACK] = allocimagemix(display, DPaleyellow, DWhite);
108 cfabc3ed 2003-11-23 devnull cols[HIGH] = allocimage(display, Rect(0, 0, 1, 1), screen->chan, 1, DDarkyellow);
109 cfabc3ed 2003-11-23 devnull cols[BORD] = allocimage(display, Rect(0, 0, 1, 1), screen->chan, 1, DYellowgreen);
110 cfabc3ed 2003-11-23 devnull cols[TEXT] = display->black;
111 cfabc3ed 2003-11-23 devnull cols[HTEXT] = display->black;
112 cfabc3ed 2003-11-23 devnull
113 cfabc3ed 2003-11-23 devnull hcols[BACK] = cols[BACK];
114 cfabc3ed 2003-11-23 devnull hcols[HIGH] = cols[HIGH];
115 5af29cd3 2003-12-04 devnull hcols[BORD] = allocimage(display, Rect(0, 0, 1, 1), screen->chan, 1, 0x006600FF);
116 cfabc3ed 2003-11-23 devnull hcols[TEXT] = hcols[BORD];
117 cfabc3ed 2003-11-23 devnull hcols[HTEXT] = hcols[TEXT];
118 cfabc3ed 2003-11-23 devnull
119 cfabc3ed 2003-11-23 devnull plumbcolor = allocimage(display, Rect(0,0,1,1), screen->chan, 1, 0x006600FF);
120 d3acba95 2003-12-04 devnull execcolor = allocimage(display, Rect(0,0,1,1), screen->chan, 1, 0xAA0000FF);
121 cfabc3ed 2003-11-23 devnull
122 cfabc3ed 2003-11-23 devnull draw(screen, screen->r, cols[BACK], nil, ZP);
123 cfabc3ed 2003-11-23 devnull geom();
124 cfabc3ed 2003-11-23 devnull loop();
125 cfabc3ed 2003-11-23 devnull }
126 cfabc3ed 2003-11-23 devnull
127 cfabc3ed 2003-11-23 devnull void
128 cfabc3ed 2003-11-23 devnull hangupnote(void *a, char *msg)
129 cfabc3ed 2003-11-23 devnull {
130 cfabc3ed 2003-11-23 devnull if(getpid() != mainpid)
131 cfabc3ed 2003-11-23 devnull noted(NDFLT);
132 cfabc3ed 2003-11-23 devnull if(strcmp(msg, "hangup") == 0 && rcpid != 0){
133 669250d1 2003-12-03 devnull postnote(PNGROUP, rcpid, "hangup");
134 cfabc3ed 2003-11-23 devnull noted(NDFLT);
135 cfabc3ed 2003-11-23 devnull }
136 cfabc3ed 2003-11-23 devnull noted(NDFLT);
137 cfabc3ed 2003-11-23 devnull }
138 cfabc3ed 2003-11-23 devnull
139 cfabc3ed 2003-11-23 devnull void
140 cfabc3ed 2003-11-23 devnull hostproc(void *arg)
141 cfabc3ed 2003-11-23 devnull {
142 cfabc3ed 2003-11-23 devnull Channel *c;
143 cfabc3ed 2003-11-23 devnull int i, n, which;
144 cfabc3ed 2003-11-23 devnull
145 cfabc3ed 2003-11-23 devnull c = arg;
146 cfabc3ed 2003-11-23 devnull
147 cfabc3ed 2003-11-23 devnull i = 0;
148 cfabc3ed 2003-11-23 devnull for(;;){
149 cfabc3ed 2003-11-23 devnull i = 1-i; /* toggle */
150 cfabc3ed 2003-11-23 devnull n = read(rcfd[0], rcbuf[i].data, sizeof rcbuf[i].data);
151 cfabc3ed 2003-11-23 devnull if(n <= 0){
152 cfabc3ed 2003-11-23 devnull if(n < 0)
153 cfabc3ed 2003-11-23 devnull fprint(2, "9term: host read error: %r\n");
154 cfabc3ed 2003-11-23 devnull threadexitsall("host");
155 cfabc3ed 2003-11-23 devnull }
156 cfabc3ed 2003-11-23 devnull rcbuf[i].n = n;
157 cfabc3ed 2003-11-23 devnull which = i;
158 cfabc3ed 2003-11-23 devnull send(c, &which);
159 cfabc3ed 2003-11-23 devnull }
160 cfabc3ed 2003-11-23 devnull }
161 cfabc3ed 2003-11-23 devnull
162 cfabc3ed 2003-11-23 devnull void
163 cfabc3ed 2003-11-23 devnull hoststart(void)
164 cfabc3ed 2003-11-23 devnull {
165 cfabc3ed 2003-11-23 devnull hostc = chancreate(sizeof(int), 0);
166 1ccf253e 2003-12-02 devnull proccreate(hostproc, hostc, 32*1024);
167 cfabc3ed 2003-11-23 devnull }
168 cfabc3ed 2003-11-23 devnull
169 cfabc3ed 2003-11-23 devnull void
170 cfabc3ed 2003-11-23 devnull loop(void)
171 cfabc3ed 2003-11-23 devnull {
172 cfabc3ed 2003-11-23 devnull Rune r;
173 cfabc3ed 2003-11-23 devnull int i;
174 cfabc3ed 2003-11-23 devnull Alt a[] = {
175 cfabc3ed 2003-11-23 devnull {mc->c, &mc->m, CHANRCV},
176 cfabc3ed 2003-11-23 devnull {kc->c, &r, CHANRCV},
177 cfabc3ed 2003-11-23 devnull {hostc, &i, CHANRCV},
178 cfabc3ed 2003-11-23 devnull {mc->resizec, nil, CHANRCV},
179 cfabc3ed 2003-11-23 devnull {nil, nil, CHANEND},
180 cfabc3ed 2003-11-23 devnull };
181 cfabc3ed 2003-11-23 devnull
182 cfabc3ed 2003-11-23 devnull for(;;) {
183 cfabc3ed 2003-11-23 devnull tcheck();
184 cfabc3ed 2003-11-23 devnull
185 cfabc3ed 2003-11-23 devnull scrdraw();
186 cfabc3ed 2003-11-23 devnull flushimage(display, 1);
187 cfabc3ed 2003-11-23 devnull a[2].op = CHANRCV;
188 cfabc3ed 2003-11-23 devnull if(!scrolling && t.qh > t.org+t.f->nchars)
189 cfabc3ed 2003-11-23 devnull a[2].op = CHANNOP;;
190 cfabc3ed 2003-11-23 devnull switch(alt(a)) {
191 cfabc3ed 2003-11-23 devnull default:
192 cfabc3ed 2003-11-23 devnull fatal("impossible");
193 cfabc3ed 2003-11-23 devnull case 0:
194 cfabc3ed 2003-11-23 devnull t.m = mc->m;
195 cfabc3ed 2003-11-23 devnull mouse();
196 cfabc3ed 2003-11-23 devnull break;
197 cfabc3ed 2003-11-23 devnull case 1:
198 cfabc3ed 2003-11-23 devnull key(r);
199 cfabc3ed 2003-11-23 devnull break;
200 cfabc3ed 2003-11-23 devnull case 2:
201 cfabc3ed 2003-11-23 devnull conswrite(rcbuf[i].data, rcbuf[i].n);
202 cfabc3ed 2003-11-23 devnull break;
203 cfabc3ed 2003-11-23 devnull case 3:
204 cfabc3ed 2003-11-23 devnull doreshape();
205 cfabc3ed 2003-11-23 devnull break;
206 cfabc3ed 2003-11-23 devnull }
207 cfabc3ed 2003-11-23 devnull }
208 cfabc3ed 2003-11-23 devnull }
209 cfabc3ed 2003-11-23 devnull
210 cfabc3ed 2003-11-23 devnull void
211 cfabc3ed 2003-11-23 devnull doreshape(void)
212 cfabc3ed 2003-11-23 devnull {
213 cfabc3ed 2003-11-23 devnull if(getwindow(display, Refnone) < 0)
214 cfabc3ed 2003-11-23 devnull fatal("can't reattach to window");
215 cfabc3ed 2003-11-23 devnull draw(screen, screen->r, cols[BACK], nil, ZP);
216 cfabc3ed 2003-11-23 devnull geom();
217 cfabc3ed 2003-11-23 devnull scrdraw();
218 cfabc3ed 2003-11-23 devnull }
219 cfabc3ed 2003-11-23 devnull
220 669250d1 2003-12-03 devnull struct winsize ows;
221 669250d1 2003-12-03 devnull
222 cfabc3ed 2003-11-23 devnull void
223 cfabc3ed 2003-11-23 devnull geom(void)
224 cfabc3ed 2003-11-23 devnull {
225 669250d1 2003-12-03 devnull struct winsize ws;
226 669250d1 2003-12-03 devnull Point p;
227 cfabc3ed 2003-11-23 devnull Rectangle r;
228 cfabc3ed 2003-11-23 devnull
229 cfabc3ed 2003-11-23 devnull r = screen->r;
230 cfabc3ed 2003-11-23 devnull scrollr = screen->r;
231 cfabc3ed 2003-11-23 devnull scrollr.max.x = r.min.x+Scrollwid;
232 cfabc3ed 2003-11-23 devnull lastsr = Rect(0,0,0,0);
233 cfabc3ed 2003-11-23 devnull
234 cfabc3ed 2003-11-23 devnull r.min.x += Scrollwid+Scrollgap;
235 cfabc3ed 2003-11-23 devnull
236 cfabc3ed 2003-11-23 devnull frclear(t.f, 0);
237 cfabc3ed 2003-11-23 devnull frinit(t.f, r, font, screen, holdon ? hcols : cols);
238 cfabc3ed 2003-11-23 devnull t.f->maxtab = maxtab*stringwidth(font, "0");
239 cfabc3ed 2003-11-23 devnull fill();
240 cfabc3ed 2003-11-23 devnull updatesel();
241 669250d1 2003-12-03 devnull
242 669250d1 2003-12-03 devnull p = stringsize(font, "0");
243 669250d1 2003-12-03 devnull if(p.x == 0 || p.y == 0)
244 669250d1 2003-12-03 devnull return;
245 669250d1 2003-12-03 devnull
246 669250d1 2003-12-03 devnull ws.ws_row = Dy(r)/p.y;
247 669250d1 2003-12-03 devnull ws.ws_col = Dx(r)/p.x;
248 669250d1 2003-12-03 devnull ws.ws_xpixel = Dx(r);
249 669250d1 2003-12-03 devnull ws.ws_ypixel = Dy(r);
250 669250d1 2003-12-03 devnull if(ws.ws_row != ows.ws_row || ws.ws_col != ows.ws_col)
251 669250d1 2003-12-03 devnull if(ioctl(rcfd[0], TIOCSWINSZ, &ws) < 0)
252 669250d1 2003-12-03 devnull fprint(2, "ioctl: %r\n");
253 cfabc3ed 2003-11-23 devnull }
254 cfabc3ed 2003-11-23 devnull
255 cfabc3ed 2003-11-23 devnull void
256 cfabc3ed 2003-11-23 devnull drawhold(int holdon)
257 cfabc3ed 2003-11-23 devnull {
258 cfabc3ed 2003-11-23 devnull if(holdon)
259 cfabc3ed 2003-11-23 devnull setcursor(mc, &whitearrow);
260 cfabc3ed 2003-11-23 devnull else
261 cfabc3ed 2003-11-23 devnull setcursor(mc, nil);
262 cfabc3ed 2003-11-23 devnull
263 cfabc3ed 2003-11-23 devnull draw(screen, screen->r, cols[BACK], nil, ZP);
264 cfabc3ed 2003-11-23 devnull geom();
265 cfabc3ed 2003-11-23 devnull scrdraw();
266 cfabc3ed 2003-11-23 devnull }
267 cfabc3ed 2003-11-23 devnull
268 d3acba95 2003-12-04 devnull void
269 d3acba95 2003-12-04 devnull wordclick(uint *q0, uint *q1)
270 d3acba95 2003-12-04 devnull {
271 d3acba95 2003-12-04 devnull while(*q1<t.nr && !isspace(t.r[*q1]))
272 d3acba95 2003-12-04 devnull (*q1)++;
273 d3acba95 2003-12-04 devnull while(*q0>0 && !isspace(t.r[*q0-1]))
274 d3acba95 2003-12-04 devnull (*q0)--;
275 d3acba95 2003-12-04 devnull }
276 cfabc3ed 2003-11-23 devnull
277 d3acba95 2003-12-04 devnull int
278 d3acba95 2003-12-04 devnull aselect(uint *q0, uint *q1, Image *color)
279 d3acba95 2003-12-04 devnull {
280 d3acba95 2003-12-04 devnull int cancel;
281 d3acba95 2003-12-04 devnull uint oldq0, oldq1, newq0, newq1;
282 d3acba95 2003-12-04 devnull
283 d3acba95 2003-12-04 devnull /* save old selection */
284 d3acba95 2003-12-04 devnull oldq0 = t.q0;
285 d3acba95 2003-12-04 devnull oldq1 = t.q1;
286 d3acba95 2003-12-04 devnull
287 d3acba95 2003-12-04 devnull /* sweep out area and record it */
288 d3acba95 2003-12-04 devnull t.f->cols[HIGH] = color;
289 d3acba95 2003-12-04 devnull t.f->cols[HTEXT] = display->white;
290 d3acba95 2003-12-04 devnull mselect();
291 d3acba95 2003-12-04 devnull newq0 = t.q0;
292 d3acba95 2003-12-04 devnull newq1 = t.q1;
293 d3acba95 2003-12-04 devnull
294 d3acba95 2003-12-04 devnull cancel = 0;
295 d3acba95 2003-12-04 devnull if(t.m.buttons != 0){
296 d3acba95 2003-12-04 devnull while(t.m.buttons){
297 d3acba95 2003-12-04 devnull readmouse(mc);
298 d3acba95 2003-12-04 devnull t.m = mc->m;
299 d3acba95 2003-12-04 devnull }
300 d3acba95 2003-12-04 devnull cancel = 1;
301 d3acba95 2003-12-04 devnull }
302 d3acba95 2003-12-04 devnull
303 d3acba95 2003-12-04 devnull /* restore old selection */
304 d3acba95 2003-12-04 devnull t.f->cols[HIGH] = cols[HIGH];
305 d3acba95 2003-12-04 devnull t.f->cols[HTEXT] = cols[HTEXT];
306 d3acba95 2003-12-04 devnull t.q0 = oldq0;
307 d3acba95 2003-12-04 devnull t.q1 = oldq1;
308 d3acba95 2003-12-04 devnull updatesel();
309 d3acba95 2003-12-04 devnull
310 d3acba95 2003-12-04 devnull if(cancel)
311 d3acba95 2003-12-04 devnull return -1;
312 d3acba95 2003-12-04 devnull
313 d3acba95 2003-12-04 devnull /* selected a region */
314 d3acba95 2003-12-04 devnull if(newq0 < newq1){
315 d3acba95 2003-12-04 devnull *q0 = newq0;
316 d3acba95 2003-12-04 devnull *q1 = newq1;
317 d3acba95 2003-12-04 devnull return 0;
318 d3acba95 2003-12-04 devnull }
319 d3acba95 2003-12-04 devnull
320 d3acba95 2003-12-04 devnull /* clicked inside previous selection */
321 e97ceade 2003-12-06 devnull /* the "<=" in newq0 <= oldq1 allows us to click the right edge */
322 e97ceade 2003-12-06 devnull if(oldq0 <= newq0 && newq0 <= oldq1){
323 d3acba95 2003-12-04 devnull *q0 = oldq0;
324 d3acba95 2003-12-04 devnull *q1 = oldq1;
325 d3acba95 2003-12-04 devnull return 0;
326 d3acba95 2003-12-04 devnull }
327 d3acba95 2003-12-04 devnull
328 d3acba95 2003-12-04 devnull /* just a click */
329 d3acba95 2003-12-04 devnull *q0 = newq0;
330 d3acba95 2003-12-04 devnull *q1 = newq1;
331 d3acba95 2003-12-04 devnull return 0;
332 d3acba95 2003-12-04 devnull }
333 d3acba95 2003-12-04 devnull
334 d3acba95 2003-12-04 devnull static Rune Lnl[1] = { '\n' };
335 d3acba95 2003-12-04 devnull
336 cfabc3ed 2003-11-23 devnull void
337 cfabc3ed 2003-11-23 devnull mouse(void)
338 cfabc3ed 2003-11-23 devnull {
339 d3acba95 2003-12-04 devnull int but;
340 d3acba95 2003-12-04 devnull uint q0, q1;
341 cfabc3ed 2003-11-23 devnull
342 cfabc3ed 2003-11-23 devnull but = t.m.buttons;
343 cfabc3ed 2003-11-23 devnull
344 cfabc3ed 2003-11-23 devnull if(but != 1 && but != 2 && but != 4)
345 cfabc3ed 2003-11-23 devnull return;
346 cfabc3ed 2003-11-23 devnull
347 cfabc3ed 2003-11-23 devnull if (ptinrect(t.m.xy, scrollr)) {
348 cfabc3ed 2003-11-23 devnull scroll(but);
349 cfabc3ed 2003-11-23 devnull if(t.qh<=t.org+t.f->nchars)
350 3fd755b7 2003-12-04 devnull consread();
351 cfabc3ed 2003-11-23 devnull return;
352 cfabc3ed 2003-11-23 devnull }
353 cfabc3ed 2003-11-23 devnull
354 cfabc3ed 2003-11-23 devnull switch(but) {
355 cfabc3ed 2003-11-23 devnull case 1:
356 cfabc3ed 2003-11-23 devnull mselect();
357 cfabc3ed 2003-11-23 devnull break;
358 cfabc3ed 2003-11-23 devnull case 2:
359 d3acba95 2003-12-04 devnull if(button2exec){
360 d3acba95 2003-12-04 devnull if(aselect(&q0, &q1, execcolor) >= 0){
361 d3acba95 2003-12-04 devnull if(q0 == q1)
362 d3acba95 2003-12-04 devnull wordclick(&q0, &q1);
363 d3acba95 2003-12-04 devnull if(q0 == q1)
364 d3acba95 2003-12-04 devnull break;
365 dff7e273 2003-12-04 devnull t.q0 = t.q1 = t.nr;
366 dff7e273 2003-12-04 devnull updatesel();
367 d3acba95 2003-12-04 devnull paste(t.r+q0, q1-q0, 1);
368 d3acba95 2003-12-04 devnull if(t.r[q1-1] != '\n')
369 d3acba95 2003-12-04 devnull paste(Lnl, 1, 1);
370 d3acba95 2003-12-04 devnull }
371 d3acba95 2003-12-04 devnull break;
372 d3acba95 2003-12-04 devnull }
373 cfabc3ed 2003-11-23 devnull domenu2(2);
374 cfabc3ed 2003-11-23 devnull break;
375 cfabc3ed 2003-11-23 devnull case 4:
376 d3acba95 2003-12-04 devnull if(aselect(&q0, &q1, plumbcolor) >= 0)
377 d3acba95 2003-12-04 devnull plumb(q0, q1);
378 cfabc3ed 2003-11-23 devnull break;
379 cfabc3ed 2003-11-23 devnull }
380 cfabc3ed 2003-11-23 devnull }
381 cfabc3ed 2003-11-23 devnull
382 cfabc3ed 2003-11-23 devnull void
383 cfabc3ed 2003-11-23 devnull mselect(void)
384 cfabc3ed 2003-11-23 devnull {
385 cfabc3ed 2003-11-23 devnull int b, x, y;
386 cfabc3ed 2003-11-23 devnull uint q0;
387 cfabc3ed 2003-11-23 devnull
388 cfabc3ed 2003-11-23 devnull b = t.m.buttons;
389 cfabc3ed 2003-11-23 devnull q0 = frcharofpt(t.f, t.m.xy) + t.org;
390 dff7e273 2003-12-04 devnull if(t.m.msec-clickmsec<500 && clickq0==q0 && t.q0==t.q1 && b==1){
391 cfabc3ed 2003-11-23 devnull doubleclick(&t.q0, &t.q1);
392 cfabc3ed 2003-11-23 devnull updatesel();
393 cfabc3ed 2003-11-23 devnull /* t.t.i->flush(); */
394 cfabc3ed 2003-11-23 devnull x = t.m.xy.x;
395 cfabc3ed 2003-11-23 devnull y = t.m.xy.y;
396 cfabc3ed 2003-11-23 devnull /* stay here until something interesting happens */
397 cfabc3ed 2003-11-23 devnull do {
398 cfabc3ed 2003-11-23 devnull readmouse(mc);
399 cfabc3ed 2003-11-23 devnull t.m = mc->m;
400 cfabc3ed 2003-11-23 devnull } while(t.m.buttons==b && abs(t.m.xy.x-x)<4 && abs(t.m.xy.y-y)<4);
401 cfabc3ed 2003-11-23 devnull t.m.xy.x = x; /* in case we're calling frselect */
402 cfabc3ed 2003-11-23 devnull t.m.xy.y = y;
403 cfabc3ed 2003-11-23 devnull clickmsec = 0;
404 cfabc3ed 2003-11-23 devnull }
405 cfabc3ed 2003-11-23 devnull
406 cfabc3ed 2003-11-23 devnull if(t.m.buttons == b) {
407 cfabc3ed 2003-11-23 devnull frselect(t.f, mc);
408 cfabc3ed 2003-11-23 devnull t.m = mc->m;
409 cfabc3ed 2003-11-23 devnull t.q0 = t.f->p0 + t.org;
410 cfabc3ed 2003-11-23 devnull t.q1 = t.f->p1 + t.org;
411 cfabc3ed 2003-11-23 devnull clickmsec = t.m.msec;
412 cfabc3ed 2003-11-23 devnull clickq0 = t.q0;
413 cfabc3ed 2003-11-23 devnull }
414 dff7e273 2003-12-04 devnull if((t.m.buttons != b) &&(b&1)){
415 dff7e273 2003-12-04 devnull enum{Cancut = 1, Canpaste = 2} state = Cancut | Canpaste;
416 cfabc3ed 2003-11-23 devnull while(t.m.buttons){
417 dff7e273 2003-12-04 devnull if(t.m.buttons&2){
418 dff7e273 2003-12-04 devnull if(state&Cancut){
419 cfabc3ed 2003-11-23 devnull snarf();
420 cfabc3ed 2003-11-23 devnull cut();
421 cfabc3ed 2003-11-23 devnull state = Canpaste;
422 cfabc3ed 2003-11-23 devnull }
423 dff7e273 2003-12-04 devnull }else if(t.m.buttons&4){
424 dff7e273 2003-12-04 devnull if(state&Canpaste){
425 cfabc3ed 2003-11-23 devnull snarfupdate();
426 dff7e273 2003-12-04 devnull if(t.nsnarf){
427 cfabc3ed 2003-11-23 devnull paste(t.snarf, t.nsnarf, 0);
428 cfabc3ed 2003-11-23 devnull }
429 cfabc3ed 2003-11-23 devnull state = Cancut|Canpaste;
430 cfabc3ed 2003-11-23 devnull }
431 cfabc3ed 2003-11-23 devnull }
432 cfabc3ed 2003-11-23 devnull readmouse(mc);
433 cfabc3ed 2003-11-23 devnull t.m = mc->m;
434 cfabc3ed 2003-11-23 devnull }
435 cfabc3ed 2003-11-23 devnull }
436 cfabc3ed 2003-11-23 devnull }
437 cfabc3ed 2003-11-23 devnull
438 cfabc3ed 2003-11-23 devnull Rune newline[] = { '\n', 0 };
439 cfabc3ed 2003-11-23 devnull
440 cfabc3ed 2003-11-23 devnull void
441 cfabc3ed 2003-11-23 devnull domenu2(int but)
442 cfabc3ed 2003-11-23 devnull {
443 cfabc3ed 2003-11-23 devnull if(scrolling)
444 cfabc3ed 2003-11-23 devnull menu2str[Scroll] = "noscroll";
445 cfabc3ed 2003-11-23 devnull else
446 cfabc3ed 2003-11-23 devnull menu2str[Scroll] = "scroll";
447 cfabc3ed 2003-11-23 devnull
448 cfabc3ed 2003-11-23 devnull switch(menuhit(but, mc, &menu2, nil)){
449 cfabc3ed 2003-11-23 devnull case -1:
450 cfabc3ed 2003-11-23 devnull break;
451 cfabc3ed 2003-11-23 devnull case Cut:
452 cfabc3ed 2003-11-23 devnull snarf();
453 cfabc3ed 2003-11-23 devnull cut();
454 cfabc3ed 2003-11-23 devnull if(scrolling)
455 cfabc3ed 2003-11-23 devnull show(t.q0);
456 cfabc3ed 2003-11-23 devnull break;
457 cfabc3ed 2003-11-23 devnull case Paste:
458 cfabc3ed 2003-11-23 devnull snarfupdate();
459 cfabc3ed 2003-11-23 devnull paste(t.snarf, t.nsnarf, 0);
460 cfabc3ed 2003-11-23 devnull if(scrolling)
461 cfabc3ed 2003-11-23 devnull show(t.q0);
462 cfabc3ed 2003-11-23 devnull break;
463 cfabc3ed 2003-11-23 devnull case Snarf:
464 cfabc3ed 2003-11-23 devnull snarf();
465 cfabc3ed 2003-11-23 devnull if(scrolling)
466 cfabc3ed 2003-11-23 devnull show(t.q0);
467 cfabc3ed 2003-11-23 devnull break;
468 cfabc3ed 2003-11-23 devnull case Send:
469 cfabc3ed 2003-11-23 devnull snarf();
470 cfabc3ed 2003-11-23 devnull t.q0 = t.q1 = t.nr;
471 cfabc3ed 2003-11-23 devnull updatesel();
472 cfabc3ed 2003-11-23 devnull snarfupdate();
473 cfabc3ed 2003-11-23 devnull paste(t.snarf, t.nsnarf, 1);
474 cfabc3ed 2003-11-23 devnull if(t.nsnarf == 0 || t.snarf[t.nsnarf-1] != '\n')
475 cfabc3ed 2003-11-23 devnull paste(newline, 1, 1);
476 cfabc3ed 2003-11-23 devnull show(t.nr);
477 cfabc3ed 2003-11-23 devnull consread();
478 cfabc3ed 2003-11-23 devnull break;
479 cfabc3ed 2003-11-23 devnull case Scroll:
480 cfabc3ed 2003-11-23 devnull scrolling = !scrolling;
481 cfabc3ed 2003-11-23 devnull if (scrolling) {
482 cfabc3ed 2003-11-23 devnull show(t.nr);
483 cfabc3ed 2003-11-23 devnull consread();
484 cfabc3ed 2003-11-23 devnull }
485 cfabc3ed 2003-11-23 devnull break;
486 cfabc3ed 2003-11-23 devnull case Plumb:
487 cfabc3ed 2003-11-23 devnull plumb(t.q0, t.q1);
488 cfabc3ed 2003-11-23 devnull break;
489 cfabc3ed 2003-11-23 devnull default:
490 cfabc3ed 2003-11-23 devnull fatal("bad menu item");
491 cfabc3ed 2003-11-23 devnull }
492 cfabc3ed 2003-11-23 devnull }
493 cfabc3ed 2003-11-23 devnull
494 cfabc3ed 2003-11-23 devnull void
495 cfabc3ed 2003-11-23 devnull key(Rune r)
496 cfabc3ed 2003-11-23 devnull {
497 669250d1 2003-12-03 devnull uint sig;
498 cfabc3ed 2003-11-23 devnull
499 cfabc3ed 2003-11-23 devnull if(r == 0)
500 cfabc3ed 2003-11-23 devnull return;
501 cfabc3ed 2003-11-23 devnull if(r==SCROLLKEY){ /* scroll key */
502 cfabc3ed 2003-11-23 devnull setorigin(line2q(t.f->maxlines*2/3), 1);
503 cfabc3ed 2003-11-23 devnull if(t.qh<=t.org+t.f->nchars)
504 cfabc3ed 2003-11-23 devnull consread();
505 cfabc3ed 2003-11-23 devnull return;
506 cfabc3ed 2003-11-23 devnull }else if(r == BACKSCROLLKEY){
507 cfabc3ed 2003-11-23 devnull setorigin(backnl(t.org, t.f->maxlines*2/3), 1);
508 cfabc3ed 2003-11-23 devnull return;
509 cfabc3ed 2003-11-23 devnull }else if(r == CUT){
510 cfabc3ed 2003-11-23 devnull snarf();
511 cfabc3ed 2003-11-23 devnull cut();
512 cfabc3ed 2003-11-23 devnull if(scrolling)
513 cfabc3ed 2003-11-23 devnull show(t.q0);
514 cfabc3ed 2003-11-23 devnull return;
515 cfabc3ed 2003-11-23 devnull }else if(r == COPY){
516 cfabc3ed 2003-11-23 devnull snarf();
517 cfabc3ed 2003-11-23 devnull if(scrolling)
518 cfabc3ed 2003-11-23 devnull show(t.q0);
519 cfabc3ed 2003-11-23 devnull return;
520 cfabc3ed 2003-11-23 devnull }else if(r == PASTE){
521 cfabc3ed 2003-11-23 devnull snarfupdate();
522 cfabc3ed 2003-11-23 devnull paste(t.snarf, t.nsnarf, 0);
523 cfabc3ed 2003-11-23 devnull if(scrolling)
524 cfabc3ed 2003-11-23 devnull show(t.q0);
525 cfabc3ed 2003-11-23 devnull return;
526 cfabc3ed 2003-11-23 devnull }
527 cfabc3ed 2003-11-23 devnull
528 3fd755b7 2003-12-04 devnull if(rawon && t.q0==t.nr){
529 cfabc3ed 2003-11-23 devnull addraw(&r, 1);
530 3fd755b7 2003-12-04 devnull consread();
531 cfabc3ed 2003-11-23 devnull return;
532 cfabc3ed 2003-11-23 devnull }
533 cfabc3ed 2003-11-23 devnull
534 cfabc3ed 2003-11-23 devnull if(r==ESC || (holdon && r==0x7F)){ /* toggle hold */
535 cfabc3ed 2003-11-23 devnull holdon = !holdon;
536 cfabc3ed 2003-11-23 devnull drawhold(holdon);
537 cfabc3ed 2003-11-23 devnull if(!holdon)
538 cfabc3ed 2003-11-23 devnull consread();
539 cfabc3ed 2003-11-23 devnull if(r == 0x1B)
540 cfabc3ed 2003-11-23 devnull return;
541 cfabc3ed 2003-11-23 devnull }
542 cfabc3ed 2003-11-23 devnull
543 cfabc3ed 2003-11-23 devnull snarf();
544 cfabc3ed 2003-11-23 devnull
545 cfabc3ed 2003-11-23 devnull switch(r) {
546 cfabc3ed 2003-11-23 devnull case 0x7F: /* DEL: send interrupt */
547 cfabc3ed 2003-11-23 devnull t.qh = t.q0 = t.q1 = t.nr;
548 cfabc3ed 2003-11-23 devnull show(t.q0);
549 669250d1 2003-12-03 devnull sig = 2; /* SIGINT */
550 669250d1 2003-12-03 devnull if(ioctl(rcfd[0], TIOCSIG, &sig) < 0)
551 669250d1 2003-12-03 devnull fprint(2, "sending interrupt: %r\n");
552 cfabc3ed 2003-11-23 devnull break;
553 cfabc3ed 2003-11-23 devnull case 0x08: /* ^H: erase character */
554 cfabc3ed 2003-11-23 devnull case 0x15: /* ^U: erase line */
555 cfabc3ed 2003-11-23 devnull case 0x17: /* ^W: erase word */
556 cfabc3ed 2003-11-23 devnull if (t.q0 != 0 && t.q0 != t.qh)
557 cfabc3ed 2003-11-23 devnull t.q0 -= bswidth(r);
558 cfabc3ed 2003-11-23 devnull cut();
559 cfabc3ed 2003-11-23 devnull break;
560 cfabc3ed 2003-11-23 devnull default:
561 cfabc3ed 2003-11-23 devnull paste(&r, 1, 1);
562 cfabc3ed 2003-11-23 devnull break;
563 cfabc3ed 2003-11-23 devnull }
564 cfabc3ed 2003-11-23 devnull if(scrolling)
565 cfabc3ed 2003-11-23 devnull show(t.q0);
566 cfabc3ed 2003-11-23 devnull }
567 cfabc3ed 2003-11-23 devnull
568 cfabc3ed 2003-11-23 devnull int
569 cfabc3ed 2003-11-23 devnull bswidth(Rune c)
570 cfabc3ed 2003-11-23 devnull {
571 cfabc3ed 2003-11-23 devnull uint q, eq, stop;
572 cfabc3ed 2003-11-23 devnull Rune r;
573 cfabc3ed 2003-11-23 devnull int skipping;
574 cfabc3ed 2003-11-23 devnull
575 cfabc3ed 2003-11-23 devnull /* there is known to be at least one character to erase */
576 cfabc3ed 2003-11-23 devnull if(c == 0x08) /* ^H: erase character */
577 cfabc3ed 2003-11-23 devnull return 1;
578 cfabc3ed 2003-11-23 devnull q = t.q0;
579 cfabc3ed 2003-11-23 devnull stop = 0;
580 cfabc3ed 2003-11-23 devnull if(q > t.qh)
581 cfabc3ed 2003-11-23 devnull stop = t.qh;
582 cfabc3ed 2003-11-23 devnull skipping = 1;
583 cfabc3ed 2003-11-23 devnull while(q > stop){
584 cfabc3ed 2003-11-23 devnull r = t.r[q-1];
585 cfabc3ed 2003-11-23 devnull if(r == '\n'){ /* eat at most one more character */
586 cfabc3ed 2003-11-23 devnull if(q == t.q0) /* eat the newline */
587 cfabc3ed 2003-11-23 devnull --q;
588 cfabc3ed 2003-11-23 devnull break;
589 cfabc3ed 2003-11-23 devnull }
590 cfabc3ed 2003-11-23 devnull if(c == 0x17){
591 cfabc3ed 2003-11-23 devnull eq = isalnum(r);
592 cfabc3ed 2003-11-23 devnull if(eq && skipping) /* found one; stop skipping */
593 cfabc3ed 2003-11-23 devnull skipping = 0;
594 cfabc3ed 2003-11-23 devnull else if(!eq && !skipping)
595 cfabc3ed 2003-11-23 devnull break;
596 cfabc3ed 2003-11-23 devnull }
597 cfabc3ed 2003-11-23 devnull --q;
598 cfabc3ed 2003-11-23 devnull }
599 cfabc3ed 2003-11-23 devnull return t.q0-q;
600 cfabc3ed 2003-11-23 devnull }
601 cfabc3ed 2003-11-23 devnull
602 cfabc3ed 2003-11-23 devnull int
603 cfabc3ed 2003-11-23 devnull consready(void)
604 cfabc3ed 2003-11-23 devnull {
605 cfabc3ed 2003-11-23 devnull int i, c;
606 cfabc3ed 2003-11-23 devnull
607 cfabc3ed 2003-11-23 devnull if(holdon)
608 cfabc3ed 2003-11-23 devnull return 0;
609 cfabc3ed 2003-11-23 devnull
610 3fd755b7 2003-12-04 devnull if(rawon)
611 cfabc3ed 2003-11-23 devnull return t.nraw != 0;
612 cfabc3ed 2003-11-23 devnull
613 cfabc3ed 2003-11-23 devnull /* look to see if there is a complete line */
614 cfabc3ed 2003-11-23 devnull for(i=t.qh; i<t.nr; i++){
615 cfabc3ed 2003-11-23 devnull c = t.r[i];
616 cfabc3ed 2003-11-23 devnull if(c=='\n' || c=='\004')
617 cfabc3ed 2003-11-23 devnull return 1;
618 cfabc3ed 2003-11-23 devnull }
619 cfabc3ed 2003-11-23 devnull return 0;
620 cfabc3ed 2003-11-23 devnull }
621 cfabc3ed 2003-11-23 devnull
622 cfabc3ed 2003-11-23 devnull
623 cfabc3ed 2003-11-23 devnull void
624 cfabc3ed 2003-11-23 devnull consread(void)
625 cfabc3ed 2003-11-23 devnull {
626 cfabc3ed 2003-11-23 devnull char buf[8000], *p;
627 cfabc3ed 2003-11-23 devnull int c, width, n;
628 cfabc3ed 2003-11-23 devnull
629 cfabc3ed 2003-11-23 devnull for(;;) {
630 cfabc3ed 2003-11-23 devnull if(!consready())
631 cfabc3ed 2003-11-23 devnull return;
632 cfabc3ed 2003-11-23 devnull
633 cfabc3ed 2003-11-23 devnull n = sizeof(buf);
634 cfabc3ed 2003-11-23 devnull p = buf;
635 669250d1 2003-12-03 devnull c = 0;
636 cfabc3ed 2003-11-23 devnull while(n >= UTFmax && (t.qh<t.nr || t.nraw > 0)) {
637 cfabc3ed 2003-11-23 devnull if(t.qh == t.nr){
638 cfabc3ed 2003-11-23 devnull width = runetochar(p, &t.raw[0]);
639 cfabc3ed 2003-11-23 devnull t.nraw--;
640 cfabc3ed 2003-11-23 devnull runemove(t.raw, t.raw+1, t.nraw);
641 cfabc3ed 2003-11-23 devnull }else
642 cfabc3ed 2003-11-23 devnull width = runetochar(p, &t.r[t.qh++]);
643 cfabc3ed 2003-11-23 devnull c = *p;
644 cfabc3ed 2003-11-23 devnull p += width;
645 cfabc3ed 2003-11-23 devnull n -= width;
646 3fd755b7 2003-12-04 devnull if(!rawon && (c == '\n' || c == '\004'))
647 cfabc3ed 2003-11-23 devnull break;
648 cfabc3ed 2003-11-23 devnull }
649 669250d1 2003-12-03 devnull /* take out control-d when not doing a zero length write */
650 669250d1 2003-12-03 devnull n = p-buf;
651 669250d1 2003-12-03 devnull if(write(rcfd[1], buf, n) < 0)
652 cfabc3ed 2003-11-23 devnull exits(0);
653 cfabc3ed 2003-11-23 devnull /* mallocstats(); */
654 cfabc3ed 2003-11-23 devnull }
655 cfabc3ed 2003-11-23 devnull }
656 cfabc3ed 2003-11-23 devnull
657 cfabc3ed 2003-11-23 devnull void
658 cfabc3ed 2003-11-23 devnull conswrite(char *p, int n)
659 cfabc3ed 2003-11-23 devnull {
660 cfabc3ed 2003-11-23 devnull int n2, i;
661 cfabc3ed 2003-11-23 devnull Rune buf2[1000], *q;
662 cfabc3ed 2003-11-23 devnull
663 cfabc3ed 2003-11-23 devnull /* convert to runes */
664 cfabc3ed 2003-11-23 devnull i = t.npart;
665 cfabc3ed 2003-11-23 devnull if(i > 0){
666 cfabc3ed 2003-11-23 devnull /* handle partial runes */
667 cfabc3ed 2003-11-23 devnull while(i < UTFmax && n>0) {
668 cfabc3ed 2003-11-23 devnull t.part[i] = *p;
669 cfabc3ed 2003-11-23 devnull i++;
670 cfabc3ed 2003-11-23 devnull p++;
671 cfabc3ed 2003-11-23 devnull n--;
672 cfabc3ed 2003-11-23 devnull if(fullrune(t.part, i)) {
673 cfabc3ed 2003-11-23 devnull t.npart = 0;
674 cfabc3ed 2003-11-23 devnull chartorune(buf2, t.part);
675 cfabc3ed 2003-11-23 devnull runewrite(buf2, 1);
676 cfabc3ed 2003-11-23 devnull break;
677 cfabc3ed 2003-11-23 devnull }
678 cfabc3ed 2003-11-23 devnull }
679 cfabc3ed 2003-11-23 devnull /* there is a little extra room in a message buf */
680 cfabc3ed 2003-11-23 devnull }
681 cfabc3ed 2003-11-23 devnull
682 cfabc3ed 2003-11-23 devnull while(n >= UTFmax || fullrune(p, n)) {
683 cfabc3ed 2003-11-23 devnull n2 = nelem(buf2);
684 cfabc3ed 2003-11-23 devnull q = buf2;
685 cfabc3ed 2003-11-23 devnull
686 cfabc3ed 2003-11-23 devnull while(n2) {
687 cfabc3ed 2003-11-23 devnull if(n < UTFmax && !fullrune(p, n))
688 cfabc3ed 2003-11-23 devnull break;
689 cfabc3ed 2003-11-23 devnull i = chartorune(q, p);
690 cfabc3ed 2003-11-23 devnull p += i;
691 cfabc3ed 2003-11-23 devnull n -= i;
692 cfabc3ed 2003-11-23 devnull n2--;
693 cfabc3ed 2003-11-23 devnull q++;
694 cfabc3ed 2003-11-23 devnull }
695 cfabc3ed 2003-11-23 devnull runewrite(buf2, q-buf2);
696 cfabc3ed 2003-11-23 devnull }
697 cfabc3ed 2003-11-23 devnull
698 cfabc3ed 2003-11-23 devnull if(n != 0) {
699 cfabc3ed 2003-11-23 devnull assert(n+t.npart < UTFmax);
700 cfabc3ed 2003-11-23 devnull memcpy(t.part+t.npart, p, n);
701 cfabc3ed 2003-11-23 devnull t.npart += n;
702 cfabc3ed 2003-11-23 devnull }
703 cfabc3ed 2003-11-23 devnull
704 cfabc3ed 2003-11-23 devnull if(scrolling)
705 cfabc3ed 2003-11-23 devnull show(t.qh);
706 cfabc3ed 2003-11-23 devnull }
707 cfabc3ed 2003-11-23 devnull
708 cfabc3ed 2003-11-23 devnull void
709 cfabc3ed 2003-11-23 devnull runewrite(Rune *r, int n)
710 cfabc3ed 2003-11-23 devnull {
711 cfabc3ed 2003-11-23 devnull uint m;
712 cfabc3ed 2003-11-23 devnull int i;
713 cfabc3ed 2003-11-23 devnull uint initial;
714 cfabc3ed 2003-11-23 devnull uint q0, q1;
715 cfabc3ed 2003-11-23 devnull uint p0, p1;
716 cfabc3ed 2003-11-23 devnull Rune *p, *q;
717 cfabc3ed 2003-11-23 devnull
718 cfabc3ed 2003-11-23 devnull n = label(r, n);
719 cfabc3ed 2003-11-23 devnull if(n == 0)
720 cfabc3ed 2003-11-23 devnull return;
721 cfabc3ed 2003-11-23 devnull
722 d2a414f2 2003-12-04 devnull /* get rid of backspaces */
723 cfabc3ed 2003-11-23 devnull initial = 0;
724 cfabc3ed 2003-11-23 devnull p = q = r;
725 cfabc3ed 2003-11-23 devnull for(i=0; i<n; i++) {
726 cfabc3ed 2003-11-23 devnull if(*p == '\b') {
727 cfabc3ed 2003-11-23 devnull if(q == r)
728 cfabc3ed 2003-11-23 devnull initial++;
729 cfabc3ed 2003-11-23 devnull else
730 cfabc3ed 2003-11-23 devnull --q;
731 cfabc3ed 2003-11-23 devnull } else if(*p)
732 cfabc3ed 2003-11-23 devnull *q++ = *p;
733 cfabc3ed 2003-11-23 devnull p++;
734 cfabc3ed 2003-11-23 devnull }
735 cfabc3ed 2003-11-23 devnull n = q-r;
736 cfabc3ed 2003-11-23 devnull
737 cfabc3ed 2003-11-23 devnull if(initial){
738 cfabc3ed 2003-11-23 devnull /* write turned into a delete */
739 cfabc3ed 2003-11-23 devnull
740 cfabc3ed 2003-11-23 devnull if(initial > t.qh)
741 cfabc3ed 2003-11-23 devnull initial = t.qh;
742 cfabc3ed 2003-11-23 devnull q0 = t.qh-initial;
743 cfabc3ed 2003-11-23 devnull q1 = t.qh;
744 cfabc3ed 2003-11-23 devnull
745 cfabc3ed 2003-11-23 devnull runemove(t.r+q0, t.r+q1, t.nr-q1);
746 cfabc3ed 2003-11-23 devnull t.nr -= initial;
747 cfabc3ed 2003-11-23 devnull t.qh -= initial;
748 cfabc3ed 2003-11-23 devnull if(t.q0 > q1)
749 cfabc3ed 2003-11-23 devnull t.q0 -= initial;
750 cfabc3ed 2003-11-23 devnull else if(t.q0 > q0)
751 cfabc3ed 2003-11-23 devnull t.q0 = q0;
752 cfabc3ed 2003-11-23 devnull if(t.q1 > q1)
753 cfabc3ed 2003-11-23 devnull t.q1 -= initial;
754 cfabc3ed 2003-11-23 devnull else if(t.q1 > q0)
755 cfabc3ed 2003-11-23 devnull t.q1 = q0;
756 cfabc3ed 2003-11-23 devnull if(t.org > q1)
757 cfabc3ed 2003-11-23 devnull t.org -= initial;
758 cfabc3ed 2003-11-23 devnull else if(q0 < t.org+t.f->nchars){
759 cfabc3ed 2003-11-23 devnull if(t.org < q0)
760 cfabc3ed 2003-11-23 devnull p0 = q0 - t.org;
761 cfabc3ed 2003-11-23 devnull else {
762 cfabc3ed 2003-11-23 devnull t.org = q0;
763 cfabc3ed 2003-11-23 devnull p0 = 0;
764 cfabc3ed 2003-11-23 devnull }
765 cfabc3ed 2003-11-23 devnull p1 = q1 - t.org;
766 cfabc3ed 2003-11-23 devnull if(p1 > t.f->nchars)
767 cfabc3ed 2003-11-23 devnull p1 = t.f->nchars;
768 cfabc3ed 2003-11-23 devnull frdelete(t.f, p0, p1);
769 cfabc3ed 2003-11-23 devnull fill();
770 cfabc3ed 2003-11-23 devnull }
771 cfabc3ed 2003-11-23 devnull updatesel();
772 cfabc3ed 2003-11-23 devnull }
773 cfabc3ed 2003-11-23 devnull
774 cfabc3ed 2003-11-23 devnull if(t.nr>HiWater && t.qh>=t.org){
775 cfabc3ed 2003-11-23 devnull m = HiWater-LoWater;
776 cfabc3ed 2003-11-23 devnull if(m > t.org);
777 cfabc3ed 2003-11-23 devnull m = t.org;
778 cfabc3ed 2003-11-23 devnull t.org -= m;
779 cfabc3ed 2003-11-23 devnull t.qh -= m;
780 cfabc3ed 2003-11-23 devnull if(t.q0 > m)
781 cfabc3ed 2003-11-23 devnull t.q0 -= m;
782 cfabc3ed 2003-11-23 devnull else
783 cfabc3ed 2003-11-23 devnull t.q0 = 0;
784 cfabc3ed 2003-11-23 devnull if(t.q1 > m)
785 cfabc3ed 2003-11-23 devnull t.q1 -= m;
786 cfabc3ed 2003-11-23 devnull else
787 cfabc3ed 2003-11-23 devnull t.q1 = 0;
788 cfabc3ed 2003-11-23 devnull t.nr -= m;
789 cfabc3ed 2003-11-23 devnull runemove(t.r, t.r+m, t.nr);
790 cfabc3ed 2003-11-23 devnull }
791 cfabc3ed 2003-11-23 devnull t.r = runerealloc(t.r, t.nr+n);
792 cfabc3ed 2003-11-23 devnull runemove(t.r+t.qh+n, t.r+t.qh, t.nr-t.qh);
793 cfabc3ed 2003-11-23 devnull runemove(t.r+t.qh, r, n);
794 cfabc3ed 2003-11-23 devnull t.nr += n;
795 cfabc3ed 2003-11-23 devnull if(t.qh < t.org)
796 cfabc3ed 2003-11-23 devnull t.org += n;
797 cfabc3ed 2003-11-23 devnull else if(t.qh <= t.f->nchars+t.org)
798 cfabc3ed 2003-11-23 devnull frinsert(t.f, r, r+n, t.qh-t.org);
799 cfabc3ed 2003-11-23 devnull if (t.qh <= t.q0)
800 cfabc3ed 2003-11-23 devnull t.q0 += n;
801 cfabc3ed 2003-11-23 devnull if (t.qh <= t.q1)
802 cfabc3ed 2003-11-23 devnull t.q1 += n;
803 cfabc3ed 2003-11-23 devnull t.qh += n;
804 cfabc3ed 2003-11-23 devnull updatesel();
805 cfabc3ed 2003-11-23 devnull }
806 cfabc3ed 2003-11-23 devnull
807 cfabc3ed 2003-11-23 devnull
808 cfabc3ed 2003-11-23 devnull void
809 cfabc3ed 2003-11-23 devnull cut(void)
810 cfabc3ed 2003-11-23 devnull {
811 cfabc3ed 2003-11-23 devnull uint n, p0, p1;
812 cfabc3ed 2003-11-23 devnull uint q0, q1;
813 cfabc3ed 2003-11-23 devnull
814 cfabc3ed 2003-11-23 devnull q0 = t.q0;
815 cfabc3ed 2003-11-23 devnull q1 = t.q1;
816 cfabc3ed 2003-11-23 devnull
817 cfabc3ed 2003-11-23 devnull if (q0 < t.org && q1 >= t.org)
818 cfabc3ed 2003-11-23 devnull show(q0);
819 cfabc3ed 2003-11-23 devnull
820 cfabc3ed 2003-11-23 devnull n = q1-q0;
821 cfabc3ed 2003-11-23 devnull if(n == 0)
822 cfabc3ed 2003-11-23 devnull return;
823 cfabc3ed 2003-11-23 devnull runemove(t.r+q0, t.r+q1, t.nr-q1);
824 cfabc3ed 2003-11-23 devnull t.nr -= n;
825 cfabc3ed 2003-11-23 devnull t.q0 = t.q1 = q0;
826 cfabc3ed 2003-11-23 devnull if(q1 < t.qh)
827 cfabc3ed 2003-11-23 devnull t.qh -= n;
828 cfabc3ed 2003-11-23 devnull else if(q0 < t.qh)
829 cfabc3ed 2003-11-23 devnull t.qh = q0;
830 cfabc3ed 2003-11-23 devnull if(q1 < t.org)
831 cfabc3ed 2003-11-23 devnull t.org -= n;
832 cfabc3ed 2003-11-23 devnull else if(q0 < t.org+t.f->nchars){
833 cfabc3ed 2003-11-23 devnull assert(q0 >= t.org);
834 cfabc3ed 2003-11-23 devnull p0 = q0 - t.org;
835 cfabc3ed 2003-11-23 devnull p1 = q1 - t.org;
836 cfabc3ed 2003-11-23 devnull if(p1 > t.f->nchars)
837 cfabc3ed 2003-11-23 devnull p1 = t.f->nchars;
838 cfabc3ed 2003-11-23 devnull frdelete(t.f, p0, p1);
839 cfabc3ed 2003-11-23 devnull fill();
840 cfabc3ed 2003-11-23 devnull }
841 cfabc3ed 2003-11-23 devnull updatesel();
842 cfabc3ed 2003-11-23 devnull }
843 cfabc3ed 2003-11-23 devnull
844 cfabc3ed 2003-11-23 devnull void
845 cfabc3ed 2003-11-23 devnull snarfupdate(void)
846 cfabc3ed 2003-11-23 devnull {
847 cfabc3ed 2003-11-23 devnull char *pp;
848 cfabc3ed 2003-11-23 devnull int n, i;
849 cfabc3ed 2003-11-23 devnull Rune *p;
850 cfabc3ed 2003-11-23 devnull
851 cfabc3ed 2003-11-23 devnull pp = getsnarf();
852 d3acba95 2003-12-04 devnull if(pp == nil)
853 d3acba95 2003-12-04 devnull return;
854 cfabc3ed 2003-11-23 devnull n = strlen(pp);
855 cfabc3ed 2003-11-23 devnull if(n <= 0) {
856 cfabc3ed 2003-11-23 devnull /*t.nsnarf = 0;*/
857 cfabc3ed 2003-11-23 devnull return;
858 cfabc3ed 2003-11-23 devnull }
859 cfabc3ed 2003-11-23 devnull t.snarf = runerealloc(t.snarf, n);
860 cfabc3ed 2003-11-23 devnull for(i=0,p=t.snarf; i<n; p++)
861 cfabc3ed 2003-11-23 devnull i += chartorune(p, pp+i);
862 cfabc3ed 2003-11-23 devnull t.nsnarf = p-t.snarf;
863 cfabc3ed 2003-11-23 devnull
864 cfabc3ed 2003-11-23 devnull }
865 cfabc3ed 2003-11-23 devnull
866 dff7e273 2003-12-04 devnull char sbuf[SnarfSize];
867 cfabc3ed 2003-11-23 devnull void
868 cfabc3ed 2003-11-23 devnull snarf(void)
869 cfabc3ed 2003-11-23 devnull {
870 dff7e273 2003-12-04 devnull char *p;
871 cfabc3ed 2003-11-23 devnull int i, n;
872 cfabc3ed 2003-11-23 devnull Rune *rp;
873 cfabc3ed 2003-11-23 devnull
874 cfabc3ed 2003-11-23 devnull if(t.q1 == t.q0)
875 cfabc3ed 2003-11-23 devnull return;
876 cfabc3ed 2003-11-23 devnull n = t.q1-t.q0;
877 dff7e273 2003-12-04 devnull t.snarf = runerealloc(t.snarf, n);
878 dff7e273 2003-12-04 devnull for(i=0,p=sbuf,rp=t.snarf; i<n && p < sbuf+SnarfSize-UTFmax; i++){
879 cfabc3ed 2003-11-23 devnull *rp++ = *(t.r+t.q0+i);
880 cfabc3ed 2003-11-23 devnull p += runetochar(p, t.r+t.q0+i);
881 cfabc3ed 2003-11-23 devnull }
882 cfabc3ed 2003-11-23 devnull t.nsnarf = rp-t.snarf;
883 cfabc3ed 2003-11-23 devnull *p = '\0';
884 dff7e273 2003-12-04 devnull putsnarf(sbuf);
885 cfabc3ed 2003-11-23 devnull }
886 cfabc3ed 2003-11-23 devnull
887 cfabc3ed 2003-11-23 devnull void
888 cfabc3ed 2003-11-23 devnull paste(Rune *r, int n, int advance)
889 cfabc3ed 2003-11-23 devnull {
890 dff7e273 2003-12-04 devnull Rune *rbuf;
891 cfabc3ed 2003-11-23 devnull uint m;
892 cfabc3ed 2003-11-23 devnull uint q0;
893 cfabc3ed 2003-11-23 devnull
894 3fd755b7 2003-12-04 devnull if(rawon && t.q0==t.nr){
895 cfabc3ed 2003-11-23 devnull addraw(r, n);
896 cfabc3ed 2003-11-23 devnull return;
897 cfabc3ed 2003-11-23 devnull }
898 cfabc3ed 2003-11-23 devnull
899 cfabc3ed 2003-11-23 devnull cut();
900 cfabc3ed 2003-11-23 devnull if(n == 0)
901 cfabc3ed 2003-11-23 devnull return;
902 cfabc3ed 2003-11-23 devnull if(t.nr>HiWater && t.q0>=t.org && t.q0>=t.qh){
903 cfabc3ed 2003-11-23 devnull m = HiWater-LoWater;
904 cfabc3ed 2003-11-23 devnull if(m > t.org)
905 cfabc3ed 2003-11-23 devnull m = t.org;
906 cfabc3ed 2003-11-23 devnull if(m > t.qh);
907 cfabc3ed 2003-11-23 devnull m = t.qh;
908 cfabc3ed 2003-11-23 devnull t.org -= m;
909 cfabc3ed 2003-11-23 devnull t.qh -= m;
910 cfabc3ed 2003-11-23 devnull t.q0 -= m;
911 cfabc3ed 2003-11-23 devnull t.q1 -= m;
912 cfabc3ed 2003-11-23 devnull t.nr -= m;
913 cfabc3ed 2003-11-23 devnull runemove(t.r, t.r+m, t.nr);
914 dff7e273 2003-12-04 devnull }
915 dff7e273 2003-12-04 devnull
916 dff7e273 2003-12-04 devnull /*
917 dff7e273 2003-12-04 devnull * if this is a button2 execute then we might have been passed
918 dff7e273 2003-12-04 devnull * runes inside the buffer. must save them before realloc.
919 dff7e273 2003-12-04 devnull */
920 dff7e273 2003-12-04 devnull rbuf = nil;
921 dff7e273 2003-12-04 devnull if(t.r <= r && r < t.r+n){
922 dff7e273 2003-12-04 devnull rbuf = runemalloc(n);
923 dff7e273 2003-12-04 devnull runemove(rbuf, r, n);
924 dff7e273 2003-12-04 devnull r = rbuf;
925 cfabc3ed 2003-11-23 devnull }
926 cfabc3ed 2003-11-23 devnull t.r = runerealloc(t.r, t.nr+n);
927 cfabc3ed 2003-11-23 devnull q0 = t.q0;
928 cfabc3ed 2003-11-23 devnull runemove(t.r+q0+n, t.r+q0, t.nr-q0);
929 cfabc3ed 2003-11-23 devnull runemove(t.r+q0, r, n);
930 cfabc3ed 2003-11-23 devnull t.nr += n;
931 cfabc3ed 2003-11-23 devnull if(q0 < t.qh)
932 cfabc3ed 2003-11-23 devnull t.qh += n;
933 cfabc3ed 2003-11-23 devnull else
934 cfabc3ed 2003-11-23 devnull consread();
935 cfabc3ed 2003-11-23 devnull if(q0 < t.org)
936 cfabc3ed 2003-11-23 devnull t.org += n;
937 cfabc3ed 2003-11-23 devnull else if(q0 <= t.f->nchars+t.org)
938 cfabc3ed 2003-11-23 devnull frinsert(t.f, r, r+n, q0-t.org);
939 cfabc3ed 2003-11-23 devnull if(advance)
940 cfabc3ed 2003-11-23 devnull t.q0 += n;
941 cfabc3ed 2003-11-23 devnull t.q1 += n;
942 cfabc3ed 2003-11-23 devnull updatesel();
943 dff7e273 2003-12-04 devnull free(rbuf);
944 cfabc3ed 2003-11-23 devnull }
945 cfabc3ed 2003-11-23 devnull
946 cfabc3ed 2003-11-23 devnull void
947 cfabc3ed 2003-11-23 devnull fill(void)
948 cfabc3ed 2003-11-23 devnull {
949 cfabc3ed 2003-11-23 devnull if (t.f->nlines >= t.f->maxlines)
950 cfabc3ed 2003-11-23 devnull return;
951 cfabc3ed 2003-11-23 devnull frinsert(t.f, t.r + t.org + t.f->nchars, t.r + t.nr, t.f->nchars);
952 cfabc3ed 2003-11-23 devnull }
953 cfabc3ed 2003-11-23 devnull
954 cfabc3ed 2003-11-23 devnull void
955 cfabc3ed 2003-11-23 devnull updatesel(void)
956 cfabc3ed 2003-11-23 devnull {
957 cfabc3ed 2003-11-23 devnull Frame *f;
958 cfabc3ed 2003-11-23 devnull uint n;
959 cfabc3ed 2003-11-23 devnull
960 cfabc3ed 2003-11-23 devnull f = t.f;
961 cfabc3ed 2003-11-23 devnull if(t.org+f->p0 == t.q0 && t.org+f->p1 == t.q1)
962 cfabc3ed 2003-11-23 devnull return;
963 cfabc3ed 2003-11-23 devnull
964 cfabc3ed 2003-11-23 devnull n = t.f->nchars;
965 cfabc3ed 2003-11-23 devnull
966 cfabc3ed 2003-11-23 devnull frdrawsel(f, frptofchar(f, f->p0), f->p0, f->p1, 0);
967 cfabc3ed 2003-11-23 devnull if (t.q0 >= t.org)
968 cfabc3ed 2003-11-23 devnull f->p0 = t.q0-t.org;
969 cfabc3ed 2003-11-23 devnull else
970 cfabc3ed 2003-11-23 devnull f->p0 = 0;
971 cfabc3ed 2003-11-23 devnull if(f->p0 > n)
972 cfabc3ed 2003-11-23 devnull f->p0 = n;
973 cfabc3ed 2003-11-23 devnull if (t.q1 >= t.org)
974 cfabc3ed 2003-11-23 devnull f->p1 = t.q1-t.org;
975 cfabc3ed 2003-11-23 devnull else
976 cfabc3ed 2003-11-23 devnull f->p1 = 0;
977 cfabc3ed 2003-11-23 devnull if(f->p1 > n)
978 cfabc3ed 2003-11-23 devnull f->p1 = n;
979 cfabc3ed 2003-11-23 devnull frdrawsel(f, frptofchar(f, f->p0), f->p0, f->p1, 1);
980 cfabc3ed 2003-11-23 devnull
981 cfabc3ed 2003-11-23 devnull /*
982 cfabc3ed 2003-11-23 devnull if(t.qh<=t.org+t.f.nchars && t.cwqueue != 0)
983 cfabc3ed 2003-11-23 devnull t.cwqueue->wakeup <-= 0;
984 cfabc3ed 2003-11-23 devnull */
985 cfabc3ed 2003-11-23 devnull
986 cfabc3ed 2003-11-23 devnull tcheck();
987 cfabc3ed 2003-11-23 devnull }
988 cfabc3ed 2003-11-23 devnull
989 cfabc3ed 2003-11-23 devnull void
990 cfabc3ed 2003-11-23 devnull show(uint q0)
991 cfabc3ed 2003-11-23 devnull {
992 cfabc3ed 2003-11-23 devnull int nl;
993 cfabc3ed 2003-11-23 devnull uint q, oq;
994 cfabc3ed 2003-11-23 devnull
995 cfabc3ed 2003-11-23 devnull if(cansee(q0))
996 cfabc3ed 2003-11-23 devnull return;
997 cfabc3ed 2003-11-23 devnull
998 cfabc3ed 2003-11-23 devnull if (q0<t.org)
999 cfabc3ed 2003-11-23 devnull nl = t.f->maxlines/5;
1000 cfabc3ed 2003-11-23 devnull else
1001 cfabc3ed 2003-11-23 devnull nl = 4*t.f->maxlines/5;
1002 cfabc3ed 2003-11-23 devnull q = backnl(q0, nl);
1003 cfabc3ed 2003-11-23 devnull /* avoid going in the wrong direction */
1004 cfabc3ed 2003-11-23 devnull if (q0>t.org && q<t.org)
1005 cfabc3ed 2003-11-23 devnull q = t.org;
1006 cfabc3ed 2003-11-23 devnull setorigin(q, 0);
1007 cfabc3ed 2003-11-23 devnull /* keep trying until q0 is on the screen */
1008 cfabc3ed 2003-11-23 devnull while(!cansee(q0)) {
1009 cfabc3ed 2003-11-23 devnull assert(q0 >= t.org);
1010 cfabc3ed 2003-11-23 devnull oq = q;
1011 cfabc3ed 2003-11-23 devnull q = line2q(t.f->maxlines-nl);
1012 cfabc3ed 2003-11-23 devnull assert(q > oq);
1013 cfabc3ed 2003-11-23 devnull setorigin(q, 1);
1014 cfabc3ed 2003-11-23 devnull }
1015 cfabc3ed 2003-11-23 devnull }
1016 cfabc3ed 2003-11-23 devnull
1017 cfabc3ed 2003-11-23 devnull int
1018 cfabc3ed 2003-11-23 devnull cansee(uint q0)
1019 cfabc3ed 2003-11-23 devnull {
1020 cfabc3ed 2003-11-23 devnull uint qe;
1021 cfabc3ed 2003-11-23 devnull
1022 cfabc3ed 2003-11-23 devnull qe = t.org+t.f->nchars;
1023 cfabc3ed 2003-11-23 devnull
1024 cfabc3ed 2003-11-23 devnull if(q0>=t.org && q0 < qe)
1025 cfabc3ed 2003-11-23 devnull return 1;
1026 cfabc3ed 2003-11-23 devnull if (q0 != qe)
1027 cfabc3ed 2003-11-23 devnull return 0;
1028 cfabc3ed 2003-11-23 devnull if (t.f->nlines < t.f->maxlines)
1029 cfabc3ed 2003-11-23 devnull return 1;
1030 cfabc3ed 2003-11-23 devnull if (q0 > 0 && t.r[t.nr-1] == '\n')
1031 cfabc3ed 2003-11-23 devnull return 0;
1032 cfabc3ed 2003-11-23 devnull return 1;
1033 cfabc3ed 2003-11-23 devnull }
1034 cfabc3ed 2003-11-23 devnull
1035 cfabc3ed 2003-11-23 devnull
1036 cfabc3ed 2003-11-23 devnull void
1037 cfabc3ed 2003-11-23 devnull setorigin(uint org, int exact)
1038 cfabc3ed 2003-11-23 devnull {
1039 cfabc3ed 2003-11-23 devnull int i, a;
1040 cfabc3ed 2003-11-23 devnull uint n;
1041 cfabc3ed 2003-11-23 devnull
1042 cfabc3ed 2003-11-23 devnull if(org>0 && !exact){
1043 cfabc3ed 2003-11-23 devnull /* try and start after a newline */
1044 cfabc3ed 2003-11-23 devnull /* don't try harder than 256 chars */
1045 cfabc3ed 2003-11-23 devnull for(i=0; i<256 && org<t.nr; i++){
1046 cfabc3ed 2003-11-23 devnull if(t.r[org-1] == '\n')
1047 cfabc3ed 2003-11-23 devnull break;
1048 cfabc3ed 2003-11-23 devnull org++;
1049 cfabc3ed 2003-11-23 devnull }
1050 cfabc3ed 2003-11-23 devnull }
1051 cfabc3ed 2003-11-23 devnull a = org-t.org;
1052 cfabc3ed 2003-11-23 devnull
1053 cfabc3ed 2003-11-23 devnull if(a>=0 && a<t.f->nchars)
1054 cfabc3ed 2003-11-23 devnull frdelete(t.f, 0, a);
1055 cfabc3ed 2003-11-23 devnull else if(a<0 && -a<100*t.f->maxlines){
1056 cfabc3ed 2003-11-23 devnull n = t.org - org;
1057 cfabc3ed 2003-11-23 devnull frinsert(t.f, t.r+org, t.r+org+n, 0);
1058 cfabc3ed 2003-11-23 devnull }else
1059 cfabc3ed 2003-11-23 devnull frdelete(t.f, 0, t.f->nchars);
1060 cfabc3ed 2003-11-23 devnull t.org = org;
1061 cfabc3ed 2003-11-23 devnull fill();
1062 cfabc3ed 2003-11-23 devnull updatesel();
1063 cfabc3ed 2003-11-23 devnull }
1064 cfabc3ed 2003-11-23 devnull
1065 cfabc3ed 2003-11-23 devnull
1066 cfabc3ed 2003-11-23 devnull uint
1067 cfabc3ed 2003-11-23 devnull line2q(uint n)
1068 cfabc3ed 2003-11-23 devnull {
1069 cfabc3ed 2003-11-23 devnull Frame *f;
1070 cfabc3ed 2003-11-23 devnull
1071 cfabc3ed 2003-11-23 devnull f = t.f;
1072 cfabc3ed 2003-11-23 devnull return frcharofpt(f, Pt(f->r.min.x, f->r.min.y + n*font->height))+t.org;
1073 cfabc3ed 2003-11-23 devnull }
1074 cfabc3ed 2003-11-23 devnull
1075 cfabc3ed 2003-11-23 devnull uint
1076 cfabc3ed 2003-11-23 devnull backnl(uint p, uint n)
1077 cfabc3ed 2003-11-23 devnull {
1078 cfabc3ed 2003-11-23 devnull int i, j;
1079 cfabc3ed 2003-11-23 devnull
1080 cfabc3ed 2003-11-23 devnull for (i = n;; i--) {
1081 cfabc3ed 2003-11-23 devnull /* at 256 chars, call it a line anyway */
1082 cfabc3ed 2003-11-23 devnull for(j=256; --j>0 && p>0; p--)
1083 cfabc3ed 2003-11-23 devnull if(t.r[p-1]=='\n')
1084 cfabc3ed 2003-11-23 devnull break;
1085 cfabc3ed 2003-11-23 devnull if (p == 0 || i == 0)
1086 cfabc3ed 2003-11-23 devnull return p;
1087 cfabc3ed 2003-11-23 devnull p--;
1088 cfabc3ed 2003-11-23 devnull }
1089 cfabc3ed 2003-11-23 devnull return 0; /* alef bug */
1090 cfabc3ed 2003-11-23 devnull }
1091 cfabc3ed 2003-11-23 devnull
1092 cfabc3ed 2003-11-23 devnull void
1093 cfabc3ed 2003-11-23 devnull addraw(Rune *r, int nr)
1094 cfabc3ed 2003-11-23 devnull {
1095 cfabc3ed 2003-11-23 devnull t.raw = runerealloc(t.raw, t.nraw+nr);
1096 cfabc3ed 2003-11-23 devnull runemove(t.raw+t.nraw, r, nr);
1097 cfabc3ed 2003-11-23 devnull t.nraw += nr;
1098 cfabc3ed 2003-11-23 devnull /*
1099 cfabc3ed 2003-11-23 devnull if(t.crqueue != nil)
1100 cfabc3ed 2003-11-23 devnull t.crqueue->wakeup <-= 0;
1101 cfabc3ed 2003-11-23 devnull */
1102 cfabc3ed 2003-11-23 devnull }
1103 cfabc3ed 2003-11-23 devnull
1104 cfabc3ed 2003-11-23 devnull
1105 cfabc3ed 2003-11-23 devnull Rune left1[] = { '{', '[', '(', '<', 0xab, 0 };
1106 cfabc3ed 2003-11-23 devnull Rune right1[] = { '}', ']', ')', '>', 0xbb, 0 };
1107 cfabc3ed 2003-11-23 devnull Rune left2[] = { '\n', 0 };
1108 cfabc3ed 2003-11-23 devnull Rune left3[] = { '\'', '"', '`', 0 };
1109 cfabc3ed 2003-11-23 devnull
1110 cfabc3ed 2003-11-23 devnull Rune *left[] = {
1111 cfabc3ed 2003-11-23 devnull left1,
1112 cfabc3ed 2003-11-23 devnull left2,
1113 cfabc3ed 2003-11-23 devnull left3,
1114 cfabc3ed 2003-11-23 devnull 0
1115 cfabc3ed 2003-11-23 devnull };
1116 cfabc3ed 2003-11-23 devnull
1117 cfabc3ed 2003-11-23 devnull Rune *right[] = {
1118 cfabc3ed 2003-11-23 devnull right1,
1119 cfabc3ed 2003-11-23 devnull left2,
1120 cfabc3ed 2003-11-23 devnull left3,
1121 cfabc3ed 2003-11-23 devnull 0
1122 cfabc3ed 2003-11-23 devnull };
1123 cfabc3ed 2003-11-23 devnull
1124 cfabc3ed 2003-11-23 devnull void
1125 cfabc3ed 2003-11-23 devnull doubleclick(uint *q0, uint *q1)
1126 cfabc3ed 2003-11-23 devnull {
1127 cfabc3ed 2003-11-23 devnull int c, i;
1128 cfabc3ed 2003-11-23 devnull Rune *r, *l, *p;
1129 cfabc3ed 2003-11-23 devnull uint q;
1130 cfabc3ed 2003-11-23 devnull
1131 cfabc3ed 2003-11-23 devnull for(i=0; left[i]!=0; i++){
1132 cfabc3ed 2003-11-23 devnull q = *q0;
1133 cfabc3ed 2003-11-23 devnull l = left[i];
1134 cfabc3ed 2003-11-23 devnull r = right[i];
1135 cfabc3ed 2003-11-23 devnull /* try matching character to left, looking right */
1136 cfabc3ed 2003-11-23 devnull if(q == 0)
1137 cfabc3ed 2003-11-23 devnull c = '\n';
1138 cfabc3ed 2003-11-23 devnull else
1139 cfabc3ed 2003-11-23 devnull c = t.r[q-1];
1140 cfabc3ed 2003-11-23 devnull p = strrune(l, c);
1141 cfabc3ed 2003-11-23 devnull if(p != 0){
1142 cfabc3ed 2003-11-23 devnull if(clickmatch(c, r[p-l], 1, &q))
1143 cfabc3ed 2003-11-23 devnull *q1 = q-(c!='\n');
1144 cfabc3ed 2003-11-23 devnull return;
1145 cfabc3ed 2003-11-23 devnull }
1146 cfabc3ed 2003-11-23 devnull /* try matching character to right, looking left */
1147 cfabc3ed 2003-11-23 devnull if(q == t.nr)
1148 cfabc3ed 2003-11-23 devnull c = '\n';
1149 cfabc3ed 2003-11-23 devnull else
1150 cfabc3ed 2003-11-23 devnull c = t.r[q];
1151 cfabc3ed 2003-11-23 devnull p = strrune(r, c);
1152 cfabc3ed 2003-11-23 devnull if(p != 0){
1153 cfabc3ed 2003-11-23 devnull if(clickmatch(c, l[p-r], -1, &q)){
1154 cfabc3ed 2003-11-23 devnull *q1 = *q0+(*q0<t.nr && c=='\n');
1155 cfabc3ed 2003-11-23 devnull *q0 = q;
1156 cfabc3ed 2003-11-23 devnull if(c!='\n' || q!=0 || t.r[0]=='\n')
1157 cfabc3ed 2003-11-23 devnull (*q0)++;
1158 cfabc3ed 2003-11-23 devnull }
1159 cfabc3ed 2003-11-23 devnull return;
1160 cfabc3ed 2003-11-23 devnull }
1161 cfabc3ed 2003-11-23 devnull }
1162 cfabc3ed 2003-11-23 devnull /* try filling out word to right */
1163 cfabc3ed 2003-11-23 devnull while(*q1<t.nr && isalnum(t.r[*q1]))
1164 cfabc3ed 2003-11-23 devnull (*q1)++;
1165 cfabc3ed 2003-11-23 devnull /* try filling out word to left */
1166 cfabc3ed 2003-11-23 devnull while(*q0>0 && isalnum(t.r[*q0-1]))
1167 cfabc3ed 2003-11-23 devnull (*q0)--;
1168 cfabc3ed 2003-11-23 devnull }
1169 cfabc3ed 2003-11-23 devnull
1170 cfabc3ed 2003-11-23 devnull int
1171 cfabc3ed 2003-11-23 devnull clickmatch(int cl, int cr, int dir, uint *q)
1172 cfabc3ed 2003-11-23 devnull {
1173 cfabc3ed 2003-11-23 devnull Rune c;
1174 cfabc3ed 2003-11-23 devnull int nest;
1175 cfabc3ed 2003-11-23 devnull
1176 cfabc3ed 2003-11-23 devnull nest = 1;
1177 cfabc3ed 2003-11-23 devnull for(;;){
1178 cfabc3ed 2003-11-23 devnull if(dir > 0){
1179 cfabc3ed 2003-11-23 devnull if(*q == t.nr)
1180 cfabc3ed 2003-11-23 devnull break;
1181 cfabc3ed 2003-11-23 devnull c = t.r[*q];
1182 cfabc3ed 2003-11-23 devnull (*q)++;
1183 cfabc3ed 2003-11-23 devnull }else{
1184 cfabc3ed 2003-11-23 devnull if(*q == 0)
1185 cfabc3ed 2003-11-23 devnull break;
1186 cfabc3ed 2003-11-23 devnull (*q)--;
1187 cfabc3ed 2003-11-23 devnull c = t.r[*q];
1188 cfabc3ed 2003-11-23 devnull }
1189 cfabc3ed 2003-11-23 devnull if(c == cr){
1190 cfabc3ed 2003-11-23 devnull if(--nest==0)
1191 cfabc3ed 2003-11-23 devnull return 1;
1192 cfabc3ed 2003-11-23 devnull }else if(c == cl)
1193 cfabc3ed 2003-11-23 devnull nest++;
1194 cfabc3ed 2003-11-23 devnull }
1195 cfabc3ed 2003-11-23 devnull return cl=='\n' && nest==1;
1196 cfabc3ed 2003-11-23 devnull }
1197 cfabc3ed 2003-11-23 devnull
1198 cfabc3ed 2003-11-23 devnull void
1199 d3acba95 2003-12-04 devnull rcstart(int fd[2], int argc, char **argv)
1200 cfabc3ed 2003-11-23 devnull {
1201 cfabc3ed 2003-11-23 devnull int pid;
1202 d3acba95 2003-12-04 devnull char *xargv[3];
1203 cfabc3ed 2003-11-23 devnull char slave[256];
1204 cfabc3ed 2003-11-23 devnull int sfd;
1205 cfabc3ed 2003-11-23 devnull
1206 d3acba95 2003-12-04 devnull if(argc == 0){
1207 d3acba95 2003-12-04 devnull argc = 2;
1208 d3acba95 2003-12-04 devnull argv = xargv;
1209 d3acba95 2003-12-04 devnull argv[0] = getenv("SHELL");
1210 d3acba95 2003-12-04 devnull if(argv[0] == 0)
1211 d3acba95 2003-12-04 devnull argv[0] = "rc";
1212 d3acba95 2003-12-04 devnull argv[1] = "-i";
1213 d3acba95 2003-12-04 devnull argv[2] = 0;
1214 d3acba95 2003-12-04 devnull }
1215 669250d1 2003-12-03 devnull /*
1216 669250d1 2003-12-03 devnull * fd0 is slave (tty), fd1 is master (pty)
1217 669250d1 2003-12-03 devnull */
1218 669250d1 2003-12-03 devnull fd[0] = fd[1] = -1;
1219 669250d1 2003-12-03 devnull if(getpts(fd, slave) < 0)
1220 669250d1 2003-12-03 devnull fprint(2, "getpts: %r\n");
1221 669250d1 2003-12-03 devnull
1222 cfabc3ed 2003-11-23 devnull switch(pid = fork()) {
1223 cfabc3ed 2003-11-23 devnull case 0:
1224 32f69c36 2003-12-11 devnull putenv("TERM", "9term");
1225 cfabc3ed 2003-11-23 devnull close(fd[1]);
1226 cfabc3ed 2003-11-23 devnull setsid();
1227 669250d1 2003-12-03 devnull // tcsetpgrp(0, pid);
1228 cfabc3ed 2003-11-23 devnull sfd = open(slave, ORDWR);
1229 669250d1 2003-12-03 devnull if(sfd < 0)
1230 669250d1 2003-12-03 devnull fprint(2, "open %s: %r\n", slave);
1231 669250d1 2003-12-03 devnull if(ioctl(sfd, TIOCSCTTY, 0) < 0)
1232 669250d1 2003-12-03 devnull fprint(2, "ioctl TIOCSCTTY: %r\n");
1233 cfabc3ed 2003-11-23 devnull // ioctl(sfd, I_PUSH, "ptem");
1234 cfabc3ed 2003-11-23 devnull // ioctl(sfd, I_PUSH, "ldterm");
1235 cfabc3ed 2003-11-23 devnull dup(sfd, 0);
1236 cfabc3ed 2003-11-23 devnull dup(sfd, 1);
1237 cfabc3ed 2003-11-23 devnull dup(sfd, 2);
1238 683c5e53 2003-12-04 devnull system("stty tabs -onlcr -echo");
1239 cfabc3ed 2003-11-23 devnull execvp(argv[0], argv);
1240 32f69c36 2003-12-11 devnull fprint(2, "exec %s failed: %r\n", argv[0]);
1241 669250d1 2003-12-03 devnull _exits("oops");
1242 cfabc3ed 2003-11-23 devnull break;
1243 cfabc3ed 2003-11-23 devnull case -1:
1244 cfabc3ed 2003-11-23 devnull fatal("proc failed: %r");
1245 cfabc3ed 2003-11-23 devnull break;
1246 cfabc3ed 2003-11-23 devnull }
1247 cfabc3ed 2003-11-23 devnull close(fd[0]);
1248 cfabc3ed 2003-11-23 devnull fd[0] = fd[1];
1249 cfabc3ed 2003-11-23 devnull
1250 cfabc3ed 2003-11-23 devnull rcpid = pid;
1251 cfabc3ed 2003-11-23 devnull }
1252 cfabc3ed 2003-11-23 devnull
1253 cfabc3ed 2003-11-23 devnull void
1254 cfabc3ed 2003-11-23 devnull tcheck(void)
1255 cfabc3ed 2003-11-23 devnull {
1256 cfabc3ed 2003-11-23 devnull Frame *f;
1257 cfabc3ed 2003-11-23 devnull
1258 cfabc3ed 2003-11-23 devnull f = t.f;
1259 cfabc3ed 2003-11-23 devnull
1260 cfabc3ed 2003-11-23 devnull assert(t.q0 <= t.q1 && t.q1 <= t.nr);
1261 cfabc3ed 2003-11-23 devnull assert(t.org <= t.nr && t.qh <= t.nr);
1262 cfabc3ed 2003-11-23 devnull assert(f->p0 <= f->p1 && f->p1 <= f->nchars);
1263 cfabc3ed 2003-11-23 devnull assert(t.org + f->nchars <= t.nr);
1264 cfabc3ed 2003-11-23 devnull assert(t.org+f->nchars==t.nr || (f->nlines >= f->maxlines));
1265 cfabc3ed 2003-11-23 devnull }
1266 cfabc3ed 2003-11-23 devnull
1267 cfabc3ed 2003-11-23 devnull Rune*
1268 cfabc3ed 2003-11-23 devnull strrune(Rune *s, Rune c)
1269 cfabc3ed 2003-11-23 devnull {
1270 cfabc3ed 2003-11-23 devnull Rune c1;
1271 cfabc3ed 2003-11-23 devnull
1272 cfabc3ed 2003-11-23 devnull if(c == 0) {
1273 cfabc3ed 2003-11-23 devnull while(*s++)
1274 cfabc3ed 2003-11-23 devnull ;
1275 cfabc3ed 2003-11-23 devnull return s-1;
1276 cfabc3ed 2003-11-23 devnull }
1277 cfabc3ed 2003-11-23 devnull
1278 cfabc3ed 2003-11-23 devnull while(c1 = *s++)
1279 cfabc3ed 2003-11-23 devnull if(c1 == c)
1280 cfabc3ed 2003-11-23 devnull return s-1;
1281 cfabc3ed 2003-11-23 devnull return 0;
1282 cfabc3ed 2003-11-23 devnull }
1283 cfabc3ed 2003-11-23 devnull
1284 cfabc3ed 2003-11-23 devnull void
1285 cfabc3ed 2003-11-23 devnull scrdraw(void)
1286 cfabc3ed 2003-11-23 devnull {
1287 cfabc3ed 2003-11-23 devnull Rectangle r, r1, r2;
1288 cfabc3ed 2003-11-23 devnull static Image *scrx;
1289 cfabc3ed 2003-11-23 devnull
1290 cfabc3ed 2003-11-23 devnull r = scrollr;
1291 cfabc3ed 2003-11-23 devnull r.min.x += 1; /* border between margin and bar */
1292 cfabc3ed 2003-11-23 devnull r1 = r;
1293 cfabc3ed 2003-11-23 devnull if(scrx==0 || scrx->r.max.y < r.max.y){
1294 cfabc3ed 2003-11-23 devnull if(scrx)
1295 cfabc3ed 2003-11-23 devnull freeimage(scrx);
1296 cfabc3ed 2003-11-23 devnull scrx = allocimage(display, Rect(0, 0, 32, r.max.y), screen->chan, 1, DPaleyellow);
1297 cfabc3ed 2003-11-23 devnull if(scrx == 0)
1298 cfabc3ed 2003-11-23 devnull fatal("scroll balloc");
1299 cfabc3ed 2003-11-23 devnull }
1300 cfabc3ed 2003-11-23 devnull r1.min.x = 0;
1301 cfabc3ed 2003-11-23 devnull r1.max.x = Dx(r);
1302 cfabc3ed 2003-11-23 devnull r2 = scrpos(r1, t.org, t.org+t.f->nchars, t.nr);
1303 cfabc3ed 2003-11-23 devnull if(!eqrect(r2, lastsr)){
1304 cfabc3ed 2003-11-23 devnull lastsr = r2;
1305 cfabc3ed 2003-11-23 devnull draw(scrx, r1, cols[BORD], nil, ZP);
1306 cfabc3ed 2003-11-23 devnull draw(scrx, r2, cols[BACK], nil, r2.min);
1307 cfabc3ed 2003-11-23 devnull // r2 = r1;
1308 cfabc3ed 2003-11-23 devnull // r2.min.x = r2.max.x-1;
1309 cfabc3ed 2003-11-23 devnull // draw(scrx, r2, cols[BORD], nil, ZP);
1310 cfabc3ed 2003-11-23 devnull draw(screen, r, scrx, nil, r1.min);
1311 cfabc3ed 2003-11-23 devnull }
1312 cfabc3ed 2003-11-23 devnull }
1313 cfabc3ed 2003-11-23 devnull
1314 cfabc3ed 2003-11-23 devnull Rectangle
1315 cfabc3ed 2003-11-23 devnull scrpos(Rectangle r, ulong p0, ulong p1, ulong tot)
1316 cfabc3ed 2003-11-23 devnull {
1317 cfabc3ed 2003-11-23 devnull long h;
1318 cfabc3ed 2003-11-23 devnull Rectangle q;
1319 cfabc3ed 2003-11-23 devnull
1320 cfabc3ed 2003-11-23 devnull q = insetrect(r, 1);
1321 cfabc3ed 2003-11-23 devnull h = q.max.y-q.min.y;
1322 cfabc3ed 2003-11-23 devnull if(tot == 0)
1323 cfabc3ed 2003-11-23 devnull return q;
1324 cfabc3ed 2003-11-23 devnull if(tot > 1024L*1024L)
1325 cfabc3ed 2003-11-23 devnull tot >>= 10, p0 >>= 10, p1 >>= 10;
1326 cfabc3ed 2003-11-23 devnull if(p0 > 0)
1327 cfabc3ed 2003-11-23 devnull q.min.y += h*p0/tot;
1328 cfabc3ed 2003-11-23 devnull if(p1 < tot)
1329 cfabc3ed 2003-11-23 devnull q.max.y -= h*(tot-p1)/tot;
1330 cfabc3ed 2003-11-23 devnull if(q.max.y < q.min.y+2){
1331 cfabc3ed 2003-11-23 devnull if(q.min.y+2 <= r.max.y)
1332 cfabc3ed 2003-11-23 devnull q.max.y = q.min.y+2;
1333 cfabc3ed 2003-11-23 devnull else
1334 cfabc3ed 2003-11-23 devnull q.min.y = q.max.y-2;
1335 cfabc3ed 2003-11-23 devnull }
1336 cfabc3ed 2003-11-23 devnull return q;
1337 cfabc3ed 2003-11-23 devnull }
1338 cfabc3ed 2003-11-23 devnull
1339 cfabc3ed 2003-11-23 devnull void
1340 cfabc3ed 2003-11-23 devnull scroll(int but)
1341 cfabc3ed 2003-11-23 devnull {
1342 cfabc3ed 2003-11-23 devnull uint p0, oldp0;
1343 cfabc3ed 2003-11-23 devnull Rectangle s;
1344 cfabc3ed 2003-11-23 devnull int x, y, my, h, first, exact;
1345 cfabc3ed 2003-11-23 devnull
1346 cfabc3ed 2003-11-23 devnull s = insetrect(scrollr, 1);
1347 cfabc3ed 2003-11-23 devnull h = s.max.y-s.min.y;
1348 cfabc3ed 2003-11-23 devnull x = (s.min.x+s.max.x)/2;
1349 cfabc3ed 2003-11-23 devnull oldp0 = ~0;
1350 cfabc3ed 2003-11-23 devnull first = 1;
1351 cfabc3ed 2003-11-23 devnull do{
1352 cfabc3ed 2003-11-23 devnull if(t.m.xy.x<s.min.x || s.max.x<=t.m.xy.x){
1353 cfabc3ed 2003-11-23 devnull readmouse(mc);
1354 cfabc3ed 2003-11-23 devnull t.m = mc->m;
1355 cfabc3ed 2003-11-23 devnull }else{
1356 cfabc3ed 2003-11-23 devnull my = t.m.xy.y;
1357 cfabc3ed 2003-11-23 devnull if(my < s.min.y)
1358 cfabc3ed 2003-11-23 devnull my = s.min.y;
1359 cfabc3ed 2003-11-23 devnull if(my >= s.max.y)
1360 cfabc3ed 2003-11-23 devnull my = s.max.y;
1361 cfabc3ed 2003-11-23 devnull // if(!eqpt(t.m.xy, Pt(x, my)))
1362 cfabc3ed 2003-11-23 devnull // cursorset(Pt(x, my));
1363 cfabc3ed 2003-11-23 devnull exact = 1;
1364 cfabc3ed 2003-11-23 devnull if(but == 2){
1365 cfabc3ed 2003-11-23 devnull y = my;
1366 cfabc3ed 2003-11-23 devnull if(y > s.max.y-2)
1367 cfabc3ed 2003-11-23 devnull y = s.max.y-2;
1368 cfabc3ed 2003-11-23 devnull if(t.nr > 1024*1024)
1369 cfabc3ed 2003-11-23 devnull p0 = ((t.nr>>10)*(y-s.min.y)/h)<<10;
1370 cfabc3ed 2003-11-23 devnull else
1371 cfabc3ed 2003-11-23 devnull p0 = t.nr*(y-s.min.y)/h;
1372 cfabc3ed 2003-11-23 devnull exact = 0;
1373 cfabc3ed 2003-11-23 devnull } else if(but == 1)
1374 cfabc3ed 2003-11-23 devnull p0 = backnl(t.org, (my-s.min.y)/font->height);
1375 cfabc3ed 2003-11-23 devnull else
1376 cfabc3ed 2003-11-23 devnull p0 = t.org+frcharofpt(t.f, Pt(s.max.x, my));
1377 cfabc3ed 2003-11-23 devnull
1378 cfabc3ed 2003-11-23 devnull if(oldp0 != p0)
1379 cfabc3ed 2003-11-23 devnull setorigin(p0, exact);
1380 cfabc3ed 2003-11-23 devnull oldp0 = p0;
1381 cfabc3ed 2003-11-23 devnull scrdraw();
1382 cfabc3ed 2003-11-23 devnull readmouse(mc);
1383 cfabc3ed 2003-11-23 devnull t.m = mc->m;
1384 cfabc3ed 2003-11-23 devnull }
1385 cfabc3ed 2003-11-23 devnull }while(t.m.buttons & (1<<(but-1)));
1386 cfabc3ed 2003-11-23 devnull }
1387 cfabc3ed 2003-11-23 devnull
1388 cfabc3ed 2003-11-23 devnull void
1389 cfabc3ed 2003-11-23 devnull plumbstart(void)
1390 cfabc3ed 2003-11-23 devnull {
1391 32f69c36 2003-12-11 devnull if((plumbfd = plumbopen("send", OWRITE)) < 0)
1392 cfabc3ed 2003-11-23 devnull fatal("plumbopen");
1393 cfabc3ed 2003-11-23 devnull }
1394 cfabc3ed 2003-11-23 devnull
1395 cfabc3ed 2003-11-23 devnull void
1396 cfabc3ed 2003-11-23 devnull plumb(uint q0, uint q1)
1397 cfabc3ed 2003-11-23 devnull {
1398 cfabc3ed 2003-11-23 devnull Plumbmsg *pm;
1399 cfabc3ed 2003-11-23 devnull char *p;
1400 cfabc3ed 2003-11-23 devnull int i, p0, n;
1401 cfabc3ed 2003-11-23 devnull char cbuf[100];
1402 21a17ff3 2003-11-25 devnull char *w;
1403 cfabc3ed 2003-11-23 devnull
1404 f1613419 2003-11-25 devnull if(getchildwd(rcpid, childwdir, sizeof childwdir) == 0)
1405 21a17ff3 2003-11-25 devnull w = childwdir;
1406 21a17ff3 2003-11-25 devnull else
1407 21a17ff3 2003-11-25 devnull w = wdir;
1408 cfabc3ed 2003-11-23 devnull pm = malloc(sizeof(Plumbmsg));
1409 cfabc3ed 2003-11-23 devnull pm->src = strdup("9term");
1410 cfabc3ed 2003-11-23 devnull pm->dst = 0;
1411 21a17ff3 2003-11-25 devnull pm->wdir = strdup(w);
1412 cfabc3ed 2003-11-23 devnull pm->type = strdup("text");
1413 cfabc3ed 2003-11-23 devnull if(q1 > q0)
1414 cfabc3ed 2003-11-23 devnull pm->attr = nil;
1415 cfabc3ed 2003-11-23 devnull else{
1416 cfabc3ed 2003-11-23 devnull p0 = q0;
1417 d3acba95 2003-12-04 devnull wordclick(&q0, &q1);
1418 cfabc3ed 2003-11-23 devnull sprint(cbuf, "click=%d", p0-q0);
1419 cfabc3ed 2003-11-23 devnull pm->attr = plumbunpackattr(cbuf);
1420 cfabc3ed 2003-11-23 devnull }
1421 cfabc3ed 2003-11-23 devnull if(q0==q1){
1422 cfabc3ed 2003-11-23 devnull plumbfree(pm);
1423 cfabc3ed 2003-11-23 devnull return;
1424 cfabc3ed 2003-11-23 devnull }
1425 cfabc3ed 2003-11-23 devnull pm->data = malloc(SnarfSize);
1426 cfabc3ed 2003-11-23 devnull n = q1 - q0;
1427 cfabc3ed 2003-11-23 devnull for(i=0,p=pm->data; i<n && p < pm->data + SnarfSize-UTFmax; i++)
1428 cfabc3ed 2003-11-23 devnull p += runetochar(p, t.r+q0+i);
1429 cfabc3ed 2003-11-23 devnull *p = '\0';
1430 cfabc3ed 2003-11-23 devnull pm->ndata = strlen(pm->data);
1431 cfabc3ed 2003-11-23 devnull plumbsend(plumbfd, pm);
1432 cfabc3ed 2003-11-23 devnull plumbfree(pm);
1433 cfabc3ed 2003-11-23 devnull }
1434 cfabc3ed 2003-11-23 devnull
1435 cfabc3ed 2003-11-23 devnull /*
1436 cfabc3ed 2003-11-23 devnull * Process in-band messages about window title changes.
1437 cfabc3ed 2003-11-23 devnull * The messages are of the form:
1438 cfabc3ed 2003-11-23 devnull *
1439 cfabc3ed 2003-11-23 devnull * \033];xxx\007
1440 cfabc3ed 2003-11-23 devnull *
1441 cfabc3ed 2003-11-23 devnull * where xxx is the new directory. This format was chosen
1442 cfabc3ed 2003-11-23 devnull * because it changes the label on xterm windows.
1443 cfabc3ed 2003-11-23 devnull */
1444 cfabc3ed 2003-11-23 devnull int
1445 cfabc3ed 2003-11-23 devnull label(Rune *sr, int n)
1446 cfabc3ed 2003-11-23 devnull {
1447 cfabc3ed 2003-11-23 devnull Rune *sl, *el, *er, *r;
1448 cfabc3ed 2003-11-23 devnull
1449 cfabc3ed 2003-11-23 devnull er = sr+n;
1450 cfabc3ed 2003-11-23 devnull for(r=er-1; r>=sr; r--)
1451 cfabc3ed 2003-11-23 devnull if(*r == '\007')
1452 cfabc3ed 2003-11-23 devnull break;
1453 cfabc3ed 2003-11-23 devnull if(r < sr)
1454 cfabc3ed 2003-11-23 devnull return n;
1455 cfabc3ed 2003-11-23 devnull
1456 cfabc3ed 2003-11-23 devnull el = r+1;
1457 cfabc3ed 2003-11-23 devnull if(el-sr > sizeof wdir)
1458 cfabc3ed 2003-11-23 devnull sr = el - sizeof wdir;
1459 cfabc3ed 2003-11-23 devnull for(sl=el-3; sl>=sr; sl--)
1460 cfabc3ed 2003-11-23 devnull if(sl[0]=='\033' && sl[1]==']' && sl[2]==';')
1461 cfabc3ed 2003-11-23 devnull break;
1462 cfabc3ed 2003-11-23 devnull if(sl < sr)
1463 cfabc3ed 2003-11-23 devnull return n;
1464 cfabc3ed 2003-11-23 devnull
1465 cfabc3ed 2003-11-23 devnull snprint(wdir, sizeof wdir, "%.*S", (el-1)-(sl+3), sl+3);
1466 cfabc3ed 2003-11-23 devnull drawsetlabel(display, wdir);
1467 cfabc3ed 2003-11-23 devnull
1468 cfabc3ed 2003-11-23 devnull runemove(sl, el, er-el);
1469 cfabc3ed 2003-11-23 devnull n -= (el-sl);
1470 cfabc3ed 2003-11-23 devnull return n;
1471 cfabc3ed 2003-11-23 devnull }
1472 cfabc3ed 2003-11-23 devnull