using Newtonsoft.Json.Linq; using System.Collections.Generic; using System.IO; using System.Linq; namespace FSO.Common.Rendering.Emoji { public class EmojiDictionary { public Dictionary NameToEmojis = new Dictionary(); public Dictionary> KeywordToCandidates = new Dictionary>(); public Dictionary> CandidatesToKeywords = new Dictionary>(); public EmojiDictionary() { JObject emojis; using (var emojiDict = new StreamReader( new FileStream(Path.Combine(FSOEnvironment.ContentDir, "UI/emojis.json"), FileMode.Open, FileAccess.Read, FileShare.Read))) { emojis = (JObject)Newtonsoft.Json.JsonConvert.DeserializeObject(emojiDict.ReadToEnd()); } foreach (var token in emojis) { var charValue = token.Value.Value("char"); var twemojiID = ToCodePoint(charValue); NameToEmojis[token.Key] = twemojiID; var keys = token.Value.Value("keywords"); foreach (var key in keys) AddKeyword(key.Value(), token.Key); } using (var emojiDict = new StreamReader( new FileStream(Path.Combine(FSOEnvironment.ContentDir, "UI/customemojis.json"), FileMode.Open, FileAccess.Read, FileShare.Read))) { emojis = (JObject)Newtonsoft.Json.JsonConvert.DeserializeObject(emojiDict.ReadToEnd()); } foreach (var token in emojis) { NameToEmojis[token.Key] = "!" + token.Value.Value("url"); var keys = token.Value.Value("keywords"); foreach (var key in keys) AddKeyword(key.Value(), token.Key); } } public void AddKeyword(string keyword, string candidate) { List cand; if (!KeywordToCandidates.TryGetValue(keyword, out cand)) { cand = new List(); KeywordToCandidates[keyword] = cand; } cand.Add(candidate); if (!CandidatesToKeywords.TryGetValue(candidate, out cand)) { cand = new List(); CandidatesToKeywords[candidate] = cand; } cand.Add(keyword); } public string ToCodePoint(string str) { var cs = str.ToCharArray(); var i = 0; var c = 0; var p = 0; var r = new List(); var zeroWidth = str.Any(x => x == '\x200D'); while (i < cs.Length) { c = cs[i++]; if (c == 0xfe0f && !zeroWidth) continue; //"as image", just ignore this if (p > 0) { r.Add((0x10000 + ((p - 0xD800) << 10) + (c - 0xDC00)).ToString("x")); p = 0; } else if (0xD800 <= c && c <= 0xDBFF) { p = c; } else { r.Add(c.ToString("x")); } } return string.Join("-", r); } } }