Skip to content

Instantly share code, notes, and snippets.

@Korilakkuma
Created November 10, 2022 15:52
Show Gist options
  • Select an option

  • Save Korilakkuma/0f45f2d54a94c0e27ba555fc1b132323 to your computer and use it in GitHub Desktop.

Select an option

Save Korilakkuma/0f45f2d54a94c0e27ba555fc1b132323 to your computer and use it in GitHub Desktop.
<!DOCTYPE html>
<html lang="ja">
<head>
<script>
let wa_instance = null;
let dom_ready = false;
{
const wasm = atob('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');
const len = wasm.length;
const bytes = new Uint8Array(len);
for(let i = 0; i < len; i++) {
bytes[i] = wasm.charCodeAt(i);
}
WebAssembly.compile(bytes).then(function(module) {
return WebAssembly.instantiate(module);
}).then(function(instance) {
wa_instance = instance;
run();
});
}
class lifegame {
constructor(formid, canvasid)
{
this.form = document.getElementById(formid);
this.canvas = document.getElementById(canvasid);
this.context = canvas.getContext("2d");
this.intimer = false;
this.benchcnt = 0;
const o = this;
this.form.btn.addEventListener('click', function() { o.setup(); });
this.form.step.addEventListener('click', function() { if(!o.autorun) o.life(); });
this.form.running.addEventListener('change', function() { o.chgrun(); });
this.form.bench.addEventListener('click', function() {
o.benchcnt = 0;
o.autorun = true;
setTimeout(function() { o.autorun = false; alert(o.benchcnt); }, 10*1000);
o.run();
});
this.setup();
}
setup()
{
this.width = this.form.w.value - 0;
this.height = this.form.h.value - 0;
this.autorun = this.form.running.checked;
this.sz = this.width * this.height * 4;
this.canvas.width = this.width;
this.canvas.height = this.height;
// init
wa_instance.exports.init(this.width, this.height);
this.init_random();
this.draw();
this.next();
}
init_random()
{
for(let y = 0; y < this.height; y++) {
for(let x = 0; x < this.width; x++) {
wa_instance.exports.dot(x, y, Math.random() > .5 ? 1 : 0);
}
}
}
chgrun()
{
this.autorun = this.form.running.checked;
this.next();
}
run()
{
this.life();
this.next();
}
next()
{
if(!this.autorun) return;
if(this.intimer) return;
this.intimer = true;
const o = this;
setTimeout(function() { o.intimer = false; o.run(); }, 0);
}
life()
{
wa_instance.exports.lifegame();
this.draw();
this.benchcnt++;
}
draw()
{
const map = wa_instance.exports.getmap();
const data = new Uint8ClampedArray(wa_instance.exports.memory.buffer, map, this.sz);
const img = new ImageData(data, this.width, this.height);
this.context.putImageData(img, 0, 0);
}
}
function run()
{
if(!dom_ready) return;
if(!wa_instance) return;
new lifegame('form', 'canvas').run();
}
function start()
{
dom_ready = true;
run();
}
</script>
</head>
<body onload="start();">
<p>
<form id="form">
Width:<input type="text" name="w" value="512" size="5">
Height:<input type="text" name="h" value="512" size="5">
<input type="button" name="btn" value="ê›íË"">
<input type="button" name="step" value="é¿çs"">
<input type="checkbox" name="running">é©ìÆé¿çs
<input type="button" name="bench" value="ÉxÉìÉ`É}Å[ÉN"">
</form>
</p>
<canvas id="canvas" width="512" height="512" style="border: 1px solid black;"></canvas>
</body>
</html>
<!DOCTYPE html>
<html lang="ja">
<head>
<script>
let wa_instance = null;
let dom_ready = false;
{
const wasm = atob('AGFzbQEAAAABEwRgAn9/AGADf39/AGAAAX9gAAADBQQAAQIDBQUBAQGAAgYVBH8BQQALfwFBAAt/AUEAC38BQQALBysFBm1lbW9yeQIABGluaXQAAANkb3QAAQZnZXRtYXAAAghsaWZlZ2FtZQADCrgDBFMBA38gACQAIAEkASAAIAFsQQRsIQIgAkECbEH//wNqQRB2PwBrQAAaQQAkAiACJAMjAiIDIAJqIQQDQCADQY+e+Hg2AgAgA0EEaiIDIARJDQALCyAAIAEjAGwgAGpBBGwjAmpByP+jfkGPnvh4IAIbNgIACwQAIwILuwIBC38jAyEAIwBBBGwhASMCIgQjAUEBayABbGohA0EAIQkDQCADIQIgBCIDIAFqIQQgCUEBaiIJIwFGIgogCgRAIwIhBAtByP+jfiACIAFBBGsiCmooAgBGQcj/o34gAyAKaigCAEZByP+jfiAEIApqKAIARmpqIQVByP+jfiACKAIARkHI/6N+IAMoAgBGQcj/o34gBCgCAEZqaiEGQQAhCANAQcj/o34gAiAIQQRqIAFwIgpqKAIARkHI/6N+IAMgCmooAgBGQcj/o34gBCAKaigCAEZqaiIHIAUgBmpqIgpBA0YEQCAAQcj/o342AgAFIApBBEYEQCAAIAMgCGooAgA2AgAFIABBj574eDYCAAsLIAYhBSAHIQYgAEEEaiEAIAhBBGoiCCABSQ0AC0UNAAsjAiMDJAIkAws=');
const len = wasm.length;
const bytes = new Uint8Array(len);
for(let i = 0; i < len; i++) {
bytes[i] = wasm.charCodeAt(i);
}
WebAssembly.compile(bytes).then(function(module) {
return WebAssembly.instantiate(module);
}).then(function(instance) {
wa_instance = instance;
run();
});
}
class lifegame {
constructor(formid, canvasid)
{
this.form = document.getElementById(formid);
this.canvas = document.getElementById(canvasid);
this.context = canvas.getContext("2d");
this.intimer = false;
this.benchcnt = 0;
const o = this;
this.form.btn.addEventListener('click', function() { o.setup(); });
this.form.step.addEventListener('click', function() { if(!o.autorun) o.life(); });
this.form.running.addEventListener('change', function() { o.chgrun(); });
this.form.bench.addEventListener('click', function() {
o.benchcnt = 0;
o.autorun = true;
setTimeout(function() { o.autorun = false; alert(o.benchcnt); }, 10*1000);
o.run();
});
this.setup();
}
setup()
{
this.width = this.form.w.value - 0;
this.height = this.form.h.value - 0;
this.autorun = this.form.running.checked;
this.sz = this.width * this.height * 4;
this.canvas.width = this.width;
this.canvas.height = this.height;
// init
wa_instance.exports.init(this.width, this.height);
this.init_random();
this.draw();
this.next();
}
init_random()
{
for(let y = 0; y < this.height; y++) {
for(let x = 0; x < this.width; x++) {
wa_instance.exports.dot(x, y, Math.random() > .5 ? 1 : 0);
}
}
}
chgrun()
{
this.autorun = this.form.running.checked;
this.next();
}
run()
{
this.life();
this.next();
}
next()
{
if(!this.autorun) return;
if(this.intimer) return;
this.intimer = true;
const o = this;
setTimeout(function() { o.intimer = false; o.run(); }, 0);
}
life()
{
wa_instance.exports.lifegame();
this.draw();
this.benchcnt++;
}
draw()
{
const map = wa_instance.exports.getmap();
const data = new Uint8ClampedArray(wa_instance.exports.memory.buffer, map, this.sz);
const img = new ImageData(data, this.width, this.height);
this.context.putImageData(img, 0, 0);
}
}
function run()
{
if(!dom_ready) return;
if(!wa_instance) return;
new lifegame('form', 'canvas').run();
}
function start()
{
dom_ready = true;
run();
}
</script>
</head>
<body onload="start();">
<p>
<form id="form">
Width:<input type="text" name="w" value="512" size="5">
Height:<input type="text" name="h" value="512" size="5">
<input type="button" name="btn" value="ê›íË"">
<input type="button" name="step" value="é¿çs"">
<input type="checkbox" name="running">é©ìÆé¿çs
<input type="button" name="bench" value="ÉxÉìÉ`É}Å[ÉN"">
</form>
</p>
<canvas id="canvas" width="512" height="512" style="border: 1px solid black;"></canvas>
</body>
</html>
#include <stdio.h>
#include <stdlib.h>
#include <emscripten.h>
static const int pixel0 = 0xff1e0f0f;
static const int pixel1 = 0xffc8ffc8;
#define chk(ofs) (map[ofs] == pixel1)
#define pset(map, ofs, b) (map[ofs] = (b) ? pixel1 : pixel0)
static int *map = NULL;
static int *map2 = NULL;
static int width;
static int height;
static int* allocmap()
{
int sz = width * height;
int* p = (int*)malloc(sz * sizeof(int));
for(int i = 0; i < sz; i++) {
pset(p, i, 0);
}
return p;
}
EMSCRIPTEN_KEEPALIVE
void init(int w, int h)
{
if(map) free(map);
if(map2) free(map2);
width = w;
height = h;
map = allocmap();
map2 = allocmap();
}
EMSCRIPTEN_KEEPALIVE
void dot(int x, int y, int b)
{
pset(map, y * width + x, b);
}
EMSCRIPTEN_KEEPALIVE
int* getmap()
{
return map;
}
EMSCRIPTEN_KEEPALIVE
void lifegame()
{
int ofs = 0;
int cofs0;
int cofs1 = (height - 1) * width;
int cofs2 = 0;
for(int y = 0; y < height; y++) {
cofs0 = cofs1;
cofs1 = cofs2;
cofs2 = ((y+1) % height) * width;
int cnt0 = 0;
int cnt1 = 0;
{
int xx = width - 1;
if(chk(cofs0 + xx)) cnt0++;
if(chk(cofs1 + xx)) cnt0++;
if(chk(cofs2 + xx)) cnt0++;
}
if(chk(cofs0)) cnt1++;
if(chk(cofs1)) cnt1++;
if(chk(cofs2)) cnt1++;
for(int x = 0; x < width; x++) {
int xx = (x + 1) % width;
int cnt2 = 0;
if(chk(cofs0 + xx)) cnt2++;
if(chk(cofs1 + xx)) cnt2++;
if(chk(cofs2 + xx)) cnt2++;
int cnt = cnt0 + cnt1 + cnt2;
if(cnt == 3) {
pset(map2, ofs, 1);
}
else {
if(cnt == 4) {
pset(map2, ofs, chk(cofs1 + x));
}
else {
pset(map2, ofs, 0);
}
}
cnt0 = cnt1;
cnt1 = cnt2;
ofs++;
}
}
// swap buffers
{
int* oldmap = map;
map = map2;
map2 = oldmap;
}
}
(module
(memory $memory 1 256)
;; (global $pixel0 i32 (i32.const 0xff1e0f0f))
;; (global $pixel1 i32 (i32.const 0xffc8ffc8))
(global $width (mut i32) (i32.const 0))
(global $height (mut i32) (i32.const 0))
(global $map (mut i32) (i32.const 0))
(global $map2 (mut i32) (i32.const 0))
;; 初期化
(func $init (param $w i32) (param $h i32)
(local $sz i32)
(local $p i32)
(local $ep i32)
(global.set $width (local.get $w))
(global.set $height (local.get $h))
;; マップのメモリサイズ計算
(local.set $sz (i32.mul (i32.mul (local.get $w) (local.get $h)) (i32.const 4)))
;; 必要ページ数確保
(i32.mul (local.get $sz) (i32.const 2))
(i32.add (i32.const 0xffff))
(i32.shr_u (i32.const 16))
(i32.sub (memory.size))
memory.grow
drop
;; ポインタ保存
(global.set $map (i32.const 0))
(global.set $map2 (local.get $sz))
;; 塗りつぶし
(local.set $ep
(i32.add
(local.tee $p (global.get $map))
(local.get $sz)
)
)
loop $lp1
(i32.store (local.get $p) (i32.const 0xff1e0f0f))
(br_if $lp1
(i32.lt_u
(local.tee $p (i32.add (local.get $p) (i32.const 4)))
(local.get $ep)
)
)
end ;; $lp1
)
;; 点を打つ
(func $dot (param $x i32) (param $y i32) (param $b i32)
(i32.mul (local.get $y) (global.get $width))
(i32.add (local.get $x))
(i32.mul (i32.const 4))
(i32.add (global.get $map))
(select (i32.const 0xffc8ffc8) (i32.const 0xff1e0f0f) (local.get $b))
i32.store
)
;; マップを返す
(func $getmap (result i32)
global.get $map
)
;; ライフゲーム
(func $lifegame
(local $dst i32)
(local $szline i32)
(local $src0 i32)
(local $src1 i32)
(local $src2 i32)
(local $cnt0 i32)
(local $cnt1 i32)
(local $cnt2 i32)
(local $ofsx i32)
(local $y i32)
(local $tmp1 i32)
(local.set $dst (global.get $map2))
(local.set $szline (i32.mul (global.get $width) (i32.const 4)))
(local.set $src1
(i32.add
(local.tee $src2 (global.get $map))
(i32.mul
(i32.sub (global.get $height) (i32.const 1))
(local.get $szline)
)
)
)
(local.set $y (i32.const 0))
loop $lp_y
(local.set $src0 (local.get $src1))
(local.set $src2
(i32.add
(local.tee $src1 (local.get $src2))
(local.get $szline)
)
)
;; $y++ と最下行の判定
(i32.eq
(local.tee $y (i32.add (local.get $y) (i32.const 1)))
(global.get $height)
)
local.tee $tmp1
local.get $tmp1
if
;; 1行下は頂上
(local.set $src2 (global.get $map))
end
;; stack = 最下行フラグ
;; cnt0 計算
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load
(i32.add
(local.get $src0)
(local.tee $tmp1 (i32.sub (local.get $szline) (i32.const 4)))
)
)
)
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load
(i32.add
(local.get $src1)
(local.get $tmp1)
)
)
)
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load
(i32.add
(local.get $src2)
(local.get $tmp1)
)
)
)
i32.add
i32.add
local.set $cnt0
;; cnt1 計算
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load (local.get $src0))
)
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load (local.get $src1))
)
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load (local.get $src2))
)
i32.add
i32.add
local.set $cnt1
(local.set $ofsx (i32.const 0))
loop $lp_x
;; cnt2 計算
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load
(i32.add
(local.get $src0)
(local.tee $tmp1
(i32.rem_u
(i32.add
(local.get $ofsx)
(i32.const 4)
)
(local.get $szline)
)
)
)
)
)
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load
(i32.add
(local.get $src1)
(local.get $tmp1)
)
)
)
(i32.eq
(i32.const 0xffc8ffc8)
(i32.load
(i32.add
(local.get $src2)
(local.get $tmp1)
)
)
)
i32.add
i32.add
local.tee $cnt2
local.get $cnt0
local.get $cnt1
i32.add
i32.add
local.tee $tmp1 ;; cnt1~3 の合計
(i32.eq (i32.const 3))
if
;; cnt == 3 なら必ず点を打つ
(i32.store (local.get $dst) (i32.const 0xffc8ffc8))
else
(i32.eq (local.get $tmp1) (i32.const 4))
if
;; cnt == 4 なら点をコピー
(i32.store
(local.get $dst)
(i32.load (i32.add (local.get $src1) (local.get $ofsx)))
)
else
;; 点を消す
(i32.store (local.get $dst) (i32.const 0xff1e0f0f))
end
end
(local.set $cnt0 (local.get $cnt1))
(local.set $cnt1 (local.get $cnt2))
(local.set $dst (i32.add (local.get $dst) (i32.const 4)))
(i32.lt_u
(local.tee $ofsx (i32.add (local.get $ofsx) (i32.const 4)))
(local.get $szline)
)
br_if $lp_x
end ;; $lp_x
;; 次の $y と最下行判定は済んでる
(br_if $lp_y (i32.eqz))
end ;; lp_y
;; マップ交換
global.get $map
global.get $map2
global.set $map
global.set $map2
)
(export "memory" (memory 0))
(export "init" (func $init))
(export "dot" (func $dot))
(export "getmap" (func $getmap))
(export "lifegame" (func $lifegame))
)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment