@visulima/colorize
Version:
Terminal and Console string styling done right.
267 lines (255 loc) • 10.2 kB
JavaScript
Object.defineProperties(exports, { __esModule: { value: true }, [Symbol.toStringTag]: { value: 'Module' } });
const isAnsiColorSupported = require('@visulima/is-ansi-color-supported');
var __defProp$6 = Object.defineProperty;
var __name$6 = (target, value) => __defProp$6(target, "name", { value, configurable: true });
function ansiRegex({ onlyFirst = false } = {}) {
const ST = "(?:\\u0007|\\u001B\\u005C|\\u009C)";
const pattern = [
`[\\u001B\\u009B][[\\]()#;?]*(?:(?:(?:(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]+)*|[a-zA-Z\\d]+(?:;[-a-zA-Z\\d\\/#&.:=?%@~_]*)*)?${ST})`,
"(?:(?:\\d{1,4}(?:;\\d{0,4})*)?[\\dA-PR-TZcf-nq-uy=><~]))"
].join("|");
return new RegExp(pattern, onlyFirst ? void 0 : "g");
}
__name$6(ansiRegex, "ansiRegex");
var __defProp$5 = Object.defineProperty;
var __name$5 = (target, value) => __defProp$5(target, "name", { value, configurable: true });
const clamp = /* @__PURE__ */ __name$5((number_, min, max) => min > number_ ? min : number_ > max ? max : number_, "clamp");
var __defProp$4 = Object.defineProperty;
var __name$4 = (target, value) => __defProp$4(target, "name", { value, configurable: true });
const convertHexToRgb = /* @__PURE__ */ __name$4((hex) => {
let [, color] = /([a-f\d]{3,6})/i.exec(hex) ?? [];
const length_ = color ? color.length : 0;
if (length_ === 3) {
color = color[0] + color[0] + color[1] + color[1] + color[2] + color[2];
} else if (length_ !== 6) {
return [0, 0, 0];
}
const number_ = Number.parseInt(color, 16);
return [number_ >> 16 & 255, number_ >> 8 & 255, number_ & 255];
}, "convertHexToRgb");
var __defProp$3 = Object.defineProperty;
var __name$3 = (target, value) => __defProp$3(target, "name", { value, configurable: true });
const rgbToAnsi256 = /* @__PURE__ */ __name$3((r, g, b) => {
if (r === g && g === b) {
if (r < 8) {
return 16;
}
if (r > 248) {
return 231;
}
return Math.round((r - 8) / 247 * 24) + 232;
}
return 16 + // r / 255 * 5 => r / 51
36 * Math.round(r / 51) + 6 * Math.round(g / 51) + Math.round(b / 51);
}, "rgbToAnsi256");
const ansi256To16 = /* @__PURE__ */ __name$3((code) => {
let r;
let g;
let b;
if (code < 8) {
return 30 + code;
}
if (code < 16) {
return 90 + (code - 8);
}
if (code >= 232) {
r = g = b = ((code - 232) * 10 + 8) / 255;
} else {
code -= 16;
const remainder = code % 36;
r = Math.floor(code / 36) / 5;
g = Math.floor(remainder / 6) / 5;
b = remainder % 6 / 5;
}
const value = Math.max(r, g, b) * 2;
if (value === 0) {
return 30;
}
const code16 = 30 + (Math.round(b) << 2 | Math.round(g) << 1 | Math.round(r));
return value === 2 ? code16 + 60 : code16;
}, "ansi256To16");
const rgbToAnsi16 = /* @__PURE__ */ __name$3((r, g, b) => ansi256To16(rgbToAnsi256(r, g, b)), "rgbToAnsi16");
var __defProp$2 = Object.defineProperty;
var __name$2 = (target, value) => __defProp$2(target, "name", { value, configurable: true });
const closeCode = 39;
const bgCloseCode = 49;
const bgOffset = 10;
const supportedColor = isAnsiColorSupported.isStdoutColorSupported();
const mono = { close: "", open: "" };
const esc = supportedColor > 0 ? (open, close) => {
return { close: "\x1B[" + close + "m", open: "\x1B[" + open + "m" };
} : () => mono;
const createRgbFunction = /* @__PURE__ */ __name$2((function_) => (r, g, b) => function_(rgbToAnsi256(Number(r), Number(g), Number(b))), "createRgbFunction");
const createHexFunction = /* @__PURE__ */ __name$2((function_) => (hex) => {
const [r, g, b] = convertHexToRgb(hex);
return function_(r, g, b);
}, "createHexFunction");
let createAnsi256 = /* @__PURE__ */ __name$2((code) => esc("38;5;" + code, closeCode), "createAnsi256");
let createBgAnsi256 = /* @__PURE__ */ __name$2((code) => esc("48;5;" + code, bgCloseCode), "createBgAnsi256");
let createRgb = /* @__PURE__ */ __name$2((r, g, b) => esc("38;2;" + r + ";" + g + ";" + b, closeCode), "createRgb");
let createBgRgb = /* @__PURE__ */ __name$2((r, g, b) => esc("48;2;" + r + ";" + g + ";" + b, bgCloseCode), "createBgRgb");
if (supportedColor === 1) {
createAnsi256 = /* @__PURE__ */ __name$2((code) => esc(ansi256To16(Number(code)), closeCode), "createAnsi256");
createBgAnsi256 = /* @__PURE__ */ __name$2((code) => esc(ansi256To16(Number(code)) + bgOffset, bgCloseCode), "createBgAnsi256");
createRgb = /* @__PURE__ */ __name$2((r, g, b) => esc(rgbToAnsi16(Number(r), Number(g), Number(b)), closeCode), "createRgb");
createBgRgb = /* @__PURE__ */ __name$2((r, g, b) => esc(rgbToAnsi16(Number(r), Number(g), Number(b)) + bgOffset, bgCloseCode), "createBgRgb");
} else if (supportedColor === 2) {
createRgb = createRgbFunction(createAnsi256);
createBgRgb = createRgbFunction(createBgAnsi256);
}
const baseStyles = {
// 21 isn't widely supported and 22 does the same thing
bold: esc(1, 22),
dim: esc(2, 22),
hidden: esc(8, 28),
inverse: esc(7, 27),
italic: esc(3, 23),
overline: esc(53, 55),
reset: esc(0, 0),
strike: esc(9, 29),
// alias for strikethrough
strikethrough: esc(9, 29),
underline: esc(4, 24),
visible: mono
};
const baseColors = {
bgBlack: esc(40, bgCloseCode),
bgBlackBright: esc(100, bgCloseCode),
bgBlue: esc(44, bgCloseCode),
bgBlueBright: esc(104, bgCloseCode),
bgCyan: esc(46, bgCloseCode),
bgCyanBright: esc(106, bgCloseCode),
bgGray: esc(100, bgCloseCode),
// US spelling alias for bgBlackBright
bgGreen: esc(42, bgCloseCode),
bgGreenBright: esc(102, bgCloseCode),
bgGrey: esc(100, bgCloseCode),
// UK spelling alias for bgBlackBright
bgMagenta: esc(45, bgCloseCode),
bgMagentaBright: esc(105, bgCloseCode),
bgRed: esc(41, bgCloseCode),
bgRedBright: esc(101, bgCloseCode),
bgWhite: esc(47, bgCloseCode),
bgWhiteBright: esc(107, bgCloseCode),
bgYellow: esc(43, bgCloseCode),
bgYellowBright: esc(103, bgCloseCode),
black: esc(30, closeCode),
blackBright: esc(90, closeCode),
blue: esc(34, closeCode),
blueBright: esc(94, closeCode),
cyan: esc(36, closeCode),
cyanBright: esc(96, closeCode),
gray: esc(90, closeCode),
// US spelling alias for blackBright
green: esc(32, closeCode),
greenBright: esc(92, closeCode),
grey: esc(90, closeCode),
// UK spelling alias for blackBright
magenta: esc(35, closeCode),
magentaBright: esc(95, closeCode),
red: esc(31, closeCode),
redBright: esc(91, closeCode),
white: esc(37, closeCode),
whiteBright: esc(97, closeCode),
yellow: esc(33, closeCode),
yellowBright: esc(93, closeCode)
};
const styleMethods = {
bg: /* @__PURE__ */ __name$2((code) => createBgAnsi256(clamp(code, 0, 255)), "bg"),
bgHex: createHexFunction(createBgRgb),
bgRgb: /* @__PURE__ */ __name$2((r, g, b) => createBgRgb(clamp(r, 0, 255), clamp(g, 0, 255), clamp(b, 0, 255)), "bgRgb"),
fg: /* @__PURE__ */ __name$2((code) => createAnsi256(clamp(code, 0, 255)), "fg"),
hex: createHexFunction(createRgb),
rgb: /* @__PURE__ */ __name$2((r, g, b) => createRgb(clamp(r, 0, 255), clamp(g, 0, 255), clamp(b, 0, 255)), "rgb")
};
var __defProp$1 = Object.defineProperty;
var __name$1 = (target, value) => __defProp$1(target, "name", { value, configurable: true });
const stringReplaceAll = /* @__PURE__ */ __name$1((string_, searchValue, replaceValue) => {
if (searchValue === "") {
return string_;
}
let pos = string_.indexOf(searchValue);
if (pos < 0) {
return string_;
}
const substringLength = searchValue.length;
let lastPos = 0;
let result = "";
while (~pos) {
result += string_.slice(lastPos, pos) + replaceValue;
lastPos = pos + substringLength;
pos = string_.indexOf(searchValue, lastPos);
}
return result + string_.slice(lastPos);
}, "stringReplaceAll");
var __defProp = Object.defineProperty;
var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
const styles = {};
let stylePrototype = null;
const wrapText = /* @__PURE__ */ __name((strings, values, properties) => {
if (!strings) {
return "";
}
let string = strings.raw == null ? strings + "" : String.raw(strings, ...values);
if (string.includes("\x1B")) {
for (let currentProperties = properties; currentProperties; currentProperties = currentProperties.props) {
string = stringReplaceAll(string, currentProperties.close, currentProperties.open);
}
}
if (string.includes("\n")) {
string = string.replace(/(\r*\n)/g, properties.closeStack + "$1" + properties.openStack);
}
return properties.openStack + string + properties.closeStack;
}, "wrapText");
const createStyle = /* @__PURE__ */ __name(({ props }, { close, open }) => {
const openStack = (props?.openStack ?? "") + open;
const closeStack = close + (props?.closeStack ?? "");
const style = /* @__PURE__ */ __name((strings, ...values) => wrapText(strings, values, style.props), "style");
Object.setPrototypeOf(style, stylePrototype);
style.props = { close, closeStack, open, openStack, props };
style.open = openStack;
style.close = closeStack;
return style;
}, "createStyle");
const Colorize$1 = /* @__PURE__ */ __name(function() {
const self = /* @__PURE__ */ __name((string_) => string_ + "", "self");
self.strip = (value) => value.replaceAll(ansiRegex(), "");
for (const name in baseColors) {
styles[name] = {
get() {
const style = createStyle(this, baseColors[name]);
Object.defineProperty(this, name, { value: style });
return style;
}
};
}
for (const name in baseStyles) {
styles[name] = {
get() {
const style = createStyle(this, baseStyles[name]);
Object.defineProperty(this, name, { value: style });
return style;
}
};
}
stylePrototype = Object.defineProperties({}, styles);
Object.setPrototypeOf(self, stylePrototype);
return self;
}, "Colorize");
for (const name in styleMethods) {
styles[name] = {
get() {
return (...arguments_) => (
// @ts-expect-error: TODO: fix typing of `arguments_`
createStyle(this, styleMethods[name](...arguments_))
);
}
};
}
styles.ansi256 = styles.fg;
styles.bgAnsi256 = styles.bg;
const colorize = new Colorize$1();
const Colorize = Colorize$1;
module.exports = colorize;
module.exports.Colorize = Colorize;
;