JSFiddle - React, Tailwind, and code Playground
HTML
<p>
<input type="file" onchange="onChange(event);"><br><br>
<a id="anchor" download="will.chr">will.chr</a>
</p>
<canvas id="canvas"></canvas><br>
<textarea id="textarea" cols="145" rows="25"></textarea>
CSS
canvas {
border: 1px solid green;
}
JavaScript
"use strict";
let ctx;
let chr_rom;
onload = function() {
ctx = canvas.getContext("2d");
};
function onChange(e) {
let file = e.target.files[0];
let r = new FileReader();
r.onload = function(e) {
let img = new Image();
img.onload = function() {
canvas.width = img.naturalWidth;
canvas.height = img.naturalHeight;
ctx.drawImage(img, 0, 0);
picker();
};
img.src = e.target.result;
};
r.readAsDataURL(file);
}
function picker() {
const code = { // 0xAABBGGRR
0xff000000:1, 0xffff0000:4, 0xff00ff00:5, 0xffffff00:6,
0xff0000ff:2, 0xffff00ff:7, 0xff00ffff:3, 0xffffffff:0
};
const sox = 344; // screen offset
const soy = 120;
const cox = 4; // character offset
const coy = 6;
const cw = 25; // character
const ch = 18;
let bgid = 0; // BG pattern id
let spid = 1; // sprite pattern id ※0は飛ばす
let hash = [];
let sprite = "sprite_data:\n";
// ネームテーブル
let name_tbl = new Uint8Array(960);
name_tbl.fill(0);
// BG+スプライトパターン
chr_rom = new Uint8Array(8192);
chr_rom.fill(0);
for (let cy = 0; cy < ch; cy++) {
for (let cx = 0; cx < cw; cx++) {
let imgData = ctx.getImageData(sox + cx * 8, soy + cy * 8, 8, 8);
let pxl = new Uint32Array(imgData.data.buffer);
// タイル文字列
let tile = "";
for (let i = 0; i < 64; i++) {
tile += code[pxl[i]];
}
// BGパターンとネームテーブル
{
let t = tile.replace(/[4567]/g, "0");
if (! hash.hasOwnProperty(t)) {
setchr(bgid, t);
hash[t] = bgid;
bgid++;
}
name_tbl[(coy + cy) * 32 + (cox + cx)] = hash[t];
}
// スプライトパターンとスプライトデータ
if (/[4567]/.test(tile)) {
let x = (cox + cx) * 8;
let y = (coy + cy) * 8 - 1;
let c = (/7/.test(tile)) ? 1 : 0;
sprite += `\tdb\t${y}, ${spid}, ${c}, ${x}\n`;
let p = tile;
p = p.replace(/[0123]/g, "0");
p = p.replace(/4/g, "1");
p = p.replace(/5/g, "2");
p = p.replace(/[67]/g, "3");
setchr(256 + spid, p);
spid++;
}
}
}
// 出力範囲
ctx.strokeStyle =...