1 /***************************************************************************
2 *
3 * $Header: /usr/local/cvsroot/utils/ytree/termcap.c,v 1.9 1997/08/13 12:24:58 werner Rel $
4 *
5 * Termcap Term-I/O
6 *
7 ***************************************************************************/
8
9
10 #include "ytree.h"
11
12
13
14 #ifdef TERMCAP
15
16
17
18 #ifdef __NeXT__
19
20 char tcdummy[256], tcbuf[1024];
21 char *tcdptr = tcdummy;
22
23 #else
24 # define tcbuf NULL
25 # define tcdummy NULL
26 #endif /* __NeXT__ */
27
28
29 #undef wgetch
30 #undef initscr
31 #undef endwin
32
33
34 typedef struct
35 {
36 int key_code;
37 char *termcap_name;
38 char *key_sequence;
39 } SpecialKey;
40
41
42 static SpecialKey special_key[] = {
43 { KEY_BTAB, "kB", NULL },
44 { KEY_DOWN, "kd", NULL },
45 { KEY_UP, "ku", NULL },
46 { KEY_LEFT, "kl", NULL },
47 { KEY_RIGHT, "kr", NULL },
48 { KEY_END, "kH", NULL },
49 { KEY_HOME, "kh", NULL },
50 { KEY_NPAGE, "kN", NULL },
51 { KEY_PPAGE, "kP", NULL },
52 { KEY_DC, "kD", NULL },
53 { KEY_BACKSPACE, "kb", NULL },
54 { KEY_EIC, "kM", NULL },
55 { KEY_IC, "kI", NULL },
56 { KEY_DL, "kL", NULL },
57 { -1, NULL, NULL }
58 };
59
60
61
62 static int TermcapMultiByte( WINDOW *win, int ch );
63 static void SigAlarm( int signo );
64 static jmp_buf env_alarm;
65 static char *reverse;
66 static char *normal;
67
68
69
TermcapVidattr(int attr)70 void TermcapVidattr( int attr )
71 {
72 if( normal && reverse )
73 {
74 if( attr == 0 ) putp( normal );
75 else
76 {
77 if( attr & A_REVERSE ) putp( reverse );
78 }
79 }
80 }
81
82
83
TermcapWgetch(WINDOW * win)84 int TermcapWgetch( WINDOW *win )
85 {
86 int ch;
87 SpecialKey *sk_ptr;
88 BOOL one_matched = FALSE;
89 int i;
90
91 ch = wgetch( stdscr );
92
93 for( i=0, sk_ptr = special_key;
94 sk_ptr->key_code > 0;
95 sk_ptr = &special_key[++i]
96 )
97 {
98 /* Ein-Byte Codes ausblenden */
99 /*---------------------------*/
100
101 if( sk_ptr->key_sequence && *(sk_ptr->key_sequence) == ch )
102 {
103 /* Erstes Zeichen matched */
104 /*------------------------*/
105
106 if( sk_ptr->key_sequence[1] == '\0' )
107 {
108 /* 1 Byte-Code */
109 /*-------------*/
110
111 ch = sk_ptr->key_code;
112 break;
113 }
114 one_matched = TRUE;
115 }
116 }
117
118 if( one_matched )
119 {
120 /* Multi-Byte Code */
121 /*-----------------*/
122
123 ch = TermcapMultiByte( win, ch );
124 }
125 return( ch );
126 }
127
128
129
TermcapMultiByte(WINDOW * win,int ch)130 static int TermcapMultiByte( WINDOW *win, int ch )
131 {
132 SpecialKey *sk_ptr;
133 char buffer[80];
134 BOOL found;
135 int i, j;
136
137 memset( buffer, 0, sizeof( buffer ) );
138 *buffer = ch;
139
140 if( signal( SIGALRM, SigAlarm ) == SIG_ERR )
141 {
142 ERROR_MSG( "signal SIGALRM failed*ABORT" );
143 exit( 1 );
144 }
145
146 if( setjmp( env_alarm ) )
147 {
148 return( ch );
149 }
150
151 alarm( 1 );
152
153 for( j=1, found = FALSE; !found && j < sizeof( buffer ); j++ )
154 {
155 buffer[j] = wgetch( win );
156
157 for( i=0, sk_ptr = special_key;
158 sk_ptr->key_code > 0;
159 sk_ptr = &special_key[++i]
160 )
161 {
162 if( sk_ptr->key_sequence && !strcmp( sk_ptr->key_sequence, buffer ) )
163 {
164 ch = sk_ptr->key_code;
165 found = TRUE;
166 break;
167 }
168 }
169 }
170
171 alarm( 0 );
172
173 return( ch );
174 }
175
176
177
SigAlarm(int signo)178 static void SigAlarm( int signo )
179 {
180 longjmp( env_alarm, 1 );
181 }
182
183
TermcapInitscr()184 void TermcapInitscr()
185 {
186 int i;
187
188 initscr();
189
190 tgetent( tcbuf, getenv( "TERM" ) );
191
192 for( i=0; special_key[i].key_code > 0; i++ )
193 {
194 #ifdef __NeXT__
195 tcdptr = tcdummy;
196 special_key[i].key_sequence = Strdup(tgetstr( special_key[i].termcap_name, &tcdptr ));
197 #else
198 special_key[i].key_sequence = tgetstr( special_key[i].termcap_name, NULL );
199 #endif
200 }
201 #ifdef __NeXT__
202 reverse = Strdup(tgetstr( "so", &tcdptr ));
203 normal = Strdup(tgetstr( "se", &tcdptr ));
204 #else
205 reverse = tgetstr( "so", tcdummy );
206 normal = tgetstr( "se", tcdummy );
207 #endif
208 }
209
210
211
TermcapEndwin()212 void TermcapEndwin()
213 {
214 nl();
215 endwin();
216 putchar( '\n' );
217 }
218
219
220 #endif /* TERMCAP */
221
222
223