Usermode/GUITerminal - Text colouring and cursor
[tpg/acess2.git] / Usermode / Applications / gui_shell_src / vt100.c
1 /*
2  * Acess GUI Terminal
3  * - By John Hodge (thePowersGang)
4  *
5  * vt100.c
6  * - VT100/xterm Emulation
7  */
8 #include <string.h>
9 #include <limits.h>
10 #include "include/vt100.h"
11 #include "include/display.h"
12 #include <ctype.h>      // isalpha
13 #include <acess/sys.h>  // _SysDebug
14
15 const uint32_t  caVT100Colours[] = {
16         // Black, Red, Green, Yellow, Blue, Purple, Cyan, Gray
17         // Same again, but bright
18         0x000000, 0x770000, 0x007700, 0x777700, 0x000077, 0x770077, 0x007777, 0xAAAAAAA,
19         0xCCCCCC, 0xFF0000, 0x00FF00, 0xFFFF00, 0x0000FF, 0xFF00FF, 0x00FFFF, 0xFFFFFFF
20 };
21
22  int    Term_HandleVT100_Long(int Len, const char *Buf);
23
24 static inline int min(int a, int b)
25 {
26         return a < b ? a : b;
27 }
28
29 int Term_HandleVT100(int Len, const char *Buf)
30 {
31         #define MAX_VT100_ESCAPE_LEN    16
32         static char     inc_buf[MAX_VT100_ESCAPE_LEN];
33         static int      inc_len = 0;
34
35         if( inc_len > 0 || *Buf == '\x1b' )
36         {
37                  int    new_bytes = min(MAX_VT100_ESCAPE_LEN - inc_len, Len);
38                  int    ret = 0;
39                 memcpy(inc_buf + inc_len, Buf, new_bytes);
40                 inc_len += new_bytes;
41                 // Handle VT100 (like) escape sequence
42
43                 _SysDebug("inc_len = %i, new_bytes = %i", inc_len, new_bytes);
44
45                 if( inc_len <= 1 )
46                         return 1;       // Skip 1 character (the '\x1b')
47
48                 switch(inc_buf[1])
49                 {
50                 case '[':       // Multibyte, funtime starts    
51                         ret = Term_HandleVT100_Long(inc_len-2, inc_buf+2);
52                         if( ret > 0 )
53                                 ret += 2;
54                         break;
55                 default:
56                         ret = 2;
57                         break;
58                 }       
59
60                 if( ret != 0 )
61                         inc_len = 0;
62                 return ret;
63         }
64
65         switch( *Buf )
66         {
67         case '\b':
68                 // TODO: Backspace
69                 Display_MoveCursor(-1, 0);
70                 return 1;
71         case '\t':
72                 // TODO: tab (get current cursor pos, space until multiple of 8)
73                 return 1;
74         case '\n':
75                 Display_Newline(1);
76                 return 1;
77         case '\r':
78                 // TODO: Carriage return
79                 Display_MoveCursor(INT_MIN, 0);
80                 return 1;
81         }
82
83          int    ret = 0;
84         while( ret < Len )
85         {
86                 if( *Buf == '\n' )
87                         break;
88                 if( *Buf == '\x1b' )
89                         break;
90                 ret ++;
91                 Buf ++;
92         }
93         return -ret;
94 }
95
96 int Term_HandleVT100_Long(int Len, const char *Buffer)
97 {
98         char    c;
99          int    argc = 0, j = 0;
100          int    args[6] = {0,0,0,0,0,0};
101          int    bQuestionMark = 0;
102         
103         // Get Arguments
104         if(j == Len)    return 0;
105         c = Buffer[j++];
106         if(c == '?') {
107                 bQuestionMark = 1;
108                 if(j == Len)    return 0;
109                 c = Buffer[j++];
110         }
111         if( '0' <= c && c <= '9' )
112         {
113                 do {
114                         if(c == ';') {
115                                 if(j == Len)    return 0;
116                                 c = Buffer[j++];
117                         }
118                         while('0' <= c && c <= '9') {
119                                 args[argc] *= 10;
120                                 args[argc] += c-'0';
121                                 if(j == Len)    return 0;
122                                 c = Buffer[j++];
123                         }
124                         argc ++;
125                 } while(c == ';');
126         }
127         
128         // Get Command
129         if( !isalpha(c) ) {
130                 // Bother.
131                 _SysDebug("Unexpected char 0x%x in VT100 escape code", c);
132                 return -1;
133         }
134
135         if( bQuestionMark )
136         {
137                 // Special commands
138                 switch( c )
139                 {
140                 default:
141                         _SysDebug("Unknown VT100 extended escape char 0x%x", c);
142                         break;
143                 }
144         }
145         else
146         {
147                 // Standard commands
148                 switch( c )
149                 {
150                 case 'J':
151                         if( argc == 0 )
152                                 Display_ClearLine(0);
153                         else if( args[0] == 2 )
154                                 Display_ClearLines(0);  // Entire screen!
155                         else
156                                 _SysDebug("TODO: VT100 %i J", args[0]);
157                         break;
158                 case 'm':
159                         if( argc == 0 )
160                         {
161                                 // Reset
162                         }
163                         else
164                         {
165                                 int i;
166                                 for( i = 0; i < argc; i ++ )
167                                 {
168                                         if( args[i] < 8 )
169                                         {
170                                                 // Flags?
171                                         }
172                                         else if( 30 <= args[i] && args[i] <= 37 )
173                                         {
174                                                 // TODO: Bold/bright
175                                                 Display_SetForeground( caVT100Colours[ args[i]-30 ] );
176                                         } 
177                                         else if( 40 <= args[i] && args[i] <= 47 )
178                                         {
179                                                 // TODO: Bold/bright
180                                                 Display_SetBackground( caVT100Colours[ args[i]-30 ] );
181                                         } 
182                                 }
183                         }
184                         break;
185                 default:
186                         _SysDebug("Unknown VT100 escape char 0x%x", c);
187                         break;
188                 }
189         }
190         return j;
191 }

UCC git Repository :: git.ucc.asn.au