let states = {"keylayouts":[[""],[undefined], [undefined], [undefined], [undefined], [undefined], [undefined], ["0","`","]","}"], ["1","!","÷","≈"], ["2","?","¤","∞"], ["3","+","§","₴"], ["4",'"',"$","€"], ["5","%","°",""], ["6","=","<","≤"], ["7",":",">","≥"], ["8","/","•","×"], ["9","-","[","{"], ["*"], ["#"], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], ["ь","Ь","ҧ","Ҧ"], ["ф","Ф","ҩ","Ҩ"], ["ъ","Ъ","ї","Ї"], ["а","А","ҟ","Ҟ"], ["е","Е","ҝ","Ҝ"], ["о","О","ө","Ө"], ["ж","Ж","џ","Џ"], ["г","Г","ґ","Ґ"], ["с","С","ҽ","Ҽ"], ["т","Т","ћ","Ћ"], ["н","Н","њ","Њ"], ["в","В","ү","Ү"], ["п","П","ҡ","Ҡ"], ["х","Х","ҳ","Ҳ"], ["д","Д","ђ","Ђ"], ["з","З","ѕ","Ѕ"], [",","ы","і","І"], ["и","И","\u0335","\u0321"], // strikethru, hook below ["я","Я","ә","Ә"], ["ш","Ш","ѓ","Ѓ"], ["к","К","ќ","Ќ"], ["э",'Э',"є","Є"], ["у","У","ў","Ў"], ["й","Й","ј","Ј"], ["щ","Щ","ӡ","Ӡ"], ["ю","Ю","ғ","Ғ"], ["р","Р","«","„"], ["л","Л","»","“"], [undefined], [undefined], [undefined], [undefined], [undefined], [" "], [undefined], [undefined], [undefined], ["\n"], ["\x08"], ["ё","Ё","ӏ","Ӏ"], ["-","_","—","–"], [".","~","≠","±"], ["ц","Ц","ҵ","Ҵ"], [";","§","\u0308","\u0306"], // diaresis, breve [")","(","\\","|"], ["м","М","\u0329","\u0301"], // "descender", acute ["ч","Ч","һ","Һ"], ["б","Б","љ","Љ"], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], ["0"], ["1"], ["2"], ["3"], ["4"], ["5"], ["6"], ["7"], ["8"], ["9"], ["/"], ["*"], ["-"], ["+"], ["."], ["."], ["\n"], ["="], ["("], [")"], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined], [undefined] ], "code":""} // practically unused as long as there are no diacritics on the keyboard let reset = () => { states.code = 0 } let diacriticsAcute = { "Е":"Ѐ", "Г":"Ѓ", "К":"Ќ", "И":"Ѝ", "е":"ѐ", "г":"ѓ", "к":"ќ", "и":"ѝ" } let diacriticsDescender = { "Ж":"Җ", "З":"Ҙ", "К":"Қ", "Н":"Ң", "С":"Ҫ", "Т":"Ҭ", "Х":"Ҳ", "Ч":"Ҷ", "Ҽ":"Ҿ", "Г":"Ӷ", "Ғ":"Ӻ", "П":"Ԥ", "Һ":"Ԧ", "ж":"җ", "з":"ҙ", "к":"қ", "н":"ң", "с":"ҫ", "т":"ҭ", "х":"ҳ", "ч":"ҷ", "ҽ":"ҿ", "г":"ӷ", "ғ":"ӻ", "п":"ԥ", "һ":"ԧ" } let diacriticsStrikethru = { "Г":"Ғ", "К":"Ҟ", "Ү":"Ұ", "Х":"Ӿ", "г":"ғ", "к":"ҟ", "ү":"ұ", "х":"ӿ" } let diacriticsHookBelow = { "Г":"Ҕ", "П":"Ҧ", "К":"Ӄ", "Н":"Ӈ", "Ғ":"Ӻ", "Х":"Ӽ", "г":"ҕ", "п":"ҧ", "к":"ӄ", "н":"ӈ", "ғ":"ӻ", "х":"ӽ" } let diacriticsDiaresis = { "А":"Ӓ", "Ә":"Ӛ", "Ж":"Ӝ", "З":"Ӟ", "И":"Ӥ", "О":"Ӧ", "Ө":"Ӫ", "Э":"Ӭ", "У":"Ӱ", "Ч":"Ӵ", "Ы":"Ӹ", "а":"ӓ", "ә":"ӛ", "ж":"ӝ", "з":"ӟ", "и":"ӥ", "о":"ӧ", "ө":"ӫ", "э":"ӭ", "у":"ӱ", "ч":"ӵ", "ы":"ӹ" } let diacriticsBreve = { "Ж":"Ӂ", "А":"Ӑ", "Е":"Ӗ", "И":"Ӣ", "У":"Ӯ", "ж":"ӂ", "а":"ӑ", "е":"ӗ", "и":"ӣ", "у":"ӯ" } let diacriticsMapping = { "\u0329":diacriticsDescender, "\u0301":diacriticsAcute, "\u0308":diacriticsDiaresis, "\u0306":diacriticsBreve, "\u0335":diacriticsStrikethru, "\u0321":diacriticsHookBelow } let dislplayKeyLayouts = JSON.parse(JSON.stringify(states.keylayouts)) dislplayKeyLayouts.forEach(ks=>{ks.forEach((k,i)=>{ ks[i] = "\uDBBF\uDFC1"+k+"\uDBBF\uDFC0" })}) let inRange = (s,a,b) => (a <= s && s <= b) let isDiacritics = (s) => s !== undefined && inRange(s.charCodeAt(0), 0x0300, 0x036F) return Object.freeze({"n":"\uDBBF\uDFC1Бъл. Многоезична\uDBBF\uDFC0","v":"none","c":"CuriousTo\uA75Bvald","m":"rewrite", "t":dislplayKeyLayouts, "l":"bgBG", // return: [delete count, composed output] "accept":(headkey,shiftin,altgrin)=>{ let layer = 1*shiftin + 2*altgrin let s = (states.keylayouts[headkey][layer] || states.keylayouts[headkey][1*shiftin]) || states.keylayouts[headkey][0] // typing seq for diacritics: diacritics THEN a character if (isDiacritics(s)) { states.code = s return ['0', '\uDBBF\uDE01'+s] } else { // has diacritecs if (states.code != '') { if (diacriticsMapping[states.code] == undefined) { reset() return ['0',''] } let composed = diacriticsMapping[states.code][s] reset() return ['2', composed || s] } // nope! else { reset() return ['0', s] } } }, "backspace":()=>{ reset() return '' }, "end":()=>{ reset() return '' }, "reset":()=>{ reset() }, "composing":()=>(states.code!='') })