]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - win32/nt.screen.c
Import of tcsh-6.18.01
[FreeBSD/FreeBSD.git] / win32 / nt.screen.c
1 /*$Header: /p/tcsh/cvsroot/tcsh/win32/nt.screen.c,v 1.14 2006/03/14 01:22:57 mitr Exp $*/
2 /*
3  * ed.screen.c: Editor/termcap-curses interface
4  */
5 /*-
6  * Copyright (c) 1980, 1991 The Regents of the University of California.
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions and the following disclaimer.
14  * 2. Redistributions in binary form must reproduce the above copyright
15  *    notice, this list of conditions and the following disclaimer in the
16  *    documentation and/or other materials provided with the distribution.
17  * 3. Neither the name of the University nor the names of its contributors
18  *    may be used to endorse or promote products derived from this software
19  *    without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
22  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
25  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  */
33 #include "sh.h"
34
35
36 #include "ed.h"
37 #include "tc.h"
38 #include "ed.defns.h"
39
40
41 /* #define DEBUG_LITERAL */
42
43 /*
44  * IMPORTANT NOTE: these routines are allowed to look at the current screen
45  * and the current possition assuming that it is correct.  If this is not
46  * true, then the update will be WRONG!  This is (should be) a valid
47  * assumption...
48  */
49
50
51
52 extern int nt_getsize(int*,int*,int*);
53 extern int nt_ClearEOL( void) ;
54 extern void NT_ClearEOD( void) ;
55 extern void NT_ClearScreen(void) ;
56 extern void NT_VisibleBell(void);
57 extern void NT_WrapHorizontal(void);
58
59 static int GetSize(int *lins, int *cols);
60
61 int DisplayWindowHSize;
62         void
63 terminit(void)
64 {
65         return;
66 }
67
68
69
70 int T_ActualWindowSize;
71
72 static  void    ReBufferDisplay (void);
73
74
75 /*ARGSUSED*/
76         void
77 TellTC(void)
78 {
79
80         xprintf(CGETS(7, 1, "\n\tYou're using a Windows console.\n"));
81 }
82
83
84         static void
85 ReBufferDisplay(void)
86 {
87         register int i;
88         Char **b;
89         Char **bufp;
90         int lins,cols;
91
92         nt_getsize(&lins,&cols,&DisplayWindowHSize);
93
94         b = Display;
95         Display = NULL;
96         if (b != NULL) {
97                 for (bufp = b; *bufp != NULL; bufp++)
98                         xfree((ptr_t) * bufp);
99                 xfree((ptr_t) b);
100         }
101         b = Vdisplay;
102         Vdisplay = NULL;
103         if (b != NULL) {
104                 for (bufp = b; *bufp != NULL; bufp++)
105                         xfree((ptr_t) * bufp);
106                 xfree((ptr_t) b);
107         }
108         TermH = cols;
109
110         TermV = (INBUFSIZE * 4) / TermH + 1;/*FIXBUF*/
111         b = (Char **) xmalloc((size_t) (sizeof(*b) * (TermV + 1)));
112         for (i = 0; i < TermV; i++)
113                 b[i] = (Char *) xmalloc((size_t) (sizeof(*b[i]) * (TermH + 1)));
114         b[TermV] = NULL;
115         Display = b;
116         b = (Char **) xmalloc((size_t) (sizeof(*b) * (TermV + 1)));
117         for (i = 0; i < TermV; i++)
118                 b[i] = (Char *) xmalloc((size_t) (sizeof(*b[i]) * (TermH + 1)));
119         b[TermV] = NULL;
120         Vdisplay = b;
121 }
122
123         void
124 SetTC(char *what, char *how)
125 {
126         int li,win,co;
127
128         nt_getsize(&li,&co,&win);
129         if (!lstrcmp(what,"li")) {
130                 li = atoi(how);
131
132         }else if(!lstrcmp(what,"co")) { //set window, not buffer size
133                 win = atoi(how);
134         }
135         else
136                 stderror(ERR_SYSTEM, "SetTC","Sorry, this function is not supported");
137
138         ChangeSize(li,win);
139         return;
140 }
141
142
143 /*
144  * Print the termcap string out with variable substitution
145  */
146         void
147 EchoTC(Char **v)
148 {
149         Char **globbed;
150         char    cv[BUFSIZE];/*FIXBUF*/
151         int     verbose = 0, silent = 0;
152         static char *fmts = "%s\n", *fmtd = "%d\n";
153         int li,co;
154
155
156         setname("echotc");
157
158         v = glob_all_or_error(v);
159         globbed = v;
160         cleanup_push(globbed, blk_cleanup);
161
162         if (!v || !*v || *v[0] == '\0')
163                 goto end;
164         if (v[0][0] == '-') {
165                 switch (v[0][1]) {
166                         case 'v':
167                                 verbose = 1;
168                                 break;
169                         case 's':
170                                 silent = 1;
171                                 break;
172                         default:
173                                 stderror(ERR_NAME | ERR_TCUSAGE);
174                                 break;
175                 }
176                 v++;
177         }
178         if (!*v || *v[0] == '\0')
179                 goto end;
180         (void) StringCbCopy(cv,sizeof(cv), short2str(*v));
181
182         GetSize(&li,&co);
183
184         if(!lstrcmp(cv,"rows") || !lstrcmp(cv,"lines") ) {
185                 xprintf(fmtd,T_Lines);
186                 goto end;
187         }
188         else if(!lstrcmp(cv,"cols") ) {
189                 xprintf(fmtd,T_ActualWindowSize);
190                 goto end;
191         }
192         else if(!lstrcmp(cv,"buffer") ) {
193                 xprintf(fmtd,T_Cols);
194                 goto end;
195         }
196         else
197                 stderror(ERR_SYSTEM, "EchoTC","Sorry, this function is not supported");
198
199 end:
200         cleanup_until(globbed);
201 }
202
203 int    GotTermCaps = 0;
204
205
206         void
207 ResetArrowKeys(void)
208 {
209 }
210
211         void
212 DefaultArrowKeys(void)
213 {
214 }
215
216
217         int
218 SetArrowKeys(const CStr *name, XmapVal *fun, int type)
219 {
220         UNREFERENCED_PARAMETER(name);
221         UNREFERENCED_PARAMETER(fun);
222         UNREFERENCED_PARAMETER(type);
223         return -1;
224 }
225
226         int
227 IsArrowKey(Char *name)
228 {
229         UNREFERENCED_PARAMETER(name);
230         return 0;
231 }
232
233         int
234 ClearArrowKeys(const CStr *name)
235 {
236         UNREFERENCED_PARAMETER(name);
237         return -1;
238 }
239
240         void
241 PrintArrowKeys(const CStr *name)
242 {
243         UNREFERENCED_PARAMETER(name);
244         return;
245 }
246
247
248         void
249 BindArrowKeys(void)
250 {
251         return;
252 }
253
254 #define GoodStr(ignore)  1
255         void
256 SetAttributes(Char atr)
257 {
258         atr &= ATTRIBUTES;
259 }
260
261 /* PWP 6-27-88 -- if the tty driver thinks that we can tab, we ask termcap */
262         int
263 CanWeTab(void)
264 {
265         return 1;
266 }
267
268 /* move to line <where> (first line == 0) as efficiently as possible; */
269         void
270 MoveToLine(int where)
271 {
272         int     del;
273
274         if (where == CursorV)
275                 return;
276
277         if (where > TermV) {
278 #ifdef DEBUG_SCREEN
279                 xprintf("MoveToLine: where is ridiculous: %d\r\n", where);
280                 flush();
281 #endif /* DEBUG_SCREEN */
282                 return;
283         }
284
285         del = where - CursorV;
286
287         NT_MoveToLineOrChar(del, 1);
288
289         CursorV = where;                /* now where is here */
290 }
291
292 /* move to character position (where) as efficiently as possible */
293         void
294 MoveToChar(int where)           
295 {
296         if (where == CursorH)
297                 return;
298
299         if (where >= TermH) {
300 #ifdef DEBUG_SCREEN
301                 xprintf("MoveToChar: where is riduculous: %d\r\n", where);
302                 flush();
303 #endif /* DEBUG_SCREEN */
304                 return;
305         }
306
307         if (!where) {           /* if where is first column */
308                 //(void) putraw('\r');  /* do a CR */
309                 NT_MoveToLineOrChar(where, 0);
310                 flush();
311                 CursorH = 0;
312                 return;
313         }
314
315         NT_MoveToLineOrChar(where, 0);
316         CursorH = where;                /* now where is here */
317 }
318
319         void
320 so_write(register Char *cp, register int n)
321 {
322         if (n <= 0)
323                 return;                 /* catch bugs */
324
325         if (n > TermH) {
326                 return;
327         }
328
329         do {
330                 if (*cp & LITERAL) {
331                         Char   *d;
332
333                         for (d = litptr + (*cp++ & ~LITERAL) * LIT_FACTOR; *d;
334                                         d++)
335                                 (void) putraw(*d);
336                 }
337                 else
338                         (void) putraw(*cp++);
339                 CursorH++;
340         } while (--n);
341
342         if (CursorH >= TermH) { /* wrap? */
343                 CursorH = 0;
344                 CursorV++;
345                 NT_WrapHorizontal();
346
347         }
348         else if(CursorH >= DisplayWindowHSize) {
349                 flush();
350                 NT_MoveToLineOrChar(CursorH,0);
351         }
352 }
353
354
355         void
356 DeleteChars(int num)            /* deletes <num> characters */
357 {
358         if (num <= 0)
359                 return;
360
361         if (!T_CanDel) {
362 #ifdef DEBUG_EDIT
363                 xprintf(CGETS(7, 16, "ERROR: cannot delete\r\n"));
364 #endif /* DEBUG_EDIT */
365                 flush();
366                 return;
367         }
368
369         if (num > TermH) {
370 #ifdef DEBUG_SCREEN
371                 xprintf(CGETS(7, 17, "DeletChars: num is riduculous: %d\r\n"), num);
372                 flush();
373 #endif /* DEBUG_SCREEN */
374                 return;
375         }
376
377 }
378
379 /* Puts terminal in insert character mode, or inserts num characters in the
380    line */
381         void
382 Insert_write(register Char *cp, register int num)
383 {
384         UNREFERENCED_PARAMETER(cp);
385
386         if (num <= 0)
387                 return;
388         if (!T_CanIns) {
389 #ifdef DEBUG_EDIT
390                 xprintf(CGETS(7, 18, "ERROR: cannot insert\r\n"));
391 #endif /* DEBUG_EDIT */
392                 flush();
393                 return;
394         }
395
396         if (num > TermH) {
397 #ifdef DEBUG_SCREEN
398                 xprintf(CGETS(7, 19, "StartInsert: num is riduculous: %d\r\n"), num);
399                 flush();
400 #endif /* DEBUG_SCREEN */
401                 return;
402         }
403
404
405 }
406
407 /* clear to end of line.  There are num characters to clear */
408         void
409 ClearEOL(int num)
410 {
411
412         if (num <= 0)
413                 return;
414
415         nt_ClearEOL();
416
417 }
418
419         void
420 ClearScreen(void)
421 {                               /* clear the whole screen and home */
422
423         NT_ClearScreen();
424
425 }
426
427         void
428 SoundBeep(void)
429 {                               /* produce a sound */
430         beep_cmd ();
431         if (adrof(STRnobeep))
432                 return;
433
434         if (adrof(STRvisiblebell))
435                 NT_VisibleBell();       /* visible bell */
436         else
437                 MessageBeep(MB_ICONQUESTION);
438 }
439
440         void
441 ClearToBottom(void)
442 {                               /* clear to the bottom of the screen */
443         NT_ClearEOD();
444
445 }
446
447         void
448 GetTermCaps(void)
449 {
450         int lins,cols;
451
452         nt_getsize(&lins,&cols,&DisplayWindowHSize);
453
454         GotTermCaps = 1;
455
456         T_Cols = cols;
457         T_Lines = lins;
458         T_ActualWindowSize = DisplayWindowHSize;
459         T_Margin = MARGIN_AUTO;
460         T_CanCEOL  = 1;
461         T_CanDel = 0;
462         T_CanIns = 0;
463         T_CanUP = 1;
464
465         ReBufferDisplay();
466         ClearDisp();
467
468         return;
469 }
470 /* GetSize():
471  *      Return the new window size in lines and cols, and
472  *      true if the size was changed.
473  */
474         int
475 GetSize(int *lins, int *cols)
476 {
477
478         int ret = 0;
479
480         *lins = T_Lines;
481
482         *cols = T_Cols;
483
484         nt_getsize(lins,cols,&DisplayWindowHSize);
485
486         // compare the actual visible window size,but return the console buffer size
487         // this is seriously demented.
488         ret =   (T_Lines != *lins || T_ActualWindowSize != DisplayWindowHSize);
489
490         T_Lines = *lins;
491         T_Cols = *cols;
492         T_ActualWindowSize = DisplayWindowHSize;
493
494         return ret;
495 }
496         void
497 ChangeSize(int lins, int cols)
498 {
499
500         int rc = 0;
501         // here we're setting the window size, not the buffer size.
502         // 
503         nt_set_size(lins,cols);
504
505         rc = GetSize(&lins,&cols);
506
507
508         ReBufferDisplay();              /* re-make display buffers */
509         ClearDisp();
510 }
511         void
512 PutPlusOne(Char c, int width)
513 {
514         extern int OldvcV;
515
516         while (width > 1 && CursorH + width > DisplayWindowHSize)
517                 PutPlusOne(' ', 1);
518         if ((c & LITERAL) != 0) { 
519                 Char *d;
520                 for (d = litptr + (c & ~LITERAL) * LIT_FACTOR; *d; d++)
521                         (void) putwraw(*d);
522         } else {
523                 (void) putwraw(c);
524         }
525
526         Display[CursorV][CursorH++] = (Char) c;
527         while (--width > 0)
528                 Display[CursorV][CursorH++] = CHAR_DBWIDTH;
529
530         if (CursorH >= TermH) { /* if we must overflow */
531                 CursorH = 0;
532                 CursorV++;
533                 OldvcV++;
534                 NT_WrapHorizontal();
535         }
536         else if(CursorH >= DisplayWindowHSize) {
537                 NT_MoveToLineOrChar(CursorH,0);
538         }
539 }