let g_emojis; function get_emojis() { if (g_emojis) { return Promise.resolve(g_emojis); } return fetch('emojis.json').then(function(result) { g_emojis = result.json(); return g_emojis; }); } export function picker(callback, anchor) { get_emojis().then(function(json) { let existing = document.getElementById('emoji_picker'); if (existing) { existing.parentElement.removeChild(existing); return; } let div = document.createElement('div'); div.id = 'emoji_picker'; div.style.color = '#000'; div.style.background = '#fff'; div.style.border = '1px solid #000'; div.style.display = 'block'; div.style.position = 'absolute'; div.style.maxWidth = '16em'; div.style.maxHeight = '16em'; div.style.overflow = 'scroll'; div.style.fontWeight = 'bold'; div.style.cursor = 'pointer'; Object.entries(json).forEach(function(row) { let header = document.createElement('div'); header.appendChild(document.createTextNode(row[0])); div.appendChild(header); for (let entry of row[1]) { let emoji = document.createElement('span'); const k_size = '1.25em'; emoji.style.width = k_size; emoji.style.maxWidth = k_size; emoji.style.minWidth = k_size; emoji.style.height = k_size; emoji.style.maxHeight = k_size; emoji.style.minHeight = k_size; emoji.style.display = 'inline-block'; emoji.style.overflow = 'hidden'; emoji.onclick = function() { callback(entry); div.parentElement.removeChild(div); } emoji.appendChild(document.createTextNode(entry.emoji)); div.appendChild(emoji); } }); document.body.appendChild(div); if (anchor) { let rect = anchor.getBoundingClientRect(); if (rect.top < window.clientHeight / 2) { div.style.top = rect.bottom + 'px'; } else { div.style.top = (rect.top - div.clientHeight) + 'px'; } if (rect.left < window.clientWidth / 2) { div.style.left = rect.left + 'px'; } else { div.style.left = (rect.left - div.clientWidth) + 'px'; } } }); }