diff options
Diffstat (limited to 'js/ansi/newlines.js')
-rw-r--r-- | js/ansi/newlines.js | 71 |
1 files changed, 71 insertions, 0 deletions
diff --git a/js/ansi/newlines.js b/js/ansi/newlines.js new file mode 100644 index 0000000..4e37a0a --- /dev/null +++ b/js/ansi/newlines.js @@ -0,0 +1,71 @@ + +/** + * Accepts any node Stream instance and hijacks its "write()" function, + * so that it can count any newlines that get written to the output. + * + * When a '\n' byte is encountered, then a "newline" event will be emitted + * on the stream, with no arguments. It is up to the listeners to determine + * any necessary deltas required for their use-case. + * + * Ex: + * + * var cursor = ansi(process.stdout) + * , ln = 0 + * process.stdout.on('newline', function () { + * ln++ + * }) + */ + +/** + * Module dependencies. + */ + +var assert = require('assert') +var NEWLINE = '\n'.charCodeAt(0) + +function emitNewlineEvents (stream) { + if (stream._emittingNewlines) { + // already emitting newline events + return + } + + var write = stream.write + + stream.write = function (data) { + // first write the data + var rtn = write.apply(stream, arguments) + + if (stream.listeners('newline').length > 0) { + var len = data.length + , i = 0 + // now try to calculate any deltas + if (typeof data == 'string') { + for (; i<len; i++) { + processByte(stream, data.charCodeAt(i)) + } + } else { + // buffer + for (; i<len; i++) { + processByte(stream, data[i]) + } + } + } + + return rtn + } + + stream._emittingNewlines = true +} +module.exports = emitNewlineEvents + + +/** + * Processes an individual byte being written to a stream + */ + +function processByte (stream, b) { + assert.equal(typeof b, 'number') + if (b === NEWLINE) { + stream.emit('newline') + } +} |