123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201 |
- // Copyright (C) 2017 Keelan Lightfoot
- // Copyright (C) 2007-2008 Board of Regents of the University of Wisconsin
- // System (Univ. of Wisconsin-Madison, Trace R&D Center)
- // Copyright (C) 2007-2008 Omnitor AB
- // Copyright (C) 2007-2008 Voiceriver Inc
- //
- // This library is free software; you can redistribute it and/or modify it
- // under the terms of the GNU Lesser General Public License as published by
- // the Free Software Foundation; either version 2.1 of the License, or (at
- // your option) any later version.
-
- package openbaudot
-
- import "unicode"
-
- const (
- shiftUnknown = iota
- shiftLetter
- shiftFigure
- shiftWhitespace
- )
-
- var (
- defaultSubstitutes = map[rune]rune{
- '{': '(',
- '}': ')',
- '[': '(',
- ']': ')',
- }
- // TDD Telecommunications Device for the Deaf standard
- TDD = CodeSet{
- Codes: [2][]rune{
- {'\b', 'E', '\n', 'A', ' ', 'S', 'I', 'U', '\r', 'D', 'R', 'J', 'N', 'F', 'C', 'K', 'T', 'Z', 'L', 'W', 'H', 'Y', 'P', 'Q', 'O', 'B', 'G', '\x0e', 'M', 'X', 'V', '\x0f'},
- {'\b', '3', '\n', '-', ' ', ',', '8', '7', '\r', '$', '4', '\'', ',', '!', ':', '(', '5', '"', ')', '2', '=', '6', '0', '1', '9', '?', '+', '\x0e', '.', '/', ';', '\x0f'},
- },
- Substitutes: defaultSubstitutes,
- Fallback: '\'',
- ShiftCode: 0x1b,
- UnshiftCode: 0x1f,
- }
- // USTTY US Teletype Corporation
- USTTY = CodeSet{
- Codes: [2][]rune{
- {'\x00', 'E', '\n', 'A', ' ', 'S', 'I', 'U', '\r', 'D', 'R', 'J', 'N', 'F', 'C', 'K', 'T', 'Z', 'L', 'W', 'H', 'Y', 'P', 'Q', 'O', 'B', 'G', '\x0e', 'M', 'X', 'V', '\x0f'},
- {'\x00', '3', '\n', '-', ' ', '\a', '8', '7', '\r', '$', '4', '\'', ',', '!', ':', '(', '5', '"', ')', '2', '#', '6', '0', '1', '9', '?', '&', '\x0e', '.', '/', ';', '\x0f'},
- },
- Substitutes: defaultSubstitutes,
- Fallback: '-',
- ShiftCode: 0x1b,
- UnshiftCode: 0x1f,
- }
- // USITA2 USITA2
- USITA2 = CodeSet{
- Codes: [2][]rune{
- {'\x00', 'E', '\n', 'A', ' ', 'S', 'I', 'U', '\r', 'D', 'R', 'J', 'N', 'F', 'C', 'K', 'T', 'Z', 'L', 'W', 'H', 'Y', 'P', 'Q', 'O', 'B', 'G', '\x0e', 'M', 'X', 'V', '\x0f'},
- {'\x00', '3', '\n', '-', ' ', '\'', '8', '7', '\r', '$', '4', '\a', ',', '!', ':', '(', '5', '"', ')', '2', '=', '6', '0', '1', '9', '?', '&', '\x0e', '.', '/', '=', '\x0f'},
- },
- Substitutes: defaultSubstitutes,
- Fallback: '-',
- ShiftCode: 0x1b,
- UnshiftCode: 0x1f,
- }
- // Weather US Weather
- Weather = CodeSet{
- Codes: [2][]rune{
- {'\x00', 'E', '\n', 'A', ' ', 'S', 'I', 'U', '\r', 'D', 'R', 'J', 'N', 'F', 'C', 'K', 'T', 'Z', 'L', 'W', 'H', 'Y', 'P', 'Q', 'O', 'B', 'G', '\x0e', 'M', 'X', 'V', '\x0f'},
- {'\x00', '3', '\n', '↑', ' ', '\a', '8', '7', '\r', '↗', '4', '↙', '⦷', '→', '○', '←', '5', '+', '↖', '2', '↓', '6', '0', '1', '9', '⊕', '↘', '\x0e', '.', '/', '⦶', '\x0f'},
- },
- Substitutes: defaultSubstitutes,
- Fallback: '-',
- ShiftCode: 0x1b,
- UnshiftCode: 0x1f,
- }
- // Fractions US Fractions
- Fractions = CodeSet{
- Codes: [2][]rune{
- {'\x00', 'E', '\n', 'A', ' ', 'S', 'I', 'U', '\r', 'D', 'R', 'J', 'N', 'F', 'C', 'K', 'T', 'Z', 'L', 'W', 'H', 'Y', 'P', 'Q', 'O', 'B', 'G', '\x0e', 'M', 'X', 'V', '\x0f'},
- {'\x00', '3', '\n', '↑', ' ', '\a', '8', '7', '\r', '$', '4', '\'', '⅞', '¼', '⅛', '½', '5', '"', '¾', '2', ' ', '6', '0', '1', '9', '⅝', '&', '\x0e', '.', '/', '⅜', '\x0f'},
- },
- Substitutes: defaultSubstitutes,
- Fallback: '-',
- ShiftCode: 0x1b,
- UnshiftCode: 0x1f,
- }
- )
-
- // CodeSet represents a teletype character set.
- type CodeSet struct {
- // Codes specifies a mapping of runes to codes. There are two tables, 0 for ltrs, 1 for figs
- Codes [2][]rune
- // Substitutes specifies what characters to re-map to existing table entries
- Substitutes map[rune]rune
- // Fallback specifies what rune to use when a table entry or substitution cant be found
- Fallback rune
- // ShiftRune is fun
- ShiftCode byte
- // UnshiftRune is fun
- UnshiftCode byte
-
- runeToCodeSet map[rune]code
- initialized bool
- }
-
- type code struct {
- shift int
- v byte
- }
-
- //LoadCharset is fun
- func LoadCharset(cs *CodeSet) *CodeSet {
- if !cs.initialized {
- cs.initialize()
- }
- return cs
- }
-
- func (cs *CodeSet) initialize() *CodeSet {
-
- cs.runeToCodeSet = make(map[rune]code)
-
- for i, runes := range cs.Codes {
-
- var shift int
-
- switch i {
- case 0:
- shift = shiftLetter
- case 1:
- shift = shiftFigure
- }
-
- for v, r := range runes {
- if c, exists := cs.runeToCodeSet[r]; exists {
- c.shift = shiftWhitespace
- cs.runeToCodeSet[r] = c
- } else {
- cs.runeToCodeSet[r] = code{
- shift: shift,
- v: byte(v),
- }
- }
-
- }
- }
-
- for in, out := range cs.Substitutes {
- if _, ok := cs.runeToCodeSet[in]; ok {
- // dont load a translation if it overlaps an existing table entry
- continue
- }
- if b, ok := cs.runeToCodeSet[out]; ok {
- // only set the translation if the output exists in table
- cs.runeToCodeSet[in] = b
- }
- }
- return cs
- }
-
- func (cs *CodeSet) toCode(r rune) code {
-
- if c, ok := cs.runeToCodeSet[unicode.ToUpper(r)]; ok {
- return c
- }
-
- return cs.runeToCodeSet[cs.Fallback]
- }
-
- func (cs *CodeSet) toByte(r rune) byte {
-
- if c, ok := cs.runeToCodeSet[unicode.ToUpper(r)]; ok {
- return c.v
- }
-
- return cs.runeToCodeSet[cs.Fallback].v
- }
-
- func (c code) toByte() byte {
- return c.v
- }
-
- func (cs *CodeSet) shift() byte {
- return cs.ShiftCode
- }
-
- func (cs *CodeSet) unshift() byte {
- return cs.UnshiftCode
- }
-
- func (cs *CodeSet) toRune(shift int, b byte) rune {
- var i int
- switch shift {
- case shiftLetter:
- i = 0
- case shiftFigure:
- i = 1
- }
- if int(b) < len(cs.Codes[i]) {
- return cs.Codes[i][int(b)]
- }
- return '�'
- }
|