diff options
Diffstat (limited to 'keyboard.js')
-rw-r--r-- | keyboard.js | 70 |
1 files changed, 70 insertions, 0 deletions
diff --git a/keyboard.js b/keyboard.js new file mode 100644 index 0000000..e1101d8 --- /dev/null +++ b/keyboard.js @@ -0,0 +1,70 @@ +module.exports = {}; + +let inputBuffer = ""; +let initialised = false, haveEOF = false; +let waitQueue = []; + +function stdinDataListener(data) { + data = data.toString(); + inputBuffer += data; + + if (waitQueue.length == 0) return; + + const idx = inputBuffer.indexOf("\n"); + if (idx == -1) return; + + waitQueue.shift()[0](inputBuffer.slice(0, idx)); + inputBuffer = inputBuffer.slice(idx + 1); +} + +function stdinEndListener() { + haveEOF = true; + for (const [resolve, reject] of waitQueue) { + reject("End-of-file reached"); + } + waitQueue = []; +} + +function init() { + process.stdin.on("data", stdinDataListener); + process.stdin.on("end", stdinEndListener); + initialised = true; +} +module.exports.init = init; + +function end() { + process.stdin.removeListener("data", stdinDataListener); + process.stdin.removeListener("end", stdinEndListener); + process.stdin.end(); +} +module.exports.end = end; + +function getline() { + return new Promise((resolve, reject) => { + if (haveEOF) { + reject("End-of-file reached"); + return; + } + + const idx = inputBuffer.indexOf("\n"); + if (idx != -1) { + const line = inputBuffer.slice(0, idx); + inputBuffer = inputBuffer.slice(idx + 1); + resolve(line); + } else { + waitQueue.push([resolve, reject]); + } + }); +} +module.exports.getline = getline; + +async function prompt(str) { + process.stdout.write(str); + return await getline(); +} +module.exports.prompt = prompt; + +function eof() { + return haveEOF; +} +module.exports.eof = eof; |