Develop and Download Open Source Software

Browse Subversion Repository

Annotation of /trunk/teraterm/teraterm/charset.cpp

Parent Directory Parent Directory | Revision Log Revision Log


Revision 10756 - (hide annotations) (download) (as text)
Mon Jun 12 15:20:01 2023 UTC (9 months, 4 weeks ago) by zmatsuo
Original Path: trunk/teraterm/teraterm/charset.c
File MIME type: text/x-csrc
File size: 17566 byte(s)
IdRussian 時の文字コード変換を charset.c へ移動

- vtterm.c から charset.c へ移動
1 zmatsuo 10755 /*
2     * (C) 2023- TeraTerm Project
3     * All rights reserved.
4     *
5     * Redistribution and use in source and binary forms, with or without
6     * modification, are permitted provided that the following conditions
7     * are met:
8     *
9     * 1. Redistributions of source code must retain the above copyright
10     * notice, this list of conditions and the following disclaimer.
11     * 2. Redistributions in binary form must reproduce the above copyright
12     * notice, this list of conditions and the following disclaimer in the
13     * documentation and/or other materials provided with the distribution.
14     * 3. The name of the author may not be used to endorse or promote products
15     * derived from this software without specific prior written permission.
16     *
17     * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
18     * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19     * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20     * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT,
21     * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22     * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23     * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24     * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25     * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26     * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27     */
28    
29     #include "teraterm.h"
30     #include "tttypes.h"
31     #include <stdio.h>
32     #include <string.h>
33     #if !defined(_CRTDBG_MAP_ALLOC)
34     #define _CRTDBG_MAP_ALLOC
35     #endif
36     #include <stdlib.h>
37     #include <crtdbg.h>
38     #include <assert.h>
39    
40     #include "buffer.h" // for Wrap
41     #include "ttwinman.h"
42     #include "codeconv.h"
43     #include "unicode.h"
44     #include "language.h" // for JIS2SJIS()
45    
46     #include "charset.h"
47    
48     static BOOL KanjiIn; // TRUE = MBCS��1byte�������M��������
49     static BOOL EUCkanaIn, EUCsupIn;
50     static int EUCcount;
51     #if 0
52     static BOOL Special;
53     #endif
54    
55     /* GL for single shift 2/3 */
56     static int GLtmp;
57     /* single shift 2/3 flag */
58     static BOOL SSflag;
59     /* JIS -> SJIS conversion flag */
60     static BOOL ConvJIS;
61     static WORD Kanji;
62     BOOL Fallbacked;
63    
64     typedef struct {
65     /* GL, GR code group */
66     int Glr[2];
67     /* G0, G1, G2, G3 code group */
68     int Gn[4];
69     } VttermKanjiWork;
70    
71     static VttermKanjiWork KanjiWork;
72    
73    
74     /**
75     * ISO2022�p���[�N������������
76     */
77     static void CharSetInit2(VttermKanjiWork *w)
78     {
79     if (ts.Language==IdJapanese) {
80     w->Gn[0] = IdASCII;
81     w->Gn[1] = IdKatakana;
82     w->Gn[2] = IdKatakana;
83     w->Gn[3] = IdKanji;
84     w->Glr[0] = 0;
85     if ((ts.KanjiCode==IdJIS) && (ts.JIS7Katakana==0))
86     w->Glr[1] = 2; // 8-bit katakana
87     else
88     w->Glr[1] = 3;
89     }
90     else {
91     w->Gn[0] = IdASCII;
92     w->Gn[1] = IdSpecial;
93     w->Gn[2] = IdASCII;
94     w->Gn[3] = IdASCII;
95     w->Glr[0] = 0;
96     w->Glr[1] = 0;
97     }
98     }
99    
100     /**
101     * �������A���[�N������������
102     */
103     void CharSetInit(void)
104     {
105     CharSetInit2(&KanjiWork);
106     SSflag = FALSE;
107    
108     KanjiIn = FALSE;
109     EUCkanaIn = FALSE;
110     EUCsupIn = FALSE;
111     ConvJIS = FALSE;
112     Fallbacked = FALSE;
113     }
114    
115     /**
116     * 1byte���`�F�b�N
117     */
118     static BOOL CheckFirstByte(BYTE b, int lang, int kanji_code)
119     {
120     switch (lang) {
121     case IdKorean:
122     return __ismbblead(b, 51949);
123     case IdChinese:
124     if (kanji_code == IdCnGB2312) {
125     return __ismbblead(b, 936);
126     }
127     else if (ts.KanjiCode == IdCnBig5) {
128     return __ismbblead(b, 950);
129     }
130     break;
131     default:
132     assert(FALSE);
133     break;
134     }
135     assert(FALSE);
136     return FALSE;
137     }
138     /**
139     * ts.Language == IdJapanese ��
140     * 1byte���`�F�b�N
141     */
142     static BOOL CheckKanji(BYTE b)
143     {
144     VttermKanjiWork *w = &KanjiWork;
145     BOOL Check;
146    
147     if (ts.Language!=IdJapanese)
148     return FALSE;
149    
150     ConvJIS = FALSE;
151    
152     if (ts.KanjiCode==IdSJIS ||
153     (ts.FallbackToCP932 && ts.KanjiCode==IdUTF8)) {
154     if ((0x80<b) && (b<0xa0) || (0xdf<b) && (b<0xfd)) {
155     Fallbacked = TRUE;
156     return TRUE; // SJIS kanji
157     }
158     if ((0xa1<=b) && (b<=0xdf)) {
159     return FALSE; // SJIS katakana
160     }
161     }
162    
163     if ((b>=0x21) && (b<=0x7e)) {
164     Check = (w->Gn[w->Glr[0]] == IdKanji);
165     ConvJIS = Check;
166     }
167     else if ((b>=0xA1) && (b<=0xFE)) {
168     Check = (w->Gn[w->Glr[1]] == IdKanji);
169     if (ts.KanjiCode==IdEUC) {
170     Check = TRUE;
171     }
172     else if (ts.KanjiCode==IdJIS && ((ts.TermFlag & TF_FIXEDJIS)!=0) && (ts.JIS7Katakana==0)) {
173     Check = FALSE; // 8-bit katakana
174     }
175     ConvJIS = Check;
176     }
177     else {
178     Check = FALSE;
179     }
180    
181     return Check;
182     }
183    
184     static void PutKanji(BYTE b)
185     {
186     unsigned long u32 = 0;
187    
188     Kanji = Kanji + b;
189    
190     // codepage����
191     // https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-ucoderef/28fefe92-d66c-4b03-90a9-97b473223d43
192     switch (ts.Language) {
193     case IdJapanese:
194     if (ConvJIS) {
195     // JIS -> Shift_JIS(CP932)
196     Kanji = JIS2SJIS((WORD)(Kanji & 0x7f7f));
197     }
198     u32 = CP932ToUTF32(Kanji);
199     break;
200     case IdKorean:
201     if (ts.KanjiCode == IdKoreanCP51949) {
202     // CP51949
203     u32 = MBCP_UTF32(Kanji, 51949);
204     }
205     else {
206     assert(FALSE);
207     }
208     break;
209     case IdChinese:
210     if (ts.KanjiCode == IdCnGB2312) {
211     // CP936 GB2312
212     u32 = MBCP_UTF32(Kanji, 936);
213     }
214     else if (ts.KanjiCode == IdCnBig5) {
215     // CP950 Big5
216     u32 = MBCP_UTF32(Kanji, 950);
217     }
218     else {
219     assert(FALSE);
220     }
221     break;
222     default:
223     assert(FALSE);
224     break;
225     }
226    
227     PutU32(u32);
228     }
229    
230     static BOOL ParseFirstJP(BYTE b)
231     // returns TRUE if b is processed
232     // (actually allways returns TRUE)
233     {
234     VttermKanjiWork *w = &KanjiWork;
235     if (KanjiIn) {
236     if ((! ConvJIS) && (0x3F<b) && (b<0xFD) ||
237     ConvJIS && ( (0x20<b) && (b<0x7f) ||
238     (0xa0<b) && (b<0xff) ))
239     {
240     PutKanji(b);
241     KanjiIn = FALSE;
242     return TRUE;
243     }
244     else if ((ts.TermFlag & TF_CTRLINKANJI)==0) {
245     KanjiIn = FALSE;
246     }
247     else if ((b==CR) && Wrap) {
248     CarriageReturn(FALSE);
249     LineFeed(LF,FALSE);
250     Wrap = FALSE;
251     }
252     }
253    
254     if (SSflag) {
255     if (w->Gn[GLtmp] == IdKanji) {
256     Kanji = b << 8;
257     KanjiIn = TRUE;
258     SSflag = FALSE;
259     return TRUE;
260     }
261     else if (w->Gn[GLtmp] == IdKatakana) {
262     b = b | 0x80;
263     }
264    
265     PutChar(b);
266     SSflag = FALSE;
267     return TRUE;
268     }
269    
270     if ((!EUCsupIn) && (!EUCkanaIn) && (!KanjiIn) && CheckKanji(b)) {
271     Kanji = b << 8;
272     KanjiIn = TRUE;
273     return TRUE;
274     }
275    
276     if (b<=US) {
277     ParseControl(b);
278     }
279     else if (b==0x20) {
280     PutChar(b);
281     }
282     else if ((b>=0x21) && (b<=0x7E)) {
283     if (EUCsupIn) {
284     EUCcount--;
285     EUCsupIn = (EUCcount==0);
286     return TRUE;
287     }
288    
289     if ((w->Gn[w->Glr[0]] == IdKatakana) || EUCkanaIn) {
290     b = b | 0x80;
291     EUCkanaIn = FALSE;
292     {
293     // b��sjis�����p�J�^�J�i
294     unsigned long u32 = CP932ToUTF32(b);
295     PutU32(u32);
296     }
297     return TRUE;
298     }
299     PutChar(b);
300     }
301     else if (b==0x7f) {
302     return TRUE;
303     }
304     else if ((b>=0x80) && (b<=0x8D)) {
305     ParseControl(b);
306     }
307     else if (b==0x8E) { // SS2
308     switch (ts.KanjiCode) {
309     case IdEUC:
310     if (ts.ISO2022Flag & ISO2022_SS2) {
311     EUCkanaIn = TRUE;
312     }
313     break;
314     case IdUTF8:
315     PutChar('?');
316     break;
317     default:
318     ParseControl(b);
319     }
320     }
321     else if (b==0x8F) { // SS3
322     switch (ts.KanjiCode) {
323     case IdEUC:
324     if (ts.ISO2022Flag & ISO2022_SS3) {
325     EUCcount = 2;
326     EUCsupIn = TRUE;
327     }
328     break;
329     case IdUTF8:
330     PutChar('?');
331     break;
332     default:
333     ParseControl(b);
334     }
335     }
336     else if ((b>=0x90) && (b<=0x9F)) {
337     ParseControl(b);
338     }
339     else if (b==0xA0) {
340     PutChar(0x20);
341     }
342     else if ((b>=0xA1) && (b<=0xFE)) {
343     if (EUCsupIn) {
344     EUCcount--;
345     EUCsupIn = (EUCcount==0);
346     return TRUE;
347     }
348    
349     if ((w->Gn[w->Glr[1]] != IdASCII) ||
350     (ts.KanjiCode==IdEUC) && EUCkanaIn ||
351     (ts.KanjiCode==IdSJIS) ||
352     (ts.KanjiCode==IdJIS) &&
353     (ts.JIS7Katakana==0) &&
354     ((ts.TermFlag & TF_FIXEDJIS)!=0)) {
355     // b��sjis�����p�J�^�J�i
356     unsigned long u32 = CP932ToUTF32(b);
357     PutU32(u32);
358     } else {
359     if (w->Gn[w->Glr[1]] == IdASCII) {
360     b = b & 0x7f;
361     }
362     PutChar(b);
363     }
364     EUCkanaIn = FALSE;
365     }
366     else {
367     PutChar(b);
368     }
369    
370     return TRUE;
371     }
372    
373     static BOOL ParseFirstKR(BYTE b)
374     // returns TRUE if b is processed
375     // (actually allways returns TRUE)
376     {
377     VttermKanjiWork *w = &KanjiWork;
378     if (KanjiIn) {
379     if ((0x41<=b) && (b<=0x5A) ||
380     (0x61<=b) && (b<=0x7A) ||
381     (0x81<=b) && (b<=0xFE))
382     {
383     PutKanji(b);
384     KanjiIn = FALSE;
385     return TRUE;
386     }
387     else if ((ts.TermFlag & TF_CTRLINKANJI)==0) {
388     KanjiIn = FALSE;
389     }
390     else if ((b==CR) && Wrap) {
391     CarriageReturn(FALSE);
392     LineFeed(LF,FALSE);
393     Wrap = FALSE;
394     }
395     }
396    
397     if ((!KanjiIn) && CheckFirstByte(b, ts.Language, ts.KanjiCode)) {
398     Kanji = b << 8;
399     KanjiIn = TRUE;
400     return TRUE;
401     }
402    
403     if (b<=US) {
404     ParseControl(b);
405     }
406     else if (b==0x20) {
407     PutChar(b);
408     }
409     else if ((b>=0x21) && (b<=0x7E)) {
410     // if (Gn[Glr[0]] == IdKatakana) {
411     // b = b | 0x80;
412     // }
413     PutChar(b);
414     }
415     else if (b==0x7f) {
416     return TRUE;
417     }
418     else if ((0x80<=b) && (b<=0x9F)) {
419     ParseControl(b);
420     }
421     else if (b==0xA0) {
422     PutChar(0x20);
423     }
424     else if ((b>=0xA1) && (b<=0xFE)) {
425     if (w->Gn[w->Glr[1]] == IdASCII) {
426     b = b & 0x7f;
427     }
428     PutChar(b);
429     }
430     else {
431     PutChar(b);
432     }
433    
434     return TRUE;
435     }
436    
437     static BOOL ParseFirstCn(BYTE b)
438     // returns TRUE if b is processed
439     // (actually allways returns TRUE)
440     {
441     VttermKanjiWork *w = &KanjiWork;
442     if (KanjiIn) {
443     // TODO
444     if ((0x40<=b) && (b<=0x7e) ||
445     (0xa1<=b) && (b<=0xFE))
446     {
447     PutKanji(b);
448     KanjiIn = FALSE;
449     return TRUE;
450     }
451     else if ((ts.TermFlag & TF_CTRLINKANJI)==0) {
452     KanjiIn = FALSE;
453     }
454     else if ((b==CR) && Wrap) {
455     CarriageReturn(FALSE);
456     LineFeed(LF,FALSE);
457     Wrap = FALSE;
458     }
459     }
460    
461     if ((!KanjiIn) && CheckFirstByte(b, ts.Language, ts.KanjiCode)) {
462     Kanji = b << 8;
463     KanjiIn = TRUE;
464     return TRUE;
465     }
466    
467     if (b<=US) {
468     ParseControl(b);
469     }
470     else if (b==0x20) {
471     PutChar(b);
472     }
473     else if ((b>=0x21) && (b<=0x7E)) {
474     // if (Gn[Glr[0]] == IdKatakana) {
475     // b = b | 0x80;
476     // }
477     PutChar(b);
478     }
479     else if (b==0x7f) {
480     return TRUE;
481     }
482     else if ((0x80<=b) && (b<=0x9F)) {
483     ParseControl(b);
484     }
485     else if (b==0xA0) {
486     PutChar(0x20);
487     }
488     else if ((b>=0xA1) && (b<=0xFE)) {
489     if (w->Gn[w->Glr[1]] == IdASCII) {
490     b = b & 0x7f;
491     }
492     PutChar(b);
493     }
494     else {
495     PutChar(b);
496     }
497    
498     return TRUE;
499     }
500    
501     static void ParseASCII(BYTE b)
502     {
503     if (SSflag) {
504     PutChar(b);
505     SSflag = FALSE;
506     return;
507     }
508    
509     if (b<=US) {
510     ParseControl(b);
511     } else if ((b>=0x20) && (b<=0x7E)) {
512     //Kanji = 0;
513     //PutKanji(b);
514     PutChar(b);
515     } else if ((b==0x8E) || (b==0x8F)) {
516     PutChar('?');
517     } else if ((b>=0x80) && (b<=0x9F)) {
518     ParseControl(b);
519     } else if (b>=0xA0) {
520     //Kanji = 0;
521     //PutKanji(b);
522     PutChar(b);
523     }
524     }
525    
526     // UTF-8�����M�f�[�^����������
527     // returns TRUE if b is processed
528     // (actually allways returns TRUE)
529     static BOOL ParseFirstUTF8(BYTE b)
530     {
531     static BYTE buf[4];
532     static int count = 0;
533    
534     unsigned int code;
535     int i;
536    
537     if (ts.FallbackToCP932 && Fallbacked) {
538     return ParseFirstJP(b);
539     }
540    
541     // UTF-8�G���R�[�h
542     // Unicode 1byte, 2byte, 3byte, 4byte
543     // U+0000 ... U+007f 0x00 .. 0x7f
544     // U+0080 ... U+07ff 0xc2 .. 0xdf, 0x80 .. 0xbf
545     // U+0800 ... U+ffff 0xe0 .. 0xef, 0x80 .. 0xbf, 0x80 .. 0xbf
546     // U+10000 ... U+10ffff 0xf0 .. 0xf4, 0x80 .. 0xbf, 0x80 .. 0xbf, 0x80 .. 0xbf
547     // UTF-8���f�R�[�h������������
548     // - 1byte��
549     // - C1(0x80 - 0x9f)
550     // - 0xa0 - 0xc1
551     // - 0xf5 - 0xff
552     // - 2byte�����~
553     // - 0x00 - 0x7f
554     // - 0xc0 - 0xff
555    
556     // 1byte(7bit)
557     if (count == 0) {
558     if ((b & 0x80) == 0x00) {
559     // 1byte(7bit)
560     // 0x7f����, �������A���������o��
561     ParseASCII(b);
562     return TRUE;
563     }
564     if ((b & 0x40) == 0x00 || b >= 0xf6 ) {
565     // UTF-8��1byte���o���������R�[�h�������A���������o��
566     // 0x40 = 0b1011_1111, 0b10xx_xxxx������bit�p�^�[��������������
567     // 0xf6 ���������� U+10FFFF��������������
568     PutU32(b);
569     return TRUE;
570     }
571     // 1byte������
572     buf[count++] = b;
573     return TRUE;
574     }
575    
576     // 2byte(11bit)
577     if ((buf[0] & 0xe0) == 0xc0) {
578     code = 0;
579     if((b & 0xc0) == 0x80) {
580     // 5bit + 6bit
581     code = ((buf[0] & 0x1f) << 6) | (b & 0x3f);
582     if (code < 0x80) {
583     // 11bit�g����7bit���������AUTF-8���������\��
584     code = 0;
585     }
586     }
587     if (code == 0){
588     // ���������o��
589     PutU32(buf[0]);
590     PutU32(b);
591     count = 0;
592     return TRUE;
593     }
594     else {
595     PutU32(code);
596     count = 0;
597     return TRUE;
598     }
599     }
600    
601     // 2byte�����~����
602     buf[count++] = b;
603    
604     // 3byte(16bit)
605     if ((buf[0] & 0xf0) == 0xe0) {
606     if(count < 3) {
607     return TRUE;
608     }
609     code = 0;
610     if ((buf[1] & 0xc0) == 0x80 && (buf[2] & 0xc0) == 0x80) {
611     // 4bit + 6bit + 6bit
612     code = ((buf[0] & 0xf) << 12);
613     code |= ((buf[1] & 0x3f) << 6);
614     code |= ((buf[2] & 0x3f));
615     if (code < 0x800) {
616     // 16bit�g����11bit�����������AUTF-8���������\��
617     code = 0;
618     }
619     }
620     if (code == 0) {
621     // ���������o��
622     PutU32(buf[0]);
623     PutU32(buf[1]);
624     PutU32(buf[2]);
625     count = 0;
626     return TRUE;
627     } else {
628     PutU32(code);
629     count = 0;
630     return TRUE;
631     }
632     }
633    
634     // 4byte(21bit)
635     if ((buf[0] & 0xf8) == 0xf0) {
636     if(count < 4) {
637     return TRUE;
638     }
639     code = 0;
640     if ((buf[1] & 0xc0) == 0x80 && (buf[2] & 0xc0) == 0x80 && (buf[3] & 0xc0) == 0x80) {
641     // 3bit + 6bit + 6bit + 6bit
642     code = ((buf[0] & 0x07) << 18);
643     code |= ((buf[1] & 0x3f) << 12);
644     code |= ((buf[2] & 0x3f) << 6);
645     code |= (buf[3] & 0x3f);
646     if (code < 0x10000) {
647     // 21bit�g����16bit�����������AUTF-8���������\��
648     code = 0;
649     }
650     }
651     if (code == 0) {
652     // ���������o��
653     PutU32(buf[0]);
654     PutU32(buf[1]);
655     PutU32(buf[2]);
656     PutU32(buf[3]);
657     count = 0;
658     return TRUE;
659     } else {
660     PutU32(code);
661     count = 0;
662     return TRUE;
663     }
664     }
665    
666     // ��������������
667     assert(FALSE);
668    
669     for (i = 0; i < count; i++) {
670     ParseASCII(buf[i]);
671     }
672     count = 0;
673     return TRUE;
674     }
675    
676     static BOOL ParseFirstRus(BYTE b)
677     // returns if b is processed
678     {
679 zmatsuo 10756 // CP1251������
680     BYTE c = RussConv(ts.KanjiCode, IdWindows, b);
681     // CP1251->Unicode
682     unsigned long u32 = MBCP_UTF32(c, 1251);
683     PutU32(u32);
684     return TRUE;
685 zmatsuo 10755 }
686    
687     static BOOL ParseEnglish(BYTE b)
688     {
689     unsigned short u16 = 0;
690     int part = KanjiCodeToISO8859Part(ts.KanjiCode);
691     int r = UnicodeFromISO8859(part, b, &u16);
692     if (r == 0) {
693     return FALSE;
694     }
695     if (u16 < 0x100) {
696     ParseASCII((BYTE)u16);
697     }
698     else {
699     PutU32(u16);
700     }
701     return TRUE;
702     }
703    
704     void ParseFirst(BYTE b) {
705     switch (ts.Language) {
706     case IdUtf8:
707     ParseFirstUTF8(b);
708     return;
709    
710     case IdJapanese:
711     switch (ts.KanjiCode) {
712     case IdUTF8:
713     if (ParseFirstUTF8(b)) {
714     return;
715     }
716     break;
717     default:
718     if (ParseFirstJP(b)) {
719     return;
720     }
721     }
722     break;
723    
724     case IdKorean:
725     switch (ts.KanjiCode) {
726     case IdUTF8:
727     if (ParseFirstUTF8(b)) {
728     return;
729     }
730     break;
731     default:
732     if (ParseFirstKR(b)) {
733     return;
734     }
735     }
736     break;
737    
738     case IdRussian:
739     if (ParseFirstRus(b)) {
740     return;
741     }
742     break;
743    
744     case IdChinese:
745     switch (ts.KanjiCode) {
746     case IdUTF8:
747     if (ParseFirstUTF8(b)) {
748     return;
749     }
750     break;
751     default:
752     if (ParseFirstCn(b)) {
753     return;
754     }
755     }
756     break;
757     case IdEnglish: {
758     if (ParseEnglish(b)) {
759     return;
760     }
761     break;
762     }
763     }
764    
765     if (SSflag) {
766     PutChar(b);
767     SSflag = FALSE;
768     return;
769     }
770    
771     if (b<=US)
772     ParseControl(b);
773     else if ((b>=0x20) && (b<=0x7E))
774     PutChar(b);
775     else if ((b>=0x80) && (b<=0x9F))
776     ParseControl(b);
777     else if (b>=0xA0)
778     PutChar(b);
779     }
780    
781     /**
782     * �w��(Designate)
783     *
784     * @param Gn 0/1/2/3 = G0/G1/G2/G3
785     * @param codeset IdASCII 0
786     * IdKatakana 1
787     * IdKanji 2
788     * IdSpecial 3
789     */
790     void CharSet2022Designate(int gn, int cs)
791     {
792     VttermKanjiWork *w = &KanjiWork;
793     w->Gn[gn] = cs;
794     }
795    
796     /**
797     * �����o��(Invoke)
798     * @param glr 0/1 = GL/GR (Locking shift�������L��)
799     * @param gn 0/1/2/3 = G0/G1/G2/G3
800     * @param single_shift FALSE Locking shift
801     * TRUE Single shift
802     */
803     void CharSet2022Invoke(int glr, int gn, BOOL single_shift)
804     {
805     VttermKanjiWork *w = &KanjiWork;
806     if (single_shift == FALSE) {
807     // Locking shift
808     w->Glr[glr] = gn;
809     }
810     else {
811     // Single shift
812     GLtmp = gn;
813     SSflag = TRUE;
814     }
815     }
816    
817     /**
818     * DEC�����t�H���g(Tera Special font)
819     * 0140(0x60) ... 0176(0x7f) ���r�����A�T�C������������
820     * <ESC>(0 �������������G�X�P�[�v�V�[�P���X�����`
821     * about/emulations.html
822     *
823     * @param b �R�[�h
824     */
825     BOOL CharSetIsSpecial(BYTE b)
826     {
827     VttermKanjiWork *w = &KanjiWork;
828     BOOL SpecialNew = FALSE;
829    
830     if ((b>0x5F) && (b<0x80)) {
831     if (SSflag)
832     SpecialNew = (w->Gn[GLtmp]==IdSpecial);
833     else
834     SpecialNew = (w->Gn[w->Glr[0]]==IdSpecial);
835     }
836     else if (b>0xDF) {
837     if (SSflag)
838     SpecialNew = (w->Gn[GLtmp]==IdSpecial);
839     else
840     SpecialNew = (w->Gn[w->Glr[1]]==IdSpecial);
841     }
842    
843     return SpecialNew;
844     }
845    
846     static void CharSetSaveStateLow(CharSetState *state, const VttermKanjiWork *w)
847     {
848     int i;
849     state->infos[0] = w->Glr[0];
850     state->infos[1] = w->Glr[1];
851     for (i=0 ; i<=3; i++) {
852     state->infos[2 + i] = w->Gn[i];
853     }
854     }
855    
856     /**
857     * ��������������
858     */
859     void CharSetSaveState(CharSetState *state)
860     {
861     VttermKanjiWork *w = &KanjiWork;
862     CharSetSaveStateLow(state, w);
863     }
864    
865     /**
866     * ���������A����
867     */
868     void CharSetLoadState(const CharSetState *state)
869     {
870     VttermKanjiWork *w = &KanjiWork;
871     int i;
872     w->Glr[0] = state->infos[0];
873     w->Glr[1] = state->infos[1];
874     for (i=0 ; i<=3; i++) {
875     w->Gn[i] = state->infos[2 + i];
876     }
877     }

Back to OSDN">Back to OSDN
ViewVC Help
Powered by ViewVC 1.1.26