github.com/insionng/yougam@v0.0.0-20170714101924-2bc18d833463/libraries/mahonia/tcvn3.go (about)

     1  package mahonia
     2  
     3  // Converters for TCVN3 encoding.
     4  
     5  import (
     6  	"sync"
     7  )
     8  
     9  var (
    10  	onceTCVN3 sync.Once
    11  	dataTCVN3 = struct {
    12  		UnicodeToWord map[rune][2]byte
    13  		WordToUnicode [256]struct {
    14  			r rune
    15  			m *[256]rune
    16  		}
    17  	}{}
    18  )
    19  
    20  func init() {
    21  	p := new(Charset)
    22  	p.Name = "TCVN3"
    23  	p.NewDecoder = func() Decoder {
    24  		onceTCVN3.Do(buildTCVN3Tables)
    25  		return decodeTCVN3
    26  	}
    27  	p.NewEncoder = func() Encoder {
    28  		onceTCVN3.Do(buildTCVN3Tables)
    29  		return encodeTCVN3
    30  	}
    31  	RegisterCharset(p)
    32  }
    33  
    34  func decodeTCVN3(p []byte) (rune, int, Status) {
    35  	if len(p) == 0 {
    36  		return 0, 0, NO_ROOM
    37  	}
    38  	item := &dataTCVN3.WordToUnicode[p[0]]
    39  	if item.m != nil && len(p) > 1 {
    40  		if r := item.m[p[1]]; r != 0 {
    41  			return r, 2, SUCCESS
    42  		}
    43  	}
    44  	if item.r != 0 {
    45  		return item.r, 1, SUCCESS
    46  	}
    47  	if p[0] < 0x80 {
    48  		return rune(p[0]), 1, SUCCESS
    49  	}
    50  	return '?', 1, INVALID_CHAR
    51  }
    52  
    53  func encodeTCVN3(p []byte, c rune) (int, Status) {
    54  	if len(p) == 0 {
    55  		return 0, NO_ROOM
    56  	}
    57  	if c < rune(0x80) {
    58  		p[0] = byte(c)
    59  		return 1, SUCCESS
    60  	}
    61  	if v, ok := dataTCVN3.UnicodeToWord[c]; ok {
    62  		if v[1] != 0 {
    63  			if len(p) < 2 {
    64  				return 0, NO_ROOM
    65  			}
    66  			p[0] = v[0]
    67  			p[1] = v[1]
    68  			return 2, SUCCESS
    69  		} else {
    70  			p[0] = v[0]
    71  			return 1, SUCCESS
    72  		}
    73  	}
    74  	p[0] = '?'
    75  	return 1, INVALID_CHAR
    76  }
    77  
    78  func buildTCVN3Tables() {
    79  	dataTCVN3.UnicodeToWord = map[rune][2]byte{
    80  		// one byte
    81  		0x00C2: {0xA2, 0x00},
    82  		0x00CA: {0xA3, 0x00},
    83  		0x00D4: {0xA4, 0x00},
    84  		0x00E0: {0xB5, 0x00},
    85  		0x00E1: {0xB8, 0x00},
    86  		0x00E2: {0xA9, 0x00},
    87  		0x00E3: {0xB7, 0x00},
    88  		0x00E8: {0xCC, 0x00},
    89  		0x00E9: {0xD0, 0x00},
    90  		0x00EA: {0xAA, 0x00},
    91  		0x00EC: {0xD7, 0x00},
    92  		0x00ED: {0xDD, 0x00},
    93  		0x00F2: {0xDF, 0x00},
    94  		0x00F3: {0xE3, 0x00},
    95  		0x00F4: {0xAB, 0x00},
    96  		0x00F5: {0xE2, 0x00},
    97  		0x00F9: {0xEF, 0x00},
    98  		0x00FA: {0xF3, 0x00},
    99  		0x00FD: {0xFD, 0x00},
   100  		0x0102: {0xA1, 0x00},
   101  		0x0103: {0xA8, 0x00},
   102  		0x0110: {0xA7, 0x00},
   103  		0x0111: {0xAE, 0x00},
   104  		0x0129: {0xDC, 0x00},
   105  		0x0169: {0xF2, 0x00},
   106  		0x01A0: {0xA5, 0x00},
   107  		0x01A1: {0xAC, 0x00},
   108  		0x01AF: {0xA6, 0x00},
   109  		0x01B0: {0xAD, 0x00},
   110  		0x1EA1: {0xB9, 0x00},
   111  		0x1EA3: {0xB6, 0x00},
   112  		0x1EA5: {0xCA, 0x00},
   113  		0x1EA7: {0xC7, 0x00},
   114  		0x1EA9: {0xC8, 0x00},
   115  		0x1EAB: {0xC9, 0x00},
   116  		0x1EAD: {0xCB, 0x00},
   117  		0x1EAF: {0xBE, 0x00},
   118  		0x1EB1: {0xBB, 0x00},
   119  		0x1EB3: {0xBC, 0x00},
   120  		0x1EB5: {0xBD, 0x00},
   121  		0x1EB7: {0xC6, 0x00},
   122  		0x1EB9: {0xD1, 0x00},
   123  		0x1EBB: {0xCE, 0x00},
   124  		0x1EBD: {0xCF, 0x00},
   125  		0x1EBF: {0xD5, 0x00},
   126  		0x1EC1: {0xD2, 0x00},
   127  		0x1EC3: {0xD3, 0x00},
   128  		0x1EC5: {0xD4, 0x00},
   129  		0x1EC7: {0xD6, 0x00},
   130  		0x1EC9: {0xD8, 0x00},
   131  		0x1ECB: {0xDE, 0x00},
   132  		0x1ECD: {0xE4, 0x00},
   133  		0x1ECF: {0xE1, 0x00},
   134  		0x1ED1: {0xE8, 0x00},
   135  		0x1ED3: {0xE5, 0x00},
   136  		0x1ED5: {0xE6, 0x00},
   137  		0x1ED7: {0xE7, 0x00},
   138  		0x1ED9: {0xE9, 0x00},
   139  		0x1EDB: {0xED, 0x00},
   140  		0x1EDD: {0xEA, 0x00},
   141  		0x1EDF: {0xEB, 0x00},
   142  		0x1EE1: {0xEC, 0x00},
   143  		0x1EE3: {0xEE, 0x00},
   144  		0x1EE5: {0xF4, 0x00},
   145  		0x1EE7: {0xF1, 0x00},
   146  		0x1EE9: {0xF8, 0x00},
   147  		0x1EEB: {0xF5, 0x00},
   148  		0x1EED: {0xF6, 0x00},
   149  		0x1EEF: {0xF7, 0x00},
   150  		0x1EF1: {0xF9, 0x00},
   151  		0x1EF3: {0xFA, 0x00},
   152  		0x1EF5: {0xFE, 0x00},
   153  		0x1EF7: {0xFB, 0x00},
   154  		0x1EF9: {0xFC, 0x00},
   155  		// two bytes
   156  		0x00C0: {0x41, 0xB5},
   157  		0x00C1: {0x41, 0xB8},
   158  		0x00C3: {0x41, 0xB7},
   159  		0x00C8: {0x45, 0xCC},
   160  		0x00C9: {0x45, 0xD0},
   161  		0x00CC: {0x49, 0xD7},
   162  		0x00CD: {0x49, 0xDD},
   163  		0x00D2: {0x4F, 0xDF},
   164  		0x00D3: {0x4F, 0xE3},
   165  		0x00D5: {0x4F, 0xE2},
   166  		0x00D9: {0x55, 0xEF},
   167  		0x00DA: {0x55, 0xF3},
   168  		0x00DD: {0x59, 0xFD},
   169  		0x0128: {0x49, 0xDC},
   170  		0x0168: {0x55, 0xF2},
   171  		0x1EA0: {0x41, 0xB9},
   172  		0x1EA2: {0x41, 0xB6},
   173  		0x1EA4: {0xA2, 0xCA},
   174  		0x1EA6: {0xA2, 0xC7},
   175  		0x1EA8: {0xA2, 0xC8},
   176  		0x1EAA: {0xA2, 0xC9},
   177  		0x1EAC: {0xA2, 0xCB},
   178  		0x1EAE: {0xA1, 0xBE},
   179  		0x1EB0: {0xA1, 0xBB},
   180  		0x1EB2: {0xA1, 0xBC},
   181  		0x1EB4: {0xA1, 0xBD},
   182  		0x1EB6: {0xA1, 0xC6},
   183  		0x1EB8: {0x45, 0xD1},
   184  		0x1EBA: {0x45, 0xCE},
   185  		0x1EBC: {0x45, 0xCF},
   186  		0x1EBE: {0xA3, 0xD5},
   187  		0x1EC0: {0xA3, 0xD2},
   188  		0x1EC2: {0xA3, 0xD3},
   189  		0x1EC4: {0xA3, 0xD4},
   190  		0x1EC6: {0xA3, 0xD6},
   191  		0x1EC8: {0x49, 0xD8},
   192  		0x1ECA: {0x49, 0xDE},
   193  		0x1ECC: {0x4F, 0xE4},
   194  		0x1ECE: {0x4F, 0xE1},
   195  		0x1ED0: {0xA4, 0xE8},
   196  		0x1ED2: {0xA4, 0xE5},
   197  		0x1ED4: {0xA4, 0xE6},
   198  		0x1ED6: {0xA4, 0xE7},
   199  		0x1ED8: {0xA4, 0xE9},
   200  		0x1EDA: {0xA5, 0xED},
   201  		0x1EDC: {0xA5, 0xEA},
   202  		0x1EDE: {0xA5, 0xEB},
   203  		0x1EE0: {0xA5, 0xEC},
   204  		0x1EE2: {0xA5, 0xEE},
   205  		0x1EE4: {0x55, 0xF4},
   206  		0x1EE6: {0x55, 0xF1},
   207  		0x1EE8: {0xA6, 0xF8},
   208  		0x1EEA: {0xA6, 0xF5},
   209  		0x1EEC: {0xA6, 0xF6},
   210  		0x1EEE: {0xA6, 0xF7},
   211  		0x1EF0: {0xA6, 0xF9},
   212  		0x1EF2: {0x59, 0xFA},
   213  		0x1EF4: {0x59, 0xFE},
   214  		0x1EF6: {0x59, 0xFB},
   215  		0x1EF8: {0x59, 0xFC},
   216  	}
   217  	for r, b := range dataTCVN3.UnicodeToWord {
   218  		item := &dataTCVN3.WordToUnicode[b[0]]
   219  		if b[1] == 0 {
   220  			item.r = r
   221  		} else {
   222  			if item.m == nil {
   223  				item.m = new([256]rune)
   224  			}
   225  			item.m[b[1]] = r
   226  		}
   227  	}
   228  }