mirror of
https://github.com/coding-horror/basic-computer-games.git
synced 2025-12-22 07:10:42 -08:00
130 lines
4.1 KiB
HTML
130 lines
4.1 KiB
HTML
<html>
|
|
<head>
|
|
<title>Minimal node.js terminal</title>
|
|
<meta name="viewport" content="width=640, initial-scale=1">
|
|
<link
|
|
rel="stylesheet"
|
|
href="../../../00_Utilities/javascript/style_terminal.css"
|
|
/>
|
|
<link rel="stylesheet" href="HtmlTerminal.css" />
|
|
<style>
|
|
header {
|
|
position: sticky;
|
|
top: 0;
|
|
left: 0;
|
|
right: 0;
|
|
border-bottom: 1px solid var(--text);
|
|
padding: 0.25rem 0.5rem;
|
|
margin: 0;
|
|
margin-bottom: 1rem;
|
|
background: black;
|
|
display: flex;
|
|
justify-content: space-between;
|
|
}
|
|
header h1 {
|
|
font-size: small;
|
|
color: var(--text),
|
|
}
|
|
header div {
|
|
font-size: small;
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<header>
|
|
<h1><a href="../../../">BASIC Computer Games</a></h1>
|
|
</header>
|
|
<main id="output"></main>
|
|
<script src="HtmlTerminal.js" type="text/javascript"></script>
|
|
<script>
|
|
const $output = document.getElementById("output");
|
|
const term = new HtmlTerminal($output);
|
|
|
|
function getGameScriptFromHash() {
|
|
const hash = window.location.hash;
|
|
|
|
// if no game-script was provided redirect to the overview.
|
|
if (!hash) {
|
|
// show error message and link back to the index.html
|
|
console.debug("[HtmlTerminal] No game script found!");
|
|
term.writeln(`no game script found :-(\n`);
|
|
term.inserHtml(`<a href="/">>> Back to game overview!</a>`);
|
|
return;
|
|
}
|
|
|
|
// remove the hash
|
|
const gameFile = hash.replace("#", "");
|
|
return gameFile;
|
|
}
|
|
|
|
function addGitHubLink(gameFile) {
|
|
const gameFolder = gameFile.split("/")[0];
|
|
|
|
$gitHubLink = document.createElement("a");
|
|
$gitHubLink.href = `https://github.com/coding-horror/basic-computer-games/tree/main/${gameFolder}`;
|
|
$gitHubLink.innerText = `show source-code`;
|
|
|
|
var $gitHubBanner = document.createElement("div");
|
|
$gitHubBanner.classList.add("githublink");
|
|
$gitHubBanner.appendChild($gitHubLink);
|
|
|
|
const $header = document.getElementsByTagName('header')[0];
|
|
$header.append($gitHubBanner);
|
|
}
|
|
|
|
function loadGameScript(gameFile) {
|
|
// clear terminal
|
|
term.clear();
|
|
|
|
// load game-script
|
|
console.debug("[HtmlTerminal] Game script found: ", gameFile);
|
|
const gameScript = `../../../${gameFile}`;
|
|
var $scriptTag = document.createElement("script");
|
|
$scriptTag.async = "async";
|
|
$scriptTag.type = "module";
|
|
$scriptTag.src = gameScript;
|
|
$scriptTag.onerror = () => {
|
|
term.clear();
|
|
term.writeln(`Error loading game-script "${gameFile}" :-(\n`);
|
|
term.inserHtml(`<a href="/">>> Back to game overview!</a>`);
|
|
};
|
|
$scriptTag.addEventListener("load", function () {
|
|
console.log("[HtmlTerminal] Game script loaded!");
|
|
});
|
|
document.body.append($scriptTag);
|
|
}
|
|
|
|
/**
|
|
* Determine how much chars will fit in each terminal line.
|
|
*/
|
|
function getOutputColumns($element) {
|
|
|
|
const fontWidth = 10; //TODO: this width could be measured but it may be complicated!
|
|
const columnWidth = Math.trunc($element.clientWidth / fontWidth);
|
|
console.warn(`[terminal] document.body.clientWidth:${$element.clientWidth} fontsize:${fontWidth} columnWidth:${columnWidth}`);
|
|
return columnWidth;
|
|
}
|
|
|
|
/* Redirect stdin/stdout to the HtmlTerminal.
|
|
* This is VERY hacky and should never be done in a serious project!
|
|
* We can use this here because we know what we are doing and...
|
|
* ...it's just simple games ;-) */
|
|
window.process = {
|
|
stdout: {
|
|
write: (t) => term.write(t),
|
|
columns: getOutputColumns($output)
|
|
},
|
|
stdin: {
|
|
on: (event, callback) => term.input(callback),
|
|
},
|
|
exit: (code) => {},
|
|
};
|
|
|
|
// let's play 🚀
|
|
const gameFile = getGameScriptFromHash();
|
|
addGitHubLink(gameFile);
|
|
loadGameScript(gameFile);
|
|
</script>
|
|
</body>
|
|
</html>
|