All files / lib/internal/readline callbacks.js

100% Statements 132/132
100% Branches 57/57
100% Functions 4/4
100% Lines 132/132

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 1332x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 2x 1137x 1137x 4x 4x 1136x 1137x 1x 1x 1x 1136x 1137x 1137x 1133x 1137x 44x 44x 44x 1089x 1103x 1088x 1137x 1137x 1137x 2x 2x 2x 2x 2x 966x 966x 12x 12x 965x 966x 598x 598x 598x 367x 367x 367x 795x 47x 795x 33x 33x 367x 794x 204x 795x 91x 91x 367x 367x 966x 2x 2x 2x 2x 2x 2x 2x 2x 152x 152x 4x 4x 151x 152x 4x 4x 4x 147x 147x 152x 152x 152x 2x 2x 2x 2x 2x 466x 466x 4x 4x 465x 466x 21x 21x 21x 444x 444x 466x 2x 2x 2x 2x 2x 2x 2x  
'use strict';
 
const {
  NumberIsNaN,
} = primordials;
 
const {
  codes: {
    ERR_INVALID_ARG_VALUE,
    ERR_INVALID_CURSOR_POS,
  },
} = require('internal/errors');
 
const {
  validateCallback,
} = require('internal/validators');
const {
  CSI,
} = require('internal/readline/utils');
 
const {
  kClearLine,
  kClearScreenDown,
  kClearToLineBeginning,
  kClearToLineEnd,
} = CSI;
 
 
/**
 * moves the cursor to the x and y coordinate on the given stream
 */
 
function cursorTo(stream, x, y, callback) {
  if (callback !== undefined) {
    validateCallback(callback);
  }
 
  if (typeof y === 'function') {
    callback = y;
    y = undefined;
  }
 
  if (NumberIsNaN(x)) throw new ERR_INVALID_ARG_VALUE('x', x);
  if (NumberIsNaN(y)) throw new ERR_INVALID_ARG_VALUE('y', y);
 
  if (stream == null || (typeof x !== 'number' && typeof y !== 'number')) {
    if (typeof callback === 'function') process.nextTick(callback, null);
    return true;
  }
 
  if (typeof x !== 'number') throw new ERR_INVALID_CURSOR_POS();
 
  const data = typeof y !== 'number' ? CSI`${x + 1}G` : CSI`${y + 1};${x + 1}H`;
  return stream.write(data, callback);
}
 
/**
 * moves the cursor relative to its current location
 */
 
function moveCursor(stream, dx, dy, callback) {
  if (callback !== undefined) {
    validateCallback(callback);
  }
 
  if (stream == null || !(dx || dy)) {
    if (typeof callback === 'function') process.nextTick(callback, null);
    return true;
  }
 
  let data = '';
 
  if (dx < 0) {
    data += CSI`${-dx}D`;
  } else if (dx > 0) {
    data += CSI`${dx}C`;
  }
 
  if (dy < 0) {
    data += CSI`${-dy}A`;
  } else if (dy > 0) {
    data += CSI`${dy}B`;
  }
 
  return stream.write(data, callback);
}
 
/**
 * clears the current line the cursor is on:
 *   -1 for left of the cursor
 *   +1 for right of the cursor
 *    0 for the entire line
 */
 
function clearLine(stream, dir, callback) {
  if (callback !== undefined) {
    validateCallback(callback);
  }
 
  if (stream === null || stream === undefined) {
    if (typeof callback === 'function') process.nextTick(callback, null);
    return true;
  }
 
  const type =
    dir < 0 ? kClearToLineBeginning : dir > 0 ? kClearToLineEnd : kClearLine;
  return stream.write(type, callback);
}
 
/**
 * clears the screen from the current position of the cursor down
 */
 
function clearScreenDown(stream, callback) {
  if (callback !== undefined) {
    validateCallback(callback);
  }
 
  if (stream === null || stream === undefined) {
    if (typeof callback === 'function') process.nextTick(callback, null);
    return true;
  }
 
  return stream.write(kClearScreenDown, callback);
}
 
module.exports = {
  clearLine,
  clearScreenDown,
  cursorTo,
  moveCursor,
};