Improve script for detecting supported unicode aliases

This commit is contained in:
Mislav Marohnić 2017-04-21 15:12:54 +02:00
Родитель 7858e79566
Коммит ed954928d7
1 изменённых файлов: 55 добавлений и 50 удалений

Просмотреть файл

@ -11,71 +11,76 @@
<textarea id="output" rows="50" cols="80"></textarea>
<script>
const VARIATION_SELECTOR_15 = String.fromCharCode(0xfe0e);
const VARIATION_SELECTOR_16 = String.fromCharCode(0xfe0f);
const EMOJI_SIZE = 32
const VARIATION_SELECTOR_16 = /\ufe0f$/
function detectAliases(db) {
for (var i = 0; i < db.length; ++i) {
var emoji = db[i];
var raw = emoji.emoji;
if (!raw) {
continue;
}
const canvas = document.createElement('canvas')
if (raw.indexOf(VARIATION_SELECTOR_16) > -1) {
var candidates = [raw.replace(VARIATION_SELECTOR_16, ""), raw];
for (const emoji of db) {
const raw = emoji.emoji
if (!raw) continue
const candidates = [raw]
if (VARIATION_SELECTOR_16.test(raw)) {
candidates.unshift(raw.replace(VARIATION_SELECTOR_16, ''))
} else {
var candidates = [raw, raw + VARIATION_SELECTOR_16];
candidates.push(`${raw}\u{fe0f}`)
}
var aliases = candidates.filter(isColorEmoji);
emoji.emoji = aliases[0];
}
const newRaw = candidates.filter(e => detectEmoji(canvas, e))[0]
dump(db);
}
function isColorEmoji(candidate) {
// Draw the emoji twice using a different color each time. If the emoji
// draws as the same color regardless of what color we set, it's a color
// emoji.
return color(candidate, "#f00") === color(candidate, "#0f0");
}
var canvas = document.createElement("canvas");
canvas.width = canvas.height = EMOJI_SIZE;
function color(emoji, rgb) {
var context = canvas.getContext("2d");
context.clearRect(0, 0, canvas.width, canvas.height);
context.fillStyle = rgb;
context.textBaseline = "top";
context.font = EMOJI_SIZE+"px Arial";
context.fillText(emoji, 0, 0);
var data = context.getImageData(0, 0, EMOJI_SIZE, EMOJI_SIZE).data;
for (var i = 0; i < data.length; i += 4) {
if (data[i] === 0 && data[i + 1] === 0 && data[i + 2] === 0) {
continue;
if (newRaw && newRaw != raw) {
emoji.emoji = newRaw
console.info('new raw representation found for %s :%s:', raw, emoji.aliases[0])
}
if (!newRaw) {
console.warn('no raw representation for %s :%s:', raw, emoji.aliases[0])
}
return data[i].toString(16)
+ data[i + 1].toString(16)
+ data[i + 2].toString(16);
}
return "no colored pixel found";
dump(db)
}
function detectEmoji(canvas, emoji) {
const context = canvas.getContext('2d')
drawEmoji(context, emoji)
let supported = false
const data = context.getImageData(0, 16, 64, 1).data
for (let x = 0; x <= 64; x++) {
if (x <= 32) {
// character is supported if there are any colored pixels found
if (data[4*x] || data[4*x + 1] || data[4*x + 2]) supported = true
} else if (x >= 48 && data[4*x + 3] > 0) {
// however, if more than one character got rendered, treat as unsupported
supported = false
break
}
}
return supported
}
function drawEmoji(context, emoji) {
context.clearRect(0, 0, 400, 400)
context.fillStyle = '#000'
context.textBaseline = 'top'
context.font = '32px sans-serif, "Apple Color Emoji", "Segoe UI", "Segoe UI Emoji", "Segoe UI Symbol"'
context.fillText(emoji+'___', 0, 0)
}
function dump(db) {
var json = JSON.stringify(db, null, " ")
var json = JSON.stringify(db, null, ' ')
.replace(/^( +)(.+)\[\](,?)$/mg, "$1$2[\n$1]$3")
.replace(/,\n( *) /g, "\n$1, ");
document.getElementById("output").value = json + "\n";
.replace(/,\n( *) /g, "\n$1, ")
document.getElementById('output').value = `${json}\n`
}
var xhr = new XMLHttpRequest;
var xhr = new XMLHttpRequest
xhr.onload = function() {
detectAliases(JSON.parse(this.responseText));
detectAliases(JSON.parse(xhr.responseText))
};
xhr.open("GET", "emoji.json", false);
xhr.send(null);
xhr.open('GET', 'emoji.json', false)
xhr.send(null)
</script>