bef93-runner blogpost
This commit is contained in:
parent
a3c191a837
commit
4f7795c70b
@ -53,6 +53,13 @@ body {
|
|||||||
display: block;
|
display: block;
|
||||||
width: 100%; }
|
width: 100%; }
|
||||||
|
|
||||||
|
.generic_hidden {
|
||||||
|
visibility: hidden !important; }
|
||||||
|
|
||||||
|
.generic_collapsed {
|
||||||
|
visibility: collapse !important;
|
||||||
|
display: none !important; }
|
||||||
|
|
||||||
#headerdiv {
|
#headerdiv {
|
||||||
z-index: 999;
|
z-index: 999;
|
||||||
background-color: #333;
|
background-color: #333;
|
||||||
@ -610,10 +617,17 @@ html, body {
|
|||||||
background: #F8F8F8;
|
background: #F8F8F8;
|
||||||
color: black;
|
color: black;
|
||||||
border: 1px solid rgba(0, 0, 0, 0.15); }
|
border: 1px solid rgba(0, 0, 0, 0.15); }
|
||||||
.bce_code .bce_code_data {
|
.bce_code .bce_code_data, .bce_code .bce_code_editarea {
|
||||||
overflow-x: auto;
|
overflow-x: auto;
|
||||||
font-family: Consolas, Monaco, "Courier New", Menlo, monospace;
|
font-family: Consolas, Monaco, "Courier New", Menlo, monospace;
|
||||||
padding: 5px 9.5px;
|
padding: 5px 9.5px;
|
||||||
|
line-height: 12pt;
|
||||||
|
font-size: 10pt; }
|
||||||
|
.bce_code .bce_code_editarea {
|
||||||
|
display: block;
|
||||||
|
resize: none;
|
||||||
|
box-sizing: border-box;
|
||||||
|
line-height: 12pt;
|
||||||
font-size: 10pt; }
|
font-size: 10pt; }
|
||||||
.bce_code .bce_code_ctrl {
|
.bce_code .bce_code_ctrl {
|
||||||
background: #BBB;
|
background: #BBB;
|
||||||
@ -722,8 +736,5 @@ html, body {
|
|||||||
.bce_code_out .bce_code_out_right {
|
.bce_code_out .bce_code_out_right {
|
||||||
width: auto;
|
width: auto;
|
||||||
height: 150px; } }
|
height: 150px; } }
|
||||||
.b93rnr_outpanel_hidden {
|
|
||||||
visibility: collapse;
|
|
||||||
display: none; }
|
|
||||||
|
|
||||||
/*# sourceMappingURL=styles.css.map */
|
/*# sourceMappingURL=styles.css.map */
|
||||||
|
@ -5,11 +5,21 @@
|
|||||||
color: black;
|
color: black;
|
||||||
border: 1px solid rgba(0, 0, 0, 0.15);
|
border: 1px solid rgba(0, 0, 0, 0.15);
|
||||||
|
|
||||||
.bce_code_data {
|
.bce_code_data, .bce_code_editarea {
|
||||||
overflow-x: auto;
|
overflow-x: auto;
|
||||||
font-family: $FONT_CODE;
|
font-family: $FONT_CODE;
|
||||||
padding: 5px 9.5px;
|
padding: 5px 9.5px;
|
||||||
|
|
||||||
|
line-height: 12pt;
|
||||||
|
font-size: 10pt;
|
||||||
|
}
|
||||||
|
|
||||||
|
.bce_code_editarea {
|
||||||
|
display: block;
|
||||||
|
resize: none;
|
||||||
|
box-sizing: border-box;
|
||||||
|
|
||||||
|
line-height: 12pt;
|
||||||
font-size: 10pt;
|
font-size: 10pt;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -129,5 +139,3 @@
|
|||||||
.bce_code_out_right { width: auto; height: 150px;}
|
.bce_code_out_right { width: auto; height: 150px;}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.b93rnr_outpanel_hidden { visibility: collapse; display: none; }
|
|
@ -57,3 +57,6 @@ body {
|
|||||||
display: block;
|
display: block;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.generic_hidden { visibility: hidden !important; }
|
||||||
|
.generic_collapsed { visibility: collapse !important; display: none !important; }
|
||||||
|
@ -1,6 +1,15 @@
|
|||||||
|
|
||||||
const BefState = Object.freeze ({ UNINIITIALIZED: {}, INITIAL: {}, RUNNING: {}, PAUSED: {} });
|
const BefState = Object.freeze ({ INITIAL: {}, RUNNING: {}, PAUSED: {}, FINISHED: {}, EDIT: {} });
|
||||||
const BefSpeed = Object.freeze ({ SLOW: {str:'0'}, NORMAL: {str:'+'}, FAST: {str:'++'}, SUPERFAST: {str:'3+'}, MAX: {str:'4+'} });
|
const BefSpeed = Object.freeze (
|
||||||
|
{
|
||||||
|
SLOW: {val:0,str:'0' },
|
||||||
|
NORMAL: {val:1,str:'+' },
|
||||||
|
FAST: {val:2,str:'++'},
|
||||||
|
SUPERFAST: {val:3,str:'3+'},
|
||||||
|
MAX: {val:4,str:'4+'},
|
||||||
|
get: function(i){ for (let x of Object.values(BefSpeed)) if (typeof(x)==='object' && String(x.val) === String(i)) return x; return null; },
|
||||||
|
max: function( ){let max = 0; for (let x of Object.values(BefSpeed)) if (typeof(x)==='object' ) max = Math.max(x.val); return max; },
|
||||||
|
});
|
||||||
|
|
||||||
Array.prototype.peek = function() { return this[this.length - 1]; };
|
Array.prototype.peek = function() { return this[this.length - 1]; };
|
||||||
Array.prototype.revjoin = function(sep) {
|
Array.prototype.revjoin = function(sep) {
|
||||||
@ -14,14 +23,17 @@ function BefObject(domBase) {
|
|||||||
this.btnStop = domBase.getElementsByClassName('b93rnr_pause')[0];
|
this.btnStop = domBase.getElementsByClassName('b93rnr_pause')[0];
|
||||||
this.btnReset = domBase.getElementsByClassName('b93rnr_reset')[0];
|
this.btnReset = domBase.getElementsByClassName('b93rnr_reset')[0];
|
||||||
this.btnSpeed = domBase.getElementsByClassName('b93rnr_speed')[0];
|
this.btnSpeed = domBase.getElementsByClassName('b93rnr_speed')[0];
|
||||||
|
this.btnEdit = domBase.getElementsByClassName('b93rnr_edit')[0];
|
||||||
this.pnlCode = domBase.getElementsByClassName('b93rnr_data')[0];
|
this.pnlCode = domBase.getElementsByClassName('b93rnr_data')[0];
|
||||||
|
this.pnlEditArea = domBase.getElementsByClassName('b93rnr_editarea')[0];
|
||||||
this.pnlBottom = domBase.getElementsByClassName('b93rnr_outpanel')[0];
|
this.pnlBottom = domBase.getElementsByClassName('b93rnr_outpanel')[0];
|
||||||
this.pnlOutput = domBase.getElementsByClassName('b93rnr_output')[0];
|
this.pnlOutput = domBase.getElementsByClassName('b93rnr_output')[0];
|
||||||
this.pnlStack = domBase.getElementsByClassName('b93rnr_stack')[0];
|
this.pnlStack = domBase.getElementsByClassName('b93rnr_stack')[0];
|
||||||
this.lblStackSize = domBase.getElementsByClassName('b93rnr_stacksize')[0];
|
this.lblStackSize = domBase.getElementsByClassName('b93rnr_stacksize')[0];
|
||||||
|
|
||||||
this.state = BefState.UNINIITIALIZED;
|
this.state = BefState.INITIAL;
|
||||||
this.initial = atob(this.pnlCode.getAttribute('data-befcode'));
|
this.initial = atob(this.pnlCode.getAttribute('data-b93rnr_code'));
|
||||||
|
this.simspeed = BefSpeed.get(domBase.hasAttribute('data-b93rnr_initialspeed') ? domBase.getAttribute('data-b93rnr_initialspeed') : '4');
|
||||||
this.code = [];
|
this.code = [];
|
||||||
this.width = 0;
|
this.width = 0;
|
||||||
this.height = 0;
|
this.height = 0;
|
||||||
@ -32,10 +44,13 @@ function BefObject(domBase) {
|
|||||||
this.stack = [];
|
this.stack = [];
|
||||||
this.timer = null;
|
this.timer = null;
|
||||||
this.psteps = 0;
|
this.psteps = 0;
|
||||||
this.simspeed = BefSpeed.SUPERFAST;
|
|
||||||
|
this.init();
|
||||||
|
|
||||||
|
this.updateUI();
|
||||||
}
|
}
|
||||||
|
|
||||||
BefObject.prototype.Init = function() {
|
BefObject.prototype.init = function() {
|
||||||
this.state = BefState.INITIAL;
|
this.state = BefState.INITIAL;
|
||||||
|
|
||||||
let parse = this.parseBef(this.initial);
|
let parse = this.parseBef(this.initial);
|
||||||
@ -51,8 +66,21 @@ BefObject.prototype.Init = function() {
|
|||||||
this.psteps = 0;
|
this.psteps = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
BefObject.prototype.setTimer = function() {
|
||||||
|
let me = this;
|
||||||
|
|
||||||
|
let delay = (this.simspeed === BefSpeed.SLOW) ? 50 : 0;
|
||||||
|
|
||||||
|
this.timer = setTimeout(function()
|
||||||
|
{
|
||||||
|
me.step();
|
||||||
|
if (me.state!==BefState.RUNNING) return;
|
||||||
|
me.setTimer();
|
||||||
|
}, delay);
|
||||||
|
};
|
||||||
|
|
||||||
BefObject.prototype.start = function() {
|
BefObject.prototype.start = function() {
|
||||||
if (this.state === BefState.UNINIITIALIZED) this.Init();
|
if (this.state === BefState.EDIT) { this.finishEdit(); return; }
|
||||||
|
|
||||||
if (this.delta[0]===0 && this.delta[1]===0) {
|
if (this.delta[0]===0 && this.delta[1]===0) {
|
||||||
this.updateUI();
|
this.updateUI();
|
||||||
@ -68,34 +96,27 @@ BefObject.prototype.start = function() {
|
|||||||
this.setTimer();
|
this.setTimer();
|
||||||
};
|
};
|
||||||
|
|
||||||
BefObject.prototype.setTimer = function() {
|
|
||||||
let me = this;
|
|
||||||
|
|
||||||
let delay = (this.simspeed === BefSpeed.SLOW) ? 50 : 0;
|
|
||||||
|
|
||||||
this.timer = setTimeout(function()
|
|
||||||
{
|
|
||||||
me.step();
|
|
||||||
if (me.state!==BefState.RUNNING) return;
|
|
||||||
me.setTimer();
|
|
||||||
}, delay);
|
|
||||||
};
|
|
||||||
|
|
||||||
BefObject.prototype.stop = function() {
|
BefObject.prototype.stop = function() {
|
||||||
this.state = BefState.PAUSED;
|
this.state = BefState.PAUSED;
|
||||||
clearTimeout(this.timer);
|
clearTimeout(this.timer);
|
||||||
// pause
|
|
||||||
|
this.updateUI();
|
||||||
|
this.updateDisplay();
|
||||||
|
};
|
||||||
|
|
||||||
|
BefObject.prototype.finishRun = function() {
|
||||||
|
this.state = BefState.FINISHED;
|
||||||
|
clearTimeout(this.timer);
|
||||||
|
|
||||||
this.updateUI();
|
this.updateUI();
|
||||||
this.updateDisplay();
|
this.updateDisplay();
|
||||||
};
|
};
|
||||||
|
|
||||||
BefObject.prototype.reset = function() {
|
BefObject.prototype.reset = function() {
|
||||||
|
if (this.state === BefState.EDIT) { this.abortEdit(); return; }
|
||||||
if (this.state === BefState.RUNNING) this.stop();
|
if (this.state === BefState.RUNNING) this.stop();
|
||||||
|
|
||||||
this.state = BefState.INITIAL;
|
this.init();
|
||||||
this.Init();
|
|
||||||
this.state = BefState.INITIAL;
|
|
||||||
|
|
||||||
this.updateUI();
|
this.updateUI();
|
||||||
this.updateDisplay();
|
this.updateDisplay();
|
||||||
@ -103,15 +124,44 @@ BefObject.prototype.reset = function() {
|
|||||||
|
|
||||||
BefObject.prototype.incSpeed = function() {
|
BefObject.prototype.incSpeed = function() {
|
||||||
|
|
||||||
if (this.simspeed === BefSpeed.SLOW) this.simspeed = BefSpeed.NORMAL;
|
this.simspeed = BefSpeed.get((this.simspeed.val + 1) % (BefSpeed.max()+1));
|
||||||
else if (this.simspeed === BefSpeed.NORMAL) this.simspeed = BefSpeed.FAST;
|
|
||||||
else if (this.simspeed === BefSpeed.FAST) this.simspeed = BefSpeed.SUPERFAST;
|
|
||||||
else if (this.simspeed === BefSpeed.SUPERFAST) this.simspeed = BefSpeed.MAX;
|
|
||||||
else if (this.simspeed === BefSpeed.MAX) this.simspeed = BefSpeed.SLOW;
|
|
||||||
|
|
||||||
this.updateUI();
|
this.updateUI();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
BefObject.prototype.startEdit = function() {
|
||||||
|
if (this.state === BefState.RUNNING) this.stop();
|
||||||
|
|
||||||
|
this.pnlEditArea.value = this.getDisplayRaw();
|
||||||
|
|
||||||
|
this.pnlEditArea.style.width = this.pnlCode.clientWidth + 'px';
|
||||||
|
this.pnlEditArea.style.height = this.pnlCode.clientHeight + 'px';
|
||||||
|
|
||||||
|
this.state = BefState.EDIT;
|
||||||
|
|
||||||
|
this.updateUI();
|
||||||
|
};
|
||||||
|
|
||||||
|
BefObject.prototype.finishEdit = function() {
|
||||||
|
if (this.state !== BefState.EDIT) return;
|
||||||
|
|
||||||
|
this.initial = this.pnlEditArea.value;
|
||||||
|
this.init();
|
||||||
|
|
||||||
|
this.updateUI();
|
||||||
|
this.updateDisplay();
|
||||||
|
};
|
||||||
|
|
||||||
|
BefObject.prototype.abortEdit = function() {
|
||||||
|
if (this.state !== BefState.EDIT) return;
|
||||||
|
|
||||||
|
this.pnlEditArea.value = '';
|
||||||
|
this.init();
|
||||||
|
|
||||||
|
this.updateUI();
|
||||||
|
this.updateDisplay();
|
||||||
|
};
|
||||||
|
|
||||||
BefObject.prototype.step = function() {
|
BefObject.prototype.step = function() {
|
||||||
|
|
||||||
if (this.simspeed === BefSpeed.NORMAL || this.simspeed === BefSpeed.SLOW) {
|
if (this.simspeed === BefSpeed.NORMAL || this.simspeed === BefSpeed.SLOW) {
|
||||||
@ -160,7 +210,7 @@ BefObject.prototype.stepSingle = function() {
|
|||||||
|
|
||||||
if (this.delta[0]===0 && this.delta[1]===0) {
|
if (this.delta[0]===0 && this.delta[1]===0) {
|
||||||
console.log('Finished in ' + this.psteps + ' steps');
|
console.log('Finished in ' + this.psteps + ' steps');
|
||||||
this.stop();
|
this.finishRun();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -252,16 +302,63 @@ BefObject.prototype.gridget_i = function(x,y) { if (x < 0 || y < 0 || x >= thi
|
|||||||
|
|
||||||
BefObject.prototype.updateUI = function() {
|
BefObject.prototype.updateUI = function() {
|
||||||
|
|
||||||
classListSet(this.btnStart, 'ctrl_btn_disabled', this.state === BefState.RUNNING || this.state === BefState.PAUSED);
|
switch (this.state) {
|
||||||
classListSet(this.btnStop, 'ctrl_btn_disabled', this.state === BefState.UNINIITIALIZED || this.state === BefState.INITIAL);
|
case BefState.INITIAL:
|
||||||
classListSet(this.btnReset, 'ctrl_btn_disabled', this.state === BefState.UNINIITIALIZED || this.state === BefState.INITIAL);
|
cssCtrlState(this.btnStart, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnSpeed, 'ctrl_btn_disabled', true);
|
||||||
classListSet(this.pnlBottom, 'b93rnr_outpanel_hidden', this.state === BefState.UNINIITIALIZED || this.state === BefState.INITIAL);
|
cssCtrlState(this.btnStop, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnReset, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnEdit, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.pnlBottom, 'generic_collapsed', false);
|
||||||
|
cssCtrlState(this.pnlEditArea, 'generic_collapsed', false);
|
||||||
|
cssCtrlState(this.pnlCode, 'generic_collapsed', true);
|
||||||
|
break;
|
||||||
|
case BefState.RUNNING:
|
||||||
|
cssCtrlState(this.btnStart, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnSpeed, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnStop, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnReset, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnEdit, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.pnlBottom, 'generic_collapsed', true);
|
||||||
|
cssCtrlState(this.pnlEditArea, 'generic_collapsed', false);
|
||||||
|
cssCtrlState(this.pnlCode, 'generic_collapsed', true);
|
||||||
|
break;
|
||||||
|
case BefState.PAUSED:
|
||||||
|
cssCtrlState(this.btnStart, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnSpeed, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnStop, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnReset, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnEdit, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.pnlBottom, 'generic_collapsed', true);
|
||||||
|
cssCtrlState(this.pnlEditArea, 'generic_collapsed', false);
|
||||||
|
cssCtrlState(this.pnlCode, 'generic_collapsed', true);
|
||||||
|
break;
|
||||||
|
case BefState.FINISHED:
|
||||||
|
cssCtrlState(this.btnStart, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnSpeed, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnStop, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnReset, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnEdit, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.pnlBottom, 'generic_collapsed', true);
|
||||||
|
cssCtrlState(this.pnlEditArea, 'generic_collapsed', false);
|
||||||
|
cssCtrlState(this.pnlCode, 'generic_collapsed', true);
|
||||||
|
break;
|
||||||
|
case BefState.EDIT:
|
||||||
|
cssCtrlState(this.btnStart, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnSpeed, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnStop, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.btnReset, 'ctrl_btn_disabled', true);
|
||||||
|
cssCtrlState(this.btnEdit, 'ctrl_btn_disabled', false);
|
||||||
|
cssCtrlState(this.pnlBottom, 'generic_collapsed', false);
|
||||||
|
cssCtrlState(this.pnlEditArea, 'generic_collapsed', true);
|
||||||
|
cssCtrlState(this.pnlCode, 'generic_collapsed', false);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
this.btnSpeed.innerHTML = this.simspeed.str;
|
this.btnSpeed.innerHTML = this.simspeed.str;
|
||||||
};
|
};
|
||||||
|
|
||||||
BefObject.prototype.updateDisplay = function() {
|
BefObject.prototype.getDisplayHTML = function() {
|
||||||
let str = '';
|
let str = '';
|
||||||
for (let y=0; y < this.height; y++) {
|
for (let y=0; y < this.height; y++) {
|
||||||
for (let x=0; x < this.width; x++) {
|
for (let x=0; x < this.width; x++) {
|
||||||
@ -278,7 +375,22 @@ BefObject.prototype.updateDisplay = function() {
|
|||||||
}
|
}
|
||||||
str += '<br/>';
|
str += '<br/>';
|
||||||
}
|
}
|
||||||
this.pnlCode.innerHTML = str;
|
return str;
|
||||||
|
};
|
||||||
|
|
||||||
|
BefObject.prototype.getDisplayRaw = function() {
|
||||||
|
let str = '';
|
||||||
|
for (let y=0; y < this.height; y++) {
|
||||||
|
for (let x=0; x < this.width; x++) {
|
||||||
|
str += String.fromCharCode(this.code[y][x]);
|
||||||
|
}
|
||||||
|
str += '\n';
|
||||||
|
}
|
||||||
|
return str;
|
||||||
|
};
|
||||||
|
|
||||||
|
BefObject.prototype.updateDisplay = function() {
|
||||||
|
this.pnlCode.innerHTML = this.getDisplayHTML();
|
||||||
|
|
||||||
this.pnlOutput.innerHTML = htmlescape(this.output);
|
this.pnlOutput.innerHTML = htmlescape(this.output);
|
||||||
|
|
||||||
@ -307,13 +419,16 @@ BefObject.prototype.parseBef = function(str) {
|
|||||||
return [result, max, result.length];
|
return [result, max, result.length];
|
||||||
};
|
};
|
||||||
|
|
||||||
function classListSet(e, cls, active) {
|
function cssCtrlState(e, cls, state) {
|
||||||
if (active) {
|
|
||||||
if (e.classList.contains(cls)) return;
|
if (e === undefined) return;
|
||||||
e.classList.add(cls);
|
|
||||||
} else {
|
if (state) {
|
||||||
if (!e.classList.contains(cls)) return;
|
if (!e.classList.contains(cls)) return;
|
||||||
e.classList.remove(cls);
|
e.classList.remove(cls);
|
||||||
|
} else {
|
||||||
|
if (e.classList.contains(cls)) return;
|
||||||
|
e.classList.add(cls);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -334,9 +449,19 @@ window.onload = function ()
|
|||||||
|
|
||||||
let befungeObject = new BefObject(elem);
|
let befungeObject = new BefObject(elem);
|
||||||
|
|
||||||
|
if (befungeObject.btnStart !== undefined)
|
||||||
befungeObject.btnStart.onclick = function () { if (befungeObject.btnStart.classList.contains('ctrl_btn_disabled')) return; befungeObject.start(); };
|
befungeObject.btnStart.onclick = function () { if (befungeObject.btnStart.classList.contains('ctrl_btn_disabled')) return; befungeObject.start(); };
|
||||||
|
|
||||||
|
if (befungeObject.btnStop !== undefined)
|
||||||
befungeObject.btnStop.onclick = function () { if (befungeObject.btnStop.classList.contains('ctrl_btn_disabled')) return; befungeObject.stop(); };
|
befungeObject.btnStop.onclick = function () { if (befungeObject.btnStop.classList.contains('ctrl_btn_disabled')) return; befungeObject.stop(); };
|
||||||
|
|
||||||
|
if (befungeObject.btnReset !== undefined)
|
||||||
befungeObject.btnReset.onclick = function () { if (befungeObject.btnReset.classList.contains('ctrl_btn_disabled')) return; befungeObject.reset(); };
|
befungeObject.btnReset.onclick = function () { if (befungeObject.btnReset.classList.contains('ctrl_btn_disabled')) return; befungeObject.reset(); };
|
||||||
|
|
||||||
|
if (befungeObject.btnSpeed !== undefined)
|
||||||
befungeObject.btnSpeed.onclick = function () { if (befungeObject.btnSpeed.classList.contains('ctrl_btn_disabled')) return; befungeObject.incSpeed(); };
|
befungeObject.btnSpeed.onclick = function () { if (befungeObject.btnSpeed.classList.contains('ctrl_btn_disabled')) return; befungeObject.incSpeed(); };
|
||||||
|
|
||||||
|
if (befungeObject.btnEdit !== undefined)
|
||||||
|
befungeObject.btnEdit.onclick = function () { if (befungeObject.btnEdit.classList.contains('ctrl_btn_disabled')) return; befungeObject.startEdit(); };
|
||||||
}
|
}
|
||||||
};
|
};
|
@ -1,9 +1,13 @@
|
|||||||
<?php
|
<?php
|
||||||
require_once (__DIR__ . '/../internals/base.php');
|
require_once (__DIR__ . '/../internals/base.php');
|
||||||
|
|
||||||
global $PARAM_CODE;
|
global $PARAM_BEFUNGE93RUNNER;
|
||||||
global $PARAM_URL;
|
|
||||||
global $PARAM_INTERACTIVE;
|
$code = $PARAM_BEFUNGE93RUNNER['code'];
|
||||||
|
$url = $PARAM_BEFUNGE93RUNNER['url'];
|
||||||
|
$interactive = $PARAM_BEFUNGE93RUNNER['interactive'];
|
||||||
|
$initspeed = $PARAM_BEFUNGE93RUNNER['speed'];
|
||||||
|
$editable = $PARAM_BEFUNGE93RUNNER['editable'];
|
||||||
|
|
||||||
function fmtBef($str) {
|
function fmtBef($str) {
|
||||||
$str = htmlspecialchars($str);
|
$str = htmlspecialchars($str);
|
||||||
@ -18,25 +22,31 @@ function fmtBef($str) {
|
|||||||
|
|
||||||
$result = '';
|
$result = '';
|
||||||
|
|
||||||
if ($PARAM_INTERACTIVE) {
|
|
||||||
$result .= '<div class="bce_code b93rnr_base">' . "\n";
|
if ($interactive) {
|
||||||
$result .= ' <div class="bce_code_data b93rnr_data" data-befcode="' . base64_encode($PARAM_CODE) . '">' . fmtBef($PARAM_CODE) . '</div>' . "\n";
|
$speed_attr = '';
|
||||||
|
if (isset($initspeed) && $initspeed != NULL && $initspeed>0) $speed_attr = ' data-b93rnr_initialspeed="'.$initspeed.'" ';
|
||||||
|
$code_attr = '';
|
||||||
|
$code_attr = 'data-b93rnr_code="' . base64_encode($code) . '"';
|
||||||
|
|
||||||
|
$result .= '<div class="bce_code b93rnr_base" ' . $speed_attr . '>' . "\n";
|
||||||
|
$result .= ' <div class="bce_code_data b93rnr_data" '.$code_attr.'>' . fmtBef($code) . '</div>' . "\n";
|
||||||
|
$result .= ' <textarea class="bce_code_editarea b93rnr_editarea generic_collapsed"></textarea>' . "\n";
|
||||||
$result .= ' <div class="bce_code_ctrl">' . "\n";
|
$result .= ' <div class="bce_code_ctrl">' . "\n";
|
||||||
$result .= ' <div class="ctrl_btn_left">' . "\n";
|
$result .= ' <div class="ctrl_btn_left">' . "\n";
|
||||||
$result .= ' <div class="ctrl_btn_group">' . "\n";
|
$result .= ' <div class="ctrl_btn_group">' . "\n";
|
||||||
$result .= ' <div class="ctrl_btn ctrl_btn_ll b93rnr_start">Start</div>' . "\n";
|
$result .= ' <div class="ctrl_btn ctrl_btn_ll b93rnr_start">Start</div>' . "\n";
|
||||||
$result .= ' <div class="ctrl_btn ctrl_btn_rr b93rnr_speed">3+</div>' . "\n";
|
$result .= ' <div class="ctrl_btn ctrl_btn_rr b93rnr_speed">??</div>' . "\n";
|
||||||
$result .= ' </div>' . "\n";
|
$result .= ' </div>' . "\n";
|
||||||
$result .= ' <div class="ctrl_btn b93rnr_pause ctrl_btn_disabled">Pause</div>' . "\n";
|
$result .= ' <div class="ctrl_btn b93rnr_pause ctrl_btn_disabled">Pause</div>' . "\n";
|
||||||
$result .= ' <div class="ctrl_btn b93rnr_reset ctrl_btn_disabled">Reset</div>' . "\n";
|
$result .= ' <div class="ctrl_btn b93rnr_reset ctrl_btn_disabled">Reset</div>' . "\n";
|
||||||
$result .= ' </div>' . "\n";
|
$result .= ' </div>' . "\n";
|
||||||
if ($PARAM_URL !== '') {
|
|
||||||
$result .= ' <div class="ctrl_btn_right">' . "\n";
|
$result .= ' <div class="ctrl_btn_right">' . "\n";
|
||||||
$result .= ' <a class="ctrl_btn" href="' . $PARAM_URL . '" download target="_blank">Download</a>' . "\n";
|
if ($editable && $interactive) $result .= ' <div class="ctrl_btn b93rnr_edit">Edit</div>' . "\n";
|
||||||
|
if ($url !== '') $result .= ' <a class="ctrl_btn" href="' . $url . '" download target="_blank">Download</a>' . "\n";
|
||||||
$result .= ' </div>' . "\n";
|
$result .= ' </div>' . "\n";
|
||||||
}
|
|
||||||
$result .= ' </div>' . "\n";
|
$result .= ' </div>' . "\n";
|
||||||
$result .= ' <div class="bce_code_out b93rnr_outpanel b93rnr_outpanel_hidden">' . "\n";
|
$result .= ' <div class="bce_code_out b93rnr_outpanel generic_collapsed">' . "\n";
|
||||||
$result .= ' <div class="bce_code_out_left">' . "\n";
|
$result .= ' <div class="bce_code_out_left">' . "\n";
|
||||||
$result .= ' <b>Output:</b>' . "\n";
|
$result .= ' <b>Output:</b>' . "\n";
|
||||||
$result .= ' <div class="bce_code_out_text b93rnr_output"></div>' . "\n";
|
$result .= ' <div class="bce_code_out_text b93rnr_output"></div>' . "\n";
|
||||||
@ -53,13 +63,11 @@ if ($PARAM_INTERACTIVE) {
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
$result .= '<div class="bce_code">' . "\n";
|
$result .= '<div class="bce_code">' . "\n";
|
||||||
$result .= ' <div class="bce_code_data">' . fmtBef($PARAM_CODE) . '</div>' . "\n";
|
$result .= ' <div class="bce_code_data">' . fmtBef($code) . '</div>' . "\n";
|
||||||
$result .= ' <div class="bce_code_ctrl">' . "\n";
|
$result .= ' <div class="bce_code_ctrl">' . "\n";
|
||||||
if ($PARAM_URL !== '') {
|
|
||||||
$result .= ' <div class="ctrl_btn_right">' . "\n";
|
$result .= ' <div class="ctrl_btn_right">' . "\n";
|
||||||
$result .= ' <a class="ctrl_btn" href="' . $PARAM_URL . '" download target="_blank">Download</a>' . "\n";
|
if ($url !== '') $result .= ' <a class="ctrl_btn" href="' . $url . '" download target="_blank">Download</a>' . "\n";
|
||||||
$result .= ' </div>' . "\n";
|
$result .= ' </div>' . "\n";
|
||||||
}
|
|
||||||
$result .= ' </div>' . "\n";
|
$result .= ' </div>' . "\n";
|
||||||
$result .= '</div>' . "\n";
|
$result .= '</div>' . "\n";
|
||||||
}
|
}
|
||||||
|
@ -47,12 +47,18 @@ $max = ceil($max / 20) * 20;
|
|||||||
|
|
||||||
<b>Solution:</b>
|
<b>Solution:</b>
|
||||||
<?php
|
<?php
|
||||||
global $PARAM_CODE;
|
global $PARAM_BEFUNGE93RUNNER;
|
||||||
global $PARAM_URL;
|
$PARAM_BEFUNGE93RUNNER =
|
||||||
$PARAM_CODE = file_get_contents($problem['file_code']);
|
[
|
||||||
$PARAM_URL = $problem['url_raw'];
|
'code' => file_get_contents($problem['file_code']),
|
||||||
$PARAM_INTERACTIVE = !$problem['abbreviated'];
|
'url' => $problem['url_raw'],
|
||||||
|
'interactive' => !$problem['abbreviated'],
|
||||||
|
'speed' => null,
|
||||||
|
'editable' => false,
|
||||||
|
];
|
||||||
echo require (__DIR__ . '/../fragments/befunge93_runner.php');
|
echo require (__DIR__ . '/../fragments/befunge93_runner.php');
|
||||||
|
|
||||||
|
if ($problem['abbreviated']) echo '<i>This program is too big to display/execute here, click [download] to get the full program. </i><br/>';
|
||||||
?>
|
?>
|
||||||
<br/>
|
<br/>
|
||||||
|
|
||||||
@ -67,7 +73,7 @@ $max = ceil($max / 20) * 20;
|
|||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td><b>Execution time</b> (<a href="/programs/view/BefunGen">BefunExec</a>):</td>
|
<td><b>Execution time</b> (<a href="/programs/view/BefunGen">BefunExec</a>):</td>
|
||||||
<td><?php echo $problem['time'] . ' ms <i>(=' . number_format(($problem['steps']/$problem['time'])/1000, 2, '.', '') . ' MHz)</i>'; ?></td>
|
<td><?php echo $problem['time'] . ' ms <i>(=' . (($problem['time']===0) ? '?' : number_format(($problem['steps']/$problem['time'])/1000, 2, '.', '')) . ' MHz)</i>'; ?></td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td><b>Program size:</b></td>
|
<td><b>Program size:</b></td>
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
<div id="footerdiv" class="content-responsive">
|
<div id="footerdiv" class="content-responsive">
|
||||||
<hr />
|
<hr />
|
||||||
made with vanilla PHP and MySQL, no frameworks, no bootstrap, no bullshit
|
made with vanilla PHP and MySQL, no frameworks, no bootstrap, no unnecessary javascript
|
||||||
</div>
|
</div>
|
@ -22,15 +22,36 @@ class ParsedownCustom extends ParsedownExtra
|
|||||||
|
|
||||||
$Block['custom'] = false;
|
$Block['custom'] = false;
|
||||||
|
|
||||||
if (isset($Block['element']['text']['attributes']) && in_array('language-befungerunner', $Block['element']['text']['attributes']))
|
if (isset($Block['element']['text']['attributes']))
|
||||||
|
{
|
||||||
|
foreach ($Block['element']['text']['attributes'] as $attr)
|
||||||
|
{
|
||||||
|
$spl = explode('__', $attr);
|
||||||
|
|
||||||
|
if ($spl[0] === 'language-befungerunner')
|
||||||
{
|
{
|
||||||
$Block['element']['handler'] = 'handleBef93';
|
$Block['element']['handler'] = 'handleBef93';
|
||||||
$Block['custom'] = true;
|
$Block['custom'] = true;
|
||||||
|
$Block['element']['text']['b93_speed'] = null;
|
||||||
|
$Block['element']['text']['b93_interactive'] = true;
|
||||||
|
$Block['element']['text']['b93_editable'] = true;
|
||||||
|
|
||||||
|
foreach ($spl as $param)
|
||||||
|
{
|
||||||
|
if (startsWith($param, 'speed-')) $Block['element']['text']['b93_speed'] = intval( substr($param, strlen('speed-')));
|
||||||
|
if (startsWith($param, 'interactive-')) $Block['element']['text']['b93_interactive'] = boolval(substr($param, strlen('interactive-')));
|
||||||
|
if (startsWith($param, 'editable-')) $Block['element']['text']['b93_editable'] = boolval(substr($param, strlen('editable-')));
|
||||||
}
|
}
|
||||||
else if (isset($Block['element']['text']['attributes']) && in_array('language-bfjoustrunner', $Block['element']['text']['attributes']))
|
|
||||||
|
return $Block;
|
||||||
|
}
|
||||||
|
else if ($spl[0] === 'language-bfjoustrunner')
|
||||||
{
|
{
|
||||||
$Block['element']['handler'] = 'handleBFJoust';
|
$Block['element']['handler'] = 'handleBFJoust';
|
||||||
$Block['custom'] = true;
|
$Block['custom'] = true;
|
||||||
|
return $Block;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return $Block;
|
return $Block;
|
||||||
@ -60,14 +81,15 @@ class ParsedownCustom extends ParsedownExtra
|
|||||||
|
|
||||||
protected function handleBef93(array $Element)
|
protected function handleBef93(array $Element)
|
||||||
{
|
{
|
||||||
global $PARAM_CODE;
|
global $PARAM_BEFUNGE93RUNNER;
|
||||||
global $PARAM_URL;
|
$PARAM_BEFUNGE93RUNNER =
|
||||||
global $PARAM_INTERACTIVE;
|
[
|
||||||
|
'code' => $Element['text'],
|
||||||
$PARAM_CODE = $Element['text'];
|
'url' => '',
|
||||||
$PARAM_URL = '';
|
'interactive' => $Element['b93_interactive'],
|
||||||
$PARAM_INTERACTIVE = true;
|
'speed' => $Element['b93_speed'],
|
||||||
|
'editable' => $Element['b93_editable'],
|
||||||
|
];
|
||||||
return require (__DIR__ . '/../fragments/befunge93_runner.php');
|
return require (__DIR__ . '/../fragments/befunge93_runner.php');
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -26,6 +26,7 @@ class Blog
|
|||||||
[ 'id' => 8, 'date' => '2014-11-05', 'visible' => true, 'title' => 'Rapla Enhancement Script', 'fragment' => 'rapla_css.md', 'type' => 'markdown', 'cat' => 'blog' ],
|
[ 'id' => 8, 'date' => '2014-11-05', 'visible' => true, 'title' => 'Rapla Enhancement Script', 'fragment' => 'rapla_css.md', 'type' => 'markdown', 'cat' => 'blog' ],
|
||||||
[ 'id' => 20, 'date' => '2015-01-09', 'visible' => true, 'title' => 'More Befunge with Project Euler', 'fragment' => 'more_euler.md', 'type' => 'markdown', 'cat' => 'log' ],
|
[ 'id' => 20, 'date' => '2015-01-09', 'visible' => true, 'title' => 'More Befunge with Project Euler', 'fragment' => 'more_euler.md', 'type' => 'markdown', 'cat' => 'log' ],
|
||||||
[ 'id' => 9, 'date' => '2016-10-22', 'visible' => true, 'title' => 'A complete sudoku solver in Befunge-93', 'fragment' => 'sudoku_befunge.md', 'type' => 'markdown', 'cat' => 'blog' ],
|
[ 'id' => 9, 'date' => '2016-10-22', 'visible' => true, 'title' => 'A complete sudoku solver in Befunge-93', 'fragment' => 'sudoku_befunge.md', 'type' => 'markdown', 'cat' => 'blog' ],
|
||||||
|
[ 'id' => 21, 'date' => '2018-01-02', 'visible' => true, 'title' => 'A simple javascript befunge-93 runner', 'fragment' => 'js_befrunner.md', 'type' => 'markdown', 'cat' => 'blog' ],
|
||||||
];
|
];
|
||||||
|
|
||||||
return array_map('self::completeSingle', $all);
|
return array_map('self::completeSingle', $all);
|
||||||
|
41
www/statics/blog/js_befrunner.md
Normal file
41
www/statics/blog/js_befrunner.md
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
Primarily for my [project euler solutions](/blog/1/Project_Euler_with_Befunge) I wrote a small
|
||||||
|
javascript befunge-93 runner (without befunge93 size restrictions, as with most stuff on this site).
|
||||||
|
|
||||||
|
The code is note really optimized and will only run on newer browsers, but it's good enough to play a bit around.
|
||||||
|
|
||||||
|
Press **[Start]** to run the code, **[Edit]** to change the code and change the interpreter speed with the button on the right side of the **[Start]** button.
|
||||||
|
|
||||||
|
|
||||||
|
~~~befungerunner__speed-2
|
||||||
|
0".omed s"v
|
||||||
|
" >v
|
||||||
|
i 8
|
||||||
|
4
|
||||||
|
s > > ^*
|
||||||
|
i >99+0g1+#^_77+0g#^_188+0p099+0p> v
|
||||||
|
h ^ < # <
|
||||||
|
T >88+0g1+#^_66+0g#^_088+0p01-99+0p^
|
||||||
|
" ^ < <# #<
|
||||||
|
> v >99+0g1-#^_77+0g8-#^_01-88+0p099+0p^
|
||||||
|
| >#:>#,< ^ < <# <2
|
||||||
|
>88+0g1-#^_66+0g8-#^_088+0p199+0p^2
|
||||||
|
>0>:"#"\0p:5 v ^ $ g
|
||||||
|
v_^#!\+1\!`+4< ^p0+77+g0+99g0+77< >66+0g1+v v
|
||||||
|
>1-:"#"\v >66+0g88+0g+66+0p^ v+1g0+77< 8
|
||||||
|
|`0:p+19< ^ g 4
|
||||||
|
>:"#"\0\p:v> ^< - *
|
||||||
|
|\+1\!`+45<^p0+< v" "_"@"v -
|
||||||
|
>1-:"#"\ v>p099^^ < >66+v+66< #
|
||||||
|
|`0:p\+19<^0+88<^ p+1g0+77+1g0< >" " #< v
|
||||||
|
$>-66+0p077+0p1^ vp+2g0+67+2g0+56 < pp0+67:0+560<|#<
|
||||||
|
01 : # v p0 +76+1g< >"#" #< ^
|
||||||
|
>^ >65+0g6- #v_01-65+0p67+0^
|
||||||
|
^ $ <>76+0gv#
|
||||||
|
^ <> 7-v
|
||||||
|
^_v#!<
|
||||||
|
#
|
||||||
|
>+56+0p^
|
||||||
|
^1g0+56<
|
||||||
|
~~~
|
||||||
|
|
||||||
|
You can find the code either directly by looking at the file *blogpost_bef93runner.js* on this site, or on [github](https://github.com/Mikescher/www.mikescher.com).
|
@ -1 +1,3 @@
|
|||||||
These kinds of problems are fun in Befunge because you can just copy the input into your program and it becomes a part of your source code.
|
These kinds of problems are fun in Befunge because you can just copy the input into your program and it becomes a part of your source code.
|
||||||
|
|
||||||
|
The rest is just walking through all possible values and printing the largest
|
Loading…
Reference in New Issue
Block a user