const windowSize: { width?: number; height?: number } = {}; const updateWindowSize = () => { const size = require('window-size')?.get(); windowSize.width = size?.width; windowSize.height = size?.height; }; process.stdout.on('resize', updateWindowSize); export = (stream: NodeJS.WriteStream = process.stdout) => { // make sure we get initial metrics updateWindowSize(); const currentWindowSize = () => { // always return a copy. // width/height can be undefined if no TTY. return { width: windowSize.width, height: windowSize.height, }; }; const hideCursor = () => stream.write('\u001B[?25l'); const showCursor = () => stream.write('\u001B[?25h'); const cursorUp = (rows: number = 0) => stream.write(`\u001B[${rows}A`); const cursorDown = (rows: number = 0) => stream.write(`\u001B[${rows}B`); const cursorHidden = () => { const Bluebird = require('bluebird') as typeof import('bluebird'); return Bluebird.try(hideCursor).disposer(() => { showCursor(); }); }; const write = (str: string) => stream.write(str); const writeLine = (str: string) => stream.write(`${str}\n`); const clearLine = () => stream.write('\u001B[2K\r'); const replaceLine = (str: string) => { clearLine(); return write(str); }; const deleteToEnd = () => stream.write('\u001b[0J'); return { stream, currentWindowSize, hideCursor, showCursor, cursorHidden, cursorUp, cursorDown, write, writeLine, clearLine, replaceLine, deleteToEnd, }; };