mirror of
https://github.com/sern-handler/website
synced 2026-06-27 18:22:22 +00:00
feat: migrate to starlight
This commit is contained in:
267
node_modules/boxen/index.d.ts
generated
vendored
Normal file
267
node_modules/boxen/index.d.ts
generated
vendored
Normal file
@@ -0,0 +1,267 @@
|
||||
import {type LiteralUnion} from 'type-fest';
|
||||
import {type BoxStyle, type Boxes as CLIBoxes} from 'cli-boxes';
|
||||
|
||||
/**
|
||||
All box styles.
|
||||
*/
|
||||
type Boxes = {
|
||||
readonly none: BoxStyle;
|
||||
} & CLIBoxes;
|
||||
|
||||
/**
|
||||
Characters used for custom border.
|
||||
|
||||
@example
|
||||
```
|
||||
// attttb
|
||||
// l r
|
||||
// dbbbbc
|
||||
|
||||
const border: CustomBorderStyle = {
|
||||
topLeft: 'a',
|
||||
topRight: 'b',
|
||||
bottomRight: 'c',
|
||||
bottomLeft: 'd',
|
||||
left: 'l',
|
||||
right: 'r',
|
||||
top: 't',
|
||||
bottom: 'b',
|
||||
};
|
||||
```
|
||||
*/
|
||||
export type CustomBorderStyle = {
|
||||
/**
|
||||
@deprecated Use `top` and `bottom` instead.
|
||||
*/
|
||||
horizontal?: string;
|
||||
|
||||
/**
|
||||
@deprecated Use `left` and `right` instead.
|
||||
*/
|
||||
vertical?: string;
|
||||
} & BoxStyle;
|
||||
|
||||
/**
|
||||
Spacing used for `padding` and `margin`.
|
||||
*/
|
||||
export type Spacing = {
|
||||
readonly top?: number;
|
||||
readonly right?: number;
|
||||
readonly bottom?: number;
|
||||
readonly left?: number;
|
||||
};
|
||||
|
||||
export type Options = {
|
||||
/**
|
||||
Color of the box border.
|
||||
*/
|
||||
readonly borderColor?: LiteralUnion<
|
||||
| 'black'
|
||||
| 'red'
|
||||
| 'green'
|
||||
| 'yellow'
|
||||
| 'blue'
|
||||
| 'magenta'
|
||||
| 'cyan'
|
||||
| 'white'
|
||||
| 'gray'
|
||||
| 'grey'
|
||||
| 'blackBright'
|
||||
| 'redBright'
|
||||
| 'greenBright'
|
||||
| 'yellowBright'
|
||||
| 'blueBright'
|
||||
| 'magentaBright'
|
||||
| 'cyanBright'
|
||||
| 'whiteBright',
|
||||
string
|
||||
>;
|
||||
|
||||
/**
|
||||
Style of the box border.
|
||||
|
||||
@default 'single'
|
||||
*/
|
||||
readonly borderStyle?: keyof Boxes | CustomBorderStyle;
|
||||
|
||||
/**
|
||||
Reduce opacity of the border.
|
||||
|
||||
@default false
|
||||
*/
|
||||
readonly dimBorder?: boolean;
|
||||
|
||||
/**
|
||||
Space between the text and box border.
|
||||
|
||||
@default 0
|
||||
*/
|
||||
readonly padding?: number | Spacing;
|
||||
|
||||
/**
|
||||
Space around the box.
|
||||
|
||||
@default 0
|
||||
*/
|
||||
readonly margin?: number | Spacing;
|
||||
|
||||
/**
|
||||
Float the box on the available terminal screen space.
|
||||
|
||||
@default 'left'
|
||||
*/
|
||||
readonly float?: 'left' | 'right' | 'center';
|
||||
|
||||
/**
|
||||
Color of the background.
|
||||
*/
|
||||
readonly backgroundColor?: LiteralUnion<
|
||||
| 'black'
|
||||
| 'red'
|
||||
| 'green'
|
||||
| 'yellow'
|
||||
| 'blue'
|
||||
| 'magenta'
|
||||
| 'cyan'
|
||||
| 'white'
|
||||
| 'blackBright'
|
||||
| 'redBright'
|
||||
| 'greenBright'
|
||||
| 'yellowBright'
|
||||
| 'blueBright'
|
||||
| 'magentaBright'
|
||||
| 'cyanBright'
|
||||
| 'whiteBright',
|
||||
string
|
||||
>;
|
||||
|
||||
/**
|
||||
Align the text in the box based on the widest line.
|
||||
|
||||
@default 'left'
|
||||
@deprecated Use `textAlignment` instead.
|
||||
*/
|
||||
readonly align?: 'left' | 'right' | 'center';
|
||||
|
||||
/**
|
||||
Align the text in the box based on the widest line.
|
||||
|
||||
@default 'left'
|
||||
*/
|
||||
readonly textAlignment?: 'left' | 'right' | 'center';
|
||||
|
||||
/**
|
||||
Display a title at the top of the box.
|
||||
If needed, the box will horizontally expand to fit the title.
|
||||
|
||||
@example
|
||||
```
|
||||
console.log(boxen('foo bar', {title: 'example'}));
|
||||
// ┌ example ┐
|
||||
// │foo bar │
|
||||
// └─────────┘
|
||||
```
|
||||
*/
|
||||
readonly title?: string;
|
||||
|
||||
/**
|
||||
Align the title in the top bar.
|
||||
|
||||
@default 'left'
|
||||
|
||||
@example
|
||||
```
|
||||
console.log(boxen('foo bar foo bar', {title: 'example', titleAlignment: 'center'}));
|
||||
// ┌─── example ───┐
|
||||
// │foo bar foo bar│
|
||||
// └───────────────┘
|
||||
|
||||
console.log(boxen('foo bar foo bar', {title: 'example', titleAlignment: 'right'}));
|
||||
// ┌────── example ┐
|
||||
// │foo bar foo bar│
|
||||
// └───────────────┘
|
||||
```
|
||||
*/
|
||||
readonly titleAlignment?: 'left' | 'right' | 'center';
|
||||
|
||||
/**
|
||||
Set a fixed width for the box.
|
||||
|
||||
__Note__: This disables terminal overflow handling and may cause the box to look broken if the user's terminal is not wide enough.
|
||||
|
||||
@example
|
||||
```
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('foo bar', {width: 15}));
|
||||
// ┌─────────────┐
|
||||
// │foo bar │
|
||||
// └─────────────┘
|
||||
```
|
||||
*/
|
||||
readonly width?: number;
|
||||
|
||||
/**
|
||||
Set a fixed height for the box.
|
||||
|
||||
__Note__: This option will crop overflowing content.
|
||||
|
||||
@example
|
||||
```
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('foo bar', {height: 5}));
|
||||
// ┌───────┐
|
||||
// │foo bar│
|
||||
// │ │
|
||||
// │ │
|
||||
// └───────┘
|
||||
```
|
||||
*/
|
||||
readonly height?: number;
|
||||
|
||||
/**
|
||||
__boolean__: Whether or not to fit all available space within the terminal.
|
||||
|
||||
__function__: Pass a callback function to control box dimensions.
|
||||
|
||||
@example
|
||||
```
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('foo bar', {
|
||||
fullscreen: (width, height) => [width, height - 1],
|
||||
}));
|
||||
```
|
||||
*/
|
||||
readonly fullscreen?: boolean | ((width: number, height: number) => [width: number, height: number]);
|
||||
};
|
||||
|
||||
/**
|
||||
Creates a box in the terminal.
|
||||
|
||||
@param text - The text inside the box.
|
||||
@returns The box.
|
||||
|
||||
@example
|
||||
```
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('unicorn', {padding: 1}));
|
||||
// ┌─────────────┐
|
||||
// │ │
|
||||
// │ unicorn │
|
||||
// │ │
|
||||
// └─────────────┘
|
||||
|
||||
console.log(boxen('unicorn', {padding: 1, margin: 1, borderStyle: 'double'}));
|
||||
//
|
||||
// ╔═════════════╗
|
||||
// ║ ║
|
||||
// ║ unicorn ║
|
||||
// ║ ║
|
||||
// ╚═════════════╝
|
||||
//
|
||||
```
|
||||
*/
|
||||
export default function boxen(text: string, options?: Options): string;
|
||||
402
node_modules/boxen/index.js
generated
vendored
Normal file
402
node_modules/boxen/index.js
generated
vendored
Normal file
@@ -0,0 +1,402 @@
|
||||
import process from 'node:process';
|
||||
import stringWidth from 'string-width';
|
||||
import chalk from 'chalk';
|
||||
import widestLine from 'widest-line';
|
||||
import cliBoxes from 'cli-boxes';
|
||||
import camelCase from 'camelcase';
|
||||
import ansiAlign from 'ansi-align';
|
||||
import wrapAnsi from 'wrap-ansi';
|
||||
|
||||
const NEWLINE = '\n';
|
||||
const PAD = ' ';
|
||||
const NONE = 'none';
|
||||
|
||||
const terminalColumns = () => {
|
||||
const {env, stdout, stderr} = process;
|
||||
|
||||
if (stdout?.columns) {
|
||||
return stdout.columns;
|
||||
}
|
||||
|
||||
if (stderr?.columns) {
|
||||
return stderr.columns;
|
||||
}
|
||||
|
||||
if (env.COLUMNS) {
|
||||
return Number.parseInt(env.COLUMNS, 10);
|
||||
}
|
||||
|
||||
return 80;
|
||||
};
|
||||
|
||||
const getObject = detail => typeof detail === 'number' ? {
|
||||
top: detail,
|
||||
right: detail * 3,
|
||||
bottom: detail,
|
||||
left: detail * 3,
|
||||
} : {
|
||||
top: 0,
|
||||
right: 0,
|
||||
bottom: 0,
|
||||
left: 0,
|
||||
...detail,
|
||||
};
|
||||
|
||||
const getBorderWidth = borderStyle => borderStyle === NONE ? 0 : 2;
|
||||
|
||||
const getBorderChars = borderStyle => {
|
||||
const sides = [
|
||||
'topLeft',
|
||||
'topRight',
|
||||
'bottomRight',
|
||||
'bottomLeft',
|
||||
'left',
|
||||
'right',
|
||||
'top',
|
||||
'bottom',
|
||||
];
|
||||
|
||||
let characters;
|
||||
|
||||
// Create empty border style
|
||||
if (borderStyle === NONE) {
|
||||
borderStyle = {};
|
||||
for (const side of sides) {
|
||||
borderStyle[side] = '';
|
||||
}
|
||||
}
|
||||
|
||||
if (typeof borderStyle === 'string') {
|
||||
characters = cliBoxes[borderStyle];
|
||||
|
||||
if (!characters) {
|
||||
throw new TypeError(`Invalid border style: ${borderStyle}`);
|
||||
}
|
||||
} else {
|
||||
// Ensure retro-compatibility
|
||||
if (typeof borderStyle?.vertical === 'string') {
|
||||
borderStyle.left = borderStyle.vertical;
|
||||
borderStyle.right = borderStyle.vertical;
|
||||
}
|
||||
|
||||
// Ensure retro-compatibility
|
||||
if (typeof borderStyle?.horizontal === 'string') {
|
||||
borderStyle.top = borderStyle.horizontal;
|
||||
borderStyle.bottom = borderStyle.horizontal;
|
||||
}
|
||||
|
||||
for (const side of sides) {
|
||||
if (borderStyle[side] === null || typeof borderStyle[side] !== 'string') {
|
||||
throw new TypeError(`Invalid border style: ${side}`);
|
||||
}
|
||||
}
|
||||
|
||||
characters = borderStyle;
|
||||
}
|
||||
|
||||
return characters;
|
||||
};
|
||||
|
||||
const makeTitle = (text, horizontal, alignment) => {
|
||||
let title = '';
|
||||
|
||||
const textWidth = stringWidth(text);
|
||||
|
||||
switch (alignment) {
|
||||
case 'left': {
|
||||
title = text + horizontal.slice(textWidth);
|
||||
break;
|
||||
}
|
||||
|
||||
case 'right': {
|
||||
title = horizontal.slice(textWidth) + text;
|
||||
break;
|
||||
}
|
||||
|
||||
default: {
|
||||
horizontal = horizontal.slice(textWidth);
|
||||
|
||||
if (horizontal.length % 2 === 1) { // This is needed in case the length is odd
|
||||
horizontal = horizontal.slice(Math.floor(horizontal.length / 2));
|
||||
title = horizontal.slice(1) + text + horizontal; // We reduce the left part of one character to avoid the bar to go beyond its limit
|
||||
} else {
|
||||
horizontal = horizontal.slice(horizontal.length / 2);
|
||||
title = horizontal + text + horizontal;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return title;
|
||||
};
|
||||
|
||||
const makeContentText = (text, {padding, width, textAlignment, height}) => {
|
||||
text = ansiAlign(text, {align: textAlignment});
|
||||
let lines = text.split(NEWLINE);
|
||||
const textWidth = widestLine(text);
|
||||
|
||||
const max = width - padding.left - padding.right;
|
||||
|
||||
if (textWidth > max) {
|
||||
const newLines = [];
|
||||
for (const line of lines) {
|
||||
const createdLines = wrapAnsi(line, max, {hard: true});
|
||||
const alignedLines = ansiAlign(createdLines, {align: textAlignment});
|
||||
const alignedLinesArray = alignedLines.split('\n');
|
||||
const longestLength = Math.max(...alignedLinesArray.map(s => stringWidth(s)));
|
||||
|
||||
for (const alignedLine of alignedLinesArray) {
|
||||
let paddedLine;
|
||||
switch (textAlignment) {
|
||||
case 'center': {
|
||||
paddedLine = PAD.repeat((max - longestLength) / 2) + alignedLine;
|
||||
break;
|
||||
}
|
||||
|
||||
case 'right': {
|
||||
paddedLine = PAD.repeat(max - longestLength) + alignedLine;
|
||||
break;
|
||||
}
|
||||
|
||||
default: {
|
||||
paddedLine = alignedLine;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
newLines.push(paddedLine);
|
||||
}
|
||||
}
|
||||
|
||||
lines = newLines;
|
||||
}
|
||||
|
||||
if (textAlignment === 'center' && textWidth < max) {
|
||||
lines = lines.map(line => PAD.repeat((max - textWidth) / 2) + line);
|
||||
} else if (textAlignment === 'right' && textWidth < max) {
|
||||
lines = lines.map(line => PAD.repeat(max - textWidth) + line);
|
||||
}
|
||||
|
||||
const paddingLeft = PAD.repeat(padding.left);
|
||||
const paddingRight = PAD.repeat(padding.right);
|
||||
|
||||
lines = lines.map(line => paddingLeft + line + paddingRight);
|
||||
|
||||
lines = lines.map(line => {
|
||||
if (width - stringWidth(line) > 0) {
|
||||
switch (textAlignment) {
|
||||
case 'center': {
|
||||
return line + PAD.repeat(width - stringWidth(line));
|
||||
}
|
||||
|
||||
case 'right': {
|
||||
return line + PAD.repeat(width - stringWidth(line));
|
||||
}
|
||||
|
||||
default: {
|
||||
return line + PAD.repeat(width - stringWidth(line));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return line;
|
||||
});
|
||||
|
||||
if (padding.top > 0) {
|
||||
lines = [...Array.from({length: padding.top}).fill(PAD.repeat(width)), ...lines];
|
||||
}
|
||||
|
||||
if (padding.bottom > 0) {
|
||||
lines = [...lines, ...Array.from({length: padding.bottom}).fill(PAD.repeat(width))];
|
||||
}
|
||||
|
||||
if (height && lines.length > height) {
|
||||
lines = lines.slice(0, height);
|
||||
} else if (height && lines.length < height) {
|
||||
lines = [...lines, ...Array.from({length: height - lines.length}).fill(PAD.repeat(width))];
|
||||
}
|
||||
|
||||
return lines.join(NEWLINE);
|
||||
};
|
||||
|
||||
const boxContent = (content, contentWidth, options) => {
|
||||
const colorizeBorder = border => {
|
||||
const newBorder = options.borderColor ? getColorFn(options.borderColor)(border) : border;
|
||||
return options.dimBorder ? chalk.dim(newBorder) : newBorder;
|
||||
};
|
||||
|
||||
const colorizeContent = content => options.backgroundColor ? getBGColorFn(options.backgroundColor)(content) : content;
|
||||
|
||||
const chars = getBorderChars(options.borderStyle);
|
||||
const columns = terminalColumns();
|
||||
let marginLeft = PAD.repeat(options.margin.left);
|
||||
|
||||
if (options.float === 'center') {
|
||||
const marginWidth = Math.max((columns - contentWidth - getBorderWidth(options.borderStyle)) / 2, 0);
|
||||
marginLeft = PAD.repeat(marginWidth);
|
||||
} else if (options.float === 'right') {
|
||||
const marginWidth = Math.max(columns - contentWidth - options.margin.right - getBorderWidth(options.borderStyle), 0);
|
||||
marginLeft = PAD.repeat(marginWidth);
|
||||
}
|
||||
|
||||
let result = '';
|
||||
|
||||
if (options.margin.top) {
|
||||
result += NEWLINE.repeat(options.margin.top);
|
||||
}
|
||||
|
||||
if (options.borderStyle !== NONE || options.title) {
|
||||
result += colorizeBorder(marginLeft + chars.topLeft + (options.title ? makeTitle(options.title, chars.top.repeat(contentWidth), options.titleAlignment) : chars.top.repeat(contentWidth)) + chars.topRight) + NEWLINE;
|
||||
}
|
||||
|
||||
const lines = content.split(NEWLINE);
|
||||
|
||||
result += lines.map(line => marginLeft + colorizeBorder(chars.left) + colorizeContent(line) + colorizeBorder(chars.right)).join(NEWLINE);
|
||||
|
||||
if (options.borderStyle !== NONE) {
|
||||
result += NEWLINE + colorizeBorder(marginLeft + chars.bottomLeft + chars.bottom.repeat(contentWidth) + chars.bottomRight);
|
||||
}
|
||||
|
||||
if (options.margin.bottom) {
|
||||
result += NEWLINE.repeat(options.margin.bottom);
|
||||
}
|
||||
|
||||
return result;
|
||||
};
|
||||
|
||||
const sanitizeOptions = options => {
|
||||
// If fullscreen is enabled, max-out unspecified width/height
|
||||
if (options.fullscreen && process?.stdout) {
|
||||
let newDimensions = [process.stdout.columns, process.stdout.rows];
|
||||
|
||||
if (typeof options.fullscreen === 'function') {
|
||||
newDimensions = options.fullscreen(...newDimensions);
|
||||
}
|
||||
|
||||
if (!options.width) {
|
||||
options.width = newDimensions[0];
|
||||
}
|
||||
|
||||
if (!options.height) {
|
||||
options.height = newDimensions[1];
|
||||
}
|
||||
}
|
||||
|
||||
// If width is provided, make sure it's not below 1
|
||||
if (options.width) {
|
||||
options.width = Math.max(1, options.width - getBorderWidth(options.borderStyle));
|
||||
}
|
||||
|
||||
// If height is provided, make sure it's not below 1
|
||||
if (options.height) {
|
||||
options.height = Math.max(1, options.height - getBorderWidth(options.borderStyle));
|
||||
}
|
||||
|
||||
return options;
|
||||
};
|
||||
|
||||
const formatTitle = (title, borderStyle) => borderStyle === NONE ? title : ` ${title} `;
|
||||
|
||||
const determineDimensions = (text, options) => {
|
||||
options = sanitizeOptions(options);
|
||||
const widthOverride = options.width !== undefined;
|
||||
const columns = terminalColumns();
|
||||
const borderWidth = getBorderWidth(options.borderStyle);
|
||||
const maxWidth = columns - options.margin.left - options.margin.right - borderWidth;
|
||||
|
||||
const widest = widestLine(wrapAnsi(text, columns - borderWidth, {hard: true, trim: false})) + options.padding.left + options.padding.right;
|
||||
|
||||
// If title and width are provided, title adheres to fixed width
|
||||
if (options.title && widthOverride) {
|
||||
options.title = options.title.slice(0, Math.max(0, options.width - 2));
|
||||
if (options.title) {
|
||||
options.title = formatTitle(options.title, options.borderStyle);
|
||||
}
|
||||
} else if (options.title) {
|
||||
options.title = options.title.slice(0, Math.max(0, maxWidth - 2));
|
||||
|
||||
// Recheck if title isn't empty now
|
||||
if (options.title) {
|
||||
options.title = formatTitle(options.title, options.borderStyle);
|
||||
// If the title is larger than content, box adheres to title width
|
||||
if (stringWidth(options.title) > widest) {
|
||||
options.width = stringWidth(options.title);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// If fixed width is provided, use it or content width as reference
|
||||
options.width = options.width ? options.width : widest;
|
||||
|
||||
if (!widthOverride) {
|
||||
if ((options.margin.left && options.margin.right) && options.width > maxWidth) {
|
||||
// Let's assume we have margins: left = 3, right = 5, in total = 8
|
||||
const spaceForMargins = columns - options.width - borderWidth;
|
||||
// Let's assume we have space = 4
|
||||
const multiplier = spaceForMargins / (options.margin.left + options.margin.right);
|
||||
// Here: multiplier = 4/8 = 0.5
|
||||
options.margin.left = Math.max(0, Math.floor(options.margin.left * multiplier));
|
||||
options.margin.right = Math.max(0, Math.floor(options.margin.right * multiplier));
|
||||
// Left: 3 * 0.5 = 1.5 -> 1
|
||||
// Right: 6 * 0.5 = 3
|
||||
}
|
||||
|
||||
// Re-cap width considering the margins after shrinking
|
||||
options.width = Math.min(options.width, columns - borderWidth - options.margin.left - options.margin.right);
|
||||
}
|
||||
|
||||
// Prevent padding overflow
|
||||
if (options.width - (options.padding.left + options.padding.right) <= 0) {
|
||||
options.padding.left = 0;
|
||||
options.padding.right = 0;
|
||||
}
|
||||
|
||||
if (options.height && options.height - (options.padding.top + options.padding.bottom) <= 0) {
|
||||
options.padding.top = 0;
|
||||
options.padding.bottom = 0;
|
||||
}
|
||||
|
||||
return options;
|
||||
};
|
||||
|
||||
const isHex = color => color.match(/^#(?:[0-f]{3}){1,2}$/i);
|
||||
const isColorValid = color => typeof color === 'string' && (chalk[color] ?? isHex(color));
|
||||
const getColorFn = color => isHex(color) ? chalk.hex(color) : chalk[color];
|
||||
const getBGColorFn = color => isHex(color) ? chalk.bgHex(color) : chalk[camelCase(['bg', color])];
|
||||
|
||||
export default function boxen(text, options) {
|
||||
options = {
|
||||
padding: 0,
|
||||
borderStyle: 'single',
|
||||
dimBorder: false,
|
||||
textAlignment: 'left',
|
||||
float: 'left',
|
||||
titleAlignment: 'left',
|
||||
...options,
|
||||
};
|
||||
|
||||
// This option is deprecated
|
||||
if (options.align) {
|
||||
options.textAlignment = options.align;
|
||||
}
|
||||
|
||||
if (options.borderColor && !isColorValid(options.borderColor)) {
|
||||
throw new Error(`${options.borderColor} is not a valid borderColor`);
|
||||
}
|
||||
|
||||
if (options.backgroundColor && !isColorValid(options.backgroundColor)) {
|
||||
throw new Error(`${options.backgroundColor} is not a valid backgroundColor`);
|
||||
}
|
||||
|
||||
options.padding = getObject(options.padding);
|
||||
options.margin = getObject(options.margin);
|
||||
|
||||
options = determineDimensions(text, options);
|
||||
|
||||
text = makeContentText(text, options);
|
||||
|
||||
return boxContent(text, options.width, options);
|
||||
}
|
||||
|
||||
export {default as _borderStyles} from 'cli-boxes';
|
||||
9
node_modules/boxen/license
generated
vendored
Normal file
9
node_modules/boxen/license
generated
vendored
Normal file
@@ -0,0 +1,9 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (https://sindresorhus.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
29
node_modules/boxen/node_modules/string-width/index.d.ts
generated
vendored
Normal file
29
node_modules/boxen/node_modules/string-width/index.d.ts
generated
vendored
Normal file
@@ -0,0 +1,29 @@
|
||||
export interface Options {
|
||||
/**
|
||||
Count [ambiguous width characters](https://www.unicode.org/reports/tr11/#Ambiguous) as having narrow width (count of 1) instead of wide width (count of 2).
|
||||
|
||||
@default true
|
||||
*/
|
||||
readonly ambiguousIsNarrow: boolean;
|
||||
}
|
||||
|
||||
/**
|
||||
Get the visual width of a string - the number of columns required to display it.
|
||||
|
||||
Some Unicode characters are [fullwidth](https://en.wikipedia.org/wiki/Halfwidth_and_fullwidth_forms) and use double the normal width. [ANSI escape codes](https://en.wikipedia.org/wiki/ANSI_escape_code) are stripped and doesn't affect the width.
|
||||
|
||||
@example
|
||||
```
|
||||
import stringWidth from 'string-width';
|
||||
|
||||
stringWidth('a');
|
||||
//=> 1
|
||||
|
||||
stringWidth('古');
|
||||
//=> 2
|
||||
|
||||
stringWidth('\u001B[1m古\u001B[22m');
|
||||
//=> 2
|
||||
```
|
||||
*/
|
||||
export default function stringWidth(string: string, options?: Options): number;
|
||||
54
node_modules/boxen/node_modules/string-width/index.js
generated
vendored
Normal file
54
node_modules/boxen/node_modules/string-width/index.js
generated
vendored
Normal file
@@ -0,0 +1,54 @@
|
||||
import stripAnsi from 'strip-ansi';
|
||||
import eastAsianWidth from 'eastasianwidth';
|
||||
import emojiRegex from 'emoji-regex';
|
||||
|
||||
export default function stringWidth(string, options = {}) {
|
||||
if (typeof string !== 'string' || string.length === 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
options = {
|
||||
ambiguousIsNarrow: true,
|
||||
...options
|
||||
};
|
||||
|
||||
string = stripAnsi(string);
|
||||
|
||||
if (string.length === 0) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
string = string.replace(emojiRegex(), ' ');
|
||||
|
||||
const ambiguousCharacterWidth = options.ambiguousIsNarrow ? 1 : 2;
|
||||
let width = 0;
|
||||
|
||||
for (const character of string) {
|
||||
const codePoint = character.codePointAt(0);
|
||||
|
||||
// Ignore control characters
|
||||
if (codePoint <= 0x1F || (codePoint >= 0x7F && codePoint <= 0x9F)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// Ignore combining characters
|
||||
if (codePoint >= 0x300 && codePoint <= 0x36F) {
|
||||
continue;
|
||||
}
|
||||
|
||||
const code = eastAsianWidth.eastAsianWidth(character);
|
||||
switch (code) {
|
||||
case 'F':
|
||||
case 'W':
|
||||
width += 2;
|
||||
break;
|
||||
case 'A':
|
||||
width += ambiguousCharacterWidth;
|
||||
break;
|
||||
default:
|
||||
width += 1;
|
||||
}
|
||||
}
|
||||
|
||||
return width;
|
||||
}
|
||||
9
node_modules/boxen/node_modules/string-width/license
generated
vendored
Normal file
9
node_modules/boxen/node_modules/string-width/license
generated
vendored
Normal file
@@ -0,0 +1,9 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) Sindre Sorhus <sindresorhus@gmail.com> (https://sindresorhus.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
20
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/LICENSE-MIT.txt
generated
vendored
Normal file
20
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/LICENSE-MIT.txt
generated
vendored
Normal file
@@ -0,0 +1,20 @@
|
||||
Copyright Mathias Bynens <https://mathiasbynens.be/>
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining
|
||||
a copy of this software and associated documentation files (the
|
||||
"Software"), to deal in the Software without restriction, including
|
||||
without limitation the rights to use, copy, modify, merge, publish,
|
||||
distribute, sublicense, and/or sell copies of the Software, and to
|
||||
permit persons to whom the Software is furnished to do so, subject to
|
||||
the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be
|
||||
included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
||||
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
||||
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
||||
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
||||
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
137
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/README.md
generated
vendored
Normal file
137
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/README.md
generated
vendored
Normal file
@@ -0,0 +1,137 @@
|
||||
# emoji-regex [](https://travis-ci.org/mathiasbynens/emoji-regex)
|
||||
|
||||
_emoji-regex_ offers a regular expression to match all emoji symbols and sequences (including textual representations of emoji) as per the Unicode Standard.
|
||||
|
||||
This repository contains a script that generates this regular expression based on [Unicode data](https://github.com/node-unicode/node-unicode-data). Because of this, the regular expression can easily be updated whenever new emoji are added to the Unicode standard.
|
||||
|
||||
## Installation
|
||||
|
||||
Via [npm](https://www.npmjs.com/):
|
||||
|
||||
```bash
|
||||
npm install emoji-regex
|
||||
```
|
||||
|
||||
In [Node.js](https://nodejs.org/):
|
||||
|
||||
```js
|
||||
const emojiRegex = require('emoji-regex/RGI_Emoji.js');
|
||||
// Note: because the regular expression has the global flag set, this module
|
||||
// exports a function that returns the regex rather than exporting the regular
|
||||
// expression itself, to make it impossible to (accidentally) mutate the
|
||||
// original regular expression.
|
||||
|
||||
const text = `
|
||||
\u{231A}: ⌚ default emoji presentation character (Emoji_Presentation)
|
||||
\u{2194}\u{FE0F}: ↔️ default text presentation character rendered as emoji
|
||||
\u{1F469}: 👩 emoji modifier base (Emoji_Modifier_Base)
|
||||
\u{1F469}\u{1F3FF}: 👩🏿 emoji modifier base followed by a modifier
|
||||
`;
|
||||
|
||||
const regex = emojiRegex();
|
||||
let match;
|
||||
while (match = regex.exec(text)) {
|
||||
const emoji = match[0];
|
||||
console.log(`Matched sequence ${ emoji } — code points: ${ [...emoji].length }`);
|
||||
}
|
||||
```
|
||||
|
||||
Console output:
|
||||
|
||||
```
|
||||
Matched sequence ⌚ — code points: 1
|
||||
Matched sequence ⌚ — code points: 1
|
||||
Matched sequence ↔️ — code points: 2
|
||||
Matched sequence ↔️ — code points: 2
|
||||
Matched sequence 👩 — code points: 1
|
||||
Matched sequence 👩 — code points: 1
|
||||
Matched sequence 👩🏿 — code points: 2
|
||||
Matched sequence 👩🏿 — code points: 2
|
||||
```
|
||||
|
||||
## Regular expression flavors
|
||||
|
||||
The package comes with three distinct regular expressions:
|
||||
|
||||
```js
|
||||
// This is the recommended regular expression to use. It matches all
|
||||
// emoji recommended for general interchange, as defined via the
|
||||
// `RGI_Emoji` property in the Unicode Standard.
|
||||
// https://unicode.org/reports/tr51/#def_rgi_set
|
||||
// When in doubt, use this!
|
||||
const emojiRegexRGI = require('emoji-regex/RGI_Emoji.js');
|
||||
|
||||
// This is the old regular expression, prior to `RGI_Emoji` being
|
||||
// standardized. In addition to all `RGI_Emoji` sequences, it matches
|
||||
// some emoji you probably don’t want to match (such as emoji component
|
||||
// symbols that are not meant to be used separately).
|
||||
const emojiRegex = require('emoji-regex/index.js');
|
||||
|
||||
// This regular expression matches even more emoji than the previous
|
||||
// one, including emoji that render as text instead of icons (i.e.
|
||||
// emoji that are not `Emoji_Presentation` symbols and that aren’t
|
||||
// forced to render as emoji by a variation selector).
|
||||
const emojiRegexText = require('emoji-regex/text.js');
|
||||
```
|
||||
|
||||
Additionally, in environments which support ES2015 Unicode escapes, you may `require` ES2015-style versions of the regexes:
|
||||
|
||||
```js
|
||||
const emojiRegexRGI = require('emoji-regex/es2015/RGI_Emoji.js');
|
||||
const emojiRegex = require('emoji-regex/es2015/index.js');
|
||||
const emojiRegexText = require('emoji-regex/es2015/text.js');
|
||||
```
|
||||
|
||||
## For maintainers
|
||||
|
||||
### How to update emoji-regex after new Unicode Standard releases
|
||||
|
||||
1. Update the Unicode data dependency in `package.json` by running the following commands:
|
||||
|
||||
```sh
|
||||
# Example: updating from Unicode v12 to Unicode v13.
|
||||
npm uninstall @unicode/unicode-12.0.0
|
||||
npm install @unicode/unicode-13.0.0 --save-dev
|
||||
````
|
||||
|
||||
1. Generate the new output:
|
||||
|
||||
```sh
|
||||
npm run build
|
||||
```
|
||||
|
||||
1. Verify that tests still pass:
|
||||
|
||||
```sh
|
||||
npm test
|
||||
```
|
||||
|
||||
1. Send a pull request with the changes, and get it reviewed & merged.
|
||||
|
||||
1. On the `main` branch, bump the emoji-regex version number in `package.json`:
|
||||
|
||||
```sh
|
||||
npm version patch -m 'Release v%s'
|
||||
```
|
||||
|
||||
Instead of `patch`, use `minor` or `major` [as needed](https://semver.org/).
|
||||
|
||||
Note that this produces a Git commit + tag.
|
||||
|
||||
1. Push the release commit and tag:
|
||||
|
||||
```sh
|
||||
git push
|
||||
```
|
||||
|
||||
Our CI then automatically publishes the new release to npm.
|
||||
|
||||
## Author
|
||||
|
||||
| [](https://twitter.com/mathias "Follow @mathias on Twitter") |
|
||||
|---|
|
||||
| [Mathias Bynens](https://mathiasbynens.be/) |
|
||||
|
||||
## License
|
||||
|
||||
_emoji-regex_ is available under the [MIT](https://mths.be/mit) license.
|
||||
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/RGI_Emoji.d.ts
generated
vendored
Normal file
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/RGI_Emoji.d.ts
generated
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
declare module 'emoji-regex/RGI_Emoji' {
|
||||
function emojiRegex(): RegExp;
|
||||
|
||||
export = emojiRegex;
|
||||
}
|
||||
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/RGI_Emoji.js
generated
vendored
Normal file
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/RGI_Emoji.js
generated
vendored
Normal file
File diff suppressed because one or more lines are too long
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/RGI_Emoji.d.ts
generated
vendored
Normal file
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/RGI_Emoji.d.ts
generated
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
declare module 'emoji-regex/es2015/RGI_Emoji' {
|
||||
function emojiRegex(): RegExp;
|
||||
|
||||
export = emojiRegex;
|
||||
}
|
||||
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/RGI_Emoji.js
generated
vendored
Normal file
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/RGI_Emoji.js
generated
vendored
Normal file
File diff suppressed because one or more lines are too long
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/index.d.ts
generated
vendored
Normal file
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/index.d.ts
generated
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
declare module 'emoji-regex/es2015' {
|
||||
function emojiRegex(): RegExp;
|
||||
|
||||
export = emojiRegex;
|
||||
}
|
||||
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/index.js
generated
vendored
Normal file
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/index.js
generated
vendored
Normal file
File diff suppressed because one or more lines are too long
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/text.d.ts
generated
vendored
Normal file
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/text.d.ts
generated
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
declare module 'emoji-regex/es2015/text' {
|
||||
function emojiRegex(): RegExp;
|
||||
|
||||
export = emojiRegex;
|
||||
}
|
||||
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/text.js
generated
vendored
Normal file
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/es2015/text.js
generated
vendored
Normal file
File diff suppressed because one or more lines are too long
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/index.d.ts
generated
vendored
Normal file
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/index.d.ts
generated
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
declare module 'emoji-regex' {
|
||||
function emojiRegex(): RegExp;
|
||||
|
||||
export = emojiRegex;
|
||||
}
|
||||
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/index.js
generated
vendored
Normal file
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/index.js
generated
vendored
Normal file
File diff suppressed because one or more lines are too long
52
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/package.json
generated
vendored
Normal file
52
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/package.json
generated
vendored
Normal file
@@ -0,0 +1,52 @@
|
||||
{
|
||||
"name": "emoji-regex",
|
||||
"version": "9.2.2",
|
||||
"description": "A regular expression to match all Emoji-only symbols as per the Unicode Standard.",
|
||||
"homepage": "https://mths.be/emoji-regex",
|
||||
"main": "index.js",
|
||||
"types": "index.d.ts",
|
||||
"keywords": [
|
||||
"unicode",
|
||||
"regex",
|
||||
"regexp",
|
||||
"regular expressions",
|
||||
"code points",
|
||||
"symbols",
|
||||
"characters",
|
||||
"emoji"
|
||||
],
|
||||
"license": "MIT",
|
||||
"author": {
|
||||
"name": "Mathias Bynens",
|
||||
"url": "https://mathiasbynens.be/"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/mathiasbynens/emoji-regex.git"
|
||||
},
|
||||
"bugs": "https://github.com/mathiasbynens/emoji-regex/issues",
|
||||
"files": [
|
||||
"LICENSE-MIT.txt",
|
||||
"index.js",
|
||||
"index.d.ts",
|
||||
"RGI_Emoji.js",
|
||||
"RGI_Emoji.d.ts",
|
||||
"text.js",
|
||||
"text.d.ts",
|
||||
"es2015"
|
||||
],
|
||||
"scripts": {
|
||||
"build": "rm -rf -- es2015; babel src -d .; NODE_ENV=es2015 babel src es2015_types -D -d ./es2015; node script/inject-sequences.js",
|
||||
"test": "mocha",
|
||||
"test:watch": "npm run test -- --watch"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@babel/cli": "^7.4.4",
|
||||
"@babel/core": "^7.4.4",
|
||||
"@babel/plugin-proposal-unicode-property-regex": "^7.4.4",
|
||||
"@babel/preset-env": "^7.4.4",
|
||||
"@unicode/unicode-13.0.0": "^1.0.3",
|
||||
"mocha": "^6.1.4",
|
||||
"regexgen": "^1.3.0"
|
||||
}
|
||||
}
|
||||
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/text.d.ts
generated
vendored
Normal file
5
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/text.d.ts
generated
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
declare module 'emoji-regex/text' {
|
||||
function emojiRegex(): RegExp;
|
||||
|
||||
export = emojiRegex;
|
||||
}
|
||||
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/text.js
generated
vendored
Normal file
6
node_modules/boxen/node_modules/string-width/node_modules/emoji-regex/text.js
generated
vendored
Normal file
File diff suppressed because one or more lines are too long
59
node_modules/boxen/node_modules/string-width/package.json
generated
vendored
Normal file
59
node_modules/boxen/node_modules/string-width/package.json
generated
vendored
Normal file
@@ -0,0 +1,59 @@
|
||||
{
|
||||
"name": "string-width",
|
||||
"version": "5.1.2",
|
||||
"description": "Get the visual width of a string - the number of columns required to display it",
|
||||
"license": "MIT",
|
||||
"repository": "sindresorhus/string-width",
|
||||
"funding": "https://github.com/sponsors/sindresorhus",
|
||||
"author": {
|
||||
"name": "Sindre Sorhus",
|
||||
"email": "sindresorhus@gmail.com",
|
||||
"url": "https://sindresorhus.com"
|
||||
},
|
||||
"type": "module",
|
||||
"exports": "./index.js",
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
"scripts": {
|
||||
"test": "xo && ava && tsd"
|
||||
},
|
||||
"files": [
|
||||
"index.js",
|
||||
"index.d.ts"
|
||||
],
|
||||
"keywords": [
|
||||
"string",
|
||||
"character",
|
||||
"unicode",
|
||||
"width",
|
||||
"visual",
|
||||
"column",
|
||||
"columns",
|
||||
"fullwidth",
|
||||
"full-width",
|
||||
"full",
|
||||
"ansi",
|
||||
"escape",
|
||||
"codes",
|
||||
"cli",
|
||||
"command-line",
|
||||
"terminal",
|
||||
"console",
|
||||
"cjk",
|
||||
"chinese",
|
||||
"japanese",
|
||||
"korean",
|
||||
"fixed-width"
|
||||
],
|
||||
"dependencies": {
|
||||
"eastasianwidth": "^0.2.0",
|
||||
"emoji-regex": "^9.2.2",
|
||||
"strip-ansi": "^7.0.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"ava": "^3.15.0",
|
||||
"tsd": "^0.14.0",
|
||||
"xo": "^0.38.2"
|
||||
}
|
||||
}
|
||||
67
node_modules/boxen/node_modules/string-width/readme.md
generated
vendored
Normal file
67
node_modules/boxen/node_modules/string-width/readme.md
generated
vendored
Normal file
@@ -0,0 +1,67 @@
|
||||
# string-width
|
||||
|
||||
> Get the visual width of a string - the number of columns required to display it
|
||||
|
||||
Some Unicode characters are [fullwidth](https://en.wikipedia.org/wiki/Halfwidth_and_fullwidth_forms) and use double the normal width. [ANSI escape codes](https://en.wikipedia.org/wiki/ANSI_escape_code) are stripped and doesn't affect the width.
|
||||
|
||||
Useful to be able to measure the actual width of command-line output.
|
||||
|
||||
## Install
|
||||
|
||||
```
|
||||
$ npm install string-width
|
||||
```
|
||||
|
||||
## Usage
|
||||
|
||||
```js
|
||||
import stringWidth from 'string-width';
|
||||
|
||||
stringWidth('a');
|
||||
//=> 1
|
||||
|
||||
stringWidth('古');
|
||||
//=> 2
|
||||
|
||||
stringWidth('\u001B[1m古\u001B[22m');
|
||||
//=> 2
|
||||
```
|
||||
|
||||
## API
|
||||
|
||||
### stringWidth(string, options?)
|
||||
|
||||
#### string
|
||||
|
||||
Type: `string`
|
||||
|
||||
The string to be counted.
|
||||
|
||||
#### options
|
||||
|
||||
Type: `object`
|
||||
|
||||
##### ambiguousIsNarrow
|
||||
|
||||
Type: `boolean`\
|
||||
Default: `false`
|
||||
|
||||
Count [ambiguous width characters](https://www.unicode.org/reports/tr11/#Ambiguous) as having narrow width (count of 1) instead of wide width (count of 2).
|
||||
|
||||
## Related
|
||||
|
||||
- [string-width-cli](https://github.com/sindresorhus/string-width-cli) - CLI for this module
|
||||
- [string-length](https://github.com/sindresorhus/string-length) - Get the real length of a string
|
||||
- [widest-line](https://github.com/sindresorhus/widest-line) - Get the visual width of the widest line in a string
|
||||
|
||||
---
|
||||
|
||||
<div align="center">
|
||||
<b>
|
||||
<a href="https://tidelift.com/subscription/pkg/npm-string-width?utm_source=npm-string-width&utm_medium=referral&utm_campaign=readme">Get professional support for this package with a Tidelift subscription</a>
|
||||
</b>
|
||||
<br>
|
||||
<sub>
|
||||
Tidelift helps make open source sustainable for maintainers while giving companies<br>assurances about security, maintenance, and licensing for their dependencies.
|
||||
</sub>
|
||||
</div>
|
||||
67
node_modules/boxen/package.json
generated
vendored
Normal file
67
node_modules/boxen/package.json
generated
vendored
Normal file
@@ -0,0 +1,67 @@
|
||||
{
|
||||
"name": "boxen",
|
||||
"version": "7.1.1",
|
||||
"description": "Create boxes in the terminal",
|
||||
"license": "MIT",
|
||||
"repository": "sindresorhus/boxen",
|
||||
"funding": "https://github.com/sponsors/sindresorhus",
|
||||
"author": {
|
||||
"name": "Sindre Sorhus",
|
||||
"email": "sindresorhus@gmail.com",
|
||||
"url": "https://sindresorhus.com"
|
||||
},
|
||||
"type": "module",
|
||||
"exports": "./index.js",
|
||||
"engines": {
|
||||
"node": ">=14.16"
|
||||
},
|
||||
"scripts": {
|
||||
"test": "xo && nyc ava && tsd"
|
||||
},
|
||||
"files": [
|
||||
"index.js",
|
||||
"index.d.ts"
|
||||
],
|
||||
"keywords": [
|
||||
"cli",
|
||||
"box",
|
||||
"boxes",
|
||||
"terminal",
|
||||
"term",
|
||||
"console",
|
||||
"ascii",
|
||||
"unicode",
|
||||
"border",
|
||||
"text"
|
||||
],
|
||||
"dependencies": {
|
||||
"ansi-align": "^3.0.1",
|
||||
"camelcase": "^7.0.1",
|
||||
"chalk": "^5.2.0",
|
||||
"cli-boxes": "^3.0.0",
|
||||
"string-width": "^5.1.2",
|
||||
"type-fest": "^2.13.0",
|
||||
"widest-line": "^4.0.1",
|
||||
"wrap-ansi": "^8.1.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"ava": "^5.2.0",
|
||||
"nyc": "^15.1.0",
|
||||
"tsd": "^0.28.1",
|
||||
"xo": "^0.54.2"
|
||||
},
|
||||
"ava": {
|
||||
"snapshotDir": "tests/snapshots",
|
||||
"environmentVariables": {
|
||||
"COLUMNS": "60",
|
||||
"FORCE_COLOR": "0"
|
||||
}
|
||||
},
|
||||
"xo": {
|
||||
"rules": {
|
||||
"@typescript-eslint/no-redundant-type-constituents": "off",
|
||||
"unicorn/prefer-logical-operator-over-ternary": "off",
|
||||
"@typescript-eslint/no-unsafe-assignment": "off"
|
||||
}
|
||||
}
|
||||
}
|
||||
300
node_modules/boxen/readme.md
generated
vendored
Normal file
300
node_modules/boxen/readme.md
generated
vendored
Normal file
@@ -0,0 +1,300 @@
|
||||
# boxen
|
||||
|
||||
> Create boxes in the terminal
|
||||
|
||||

|
||||
|
||||
## Install
|
||||
|
||||
```sh
|
||||
npm install boxen
|
||||
```
|
||||
|
||||
## Usage
|
||||
|
||||
```js
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('unicorn', {padding: 1}));
|
||||
/*
|
||||
┌─────────────┐
|
||||
│ │
|
||||
│ unicorn │
|
||||
│ │
|
||||
└─────────────┘
|
||||
*/
|
||||
|
||||
console.log(boxen('unicorn', {padding: 1, margin: 1, borderStyle: 'double'}));
|
||||
/*
|
||||
|
||||
╔═════════════╗
|
||||
║ ║
|
||||
║ unicorn ║
|
||||
║ ║
|
||||
╚═════════════╝
|
||||
|
||||
*/
|
||||
|
||||
console.log(boxen('unicorns love rainbows', {title: 'magical', titleAlignment: 'center'}));
|
||||
/*
|
||||
┌────── magical ───────┐
|
||||
│unicorns love rainbows│
|
||||
└──────────────────────┘
|
||||
*/
|
||||
```
|
||||
|
||||
## API
|
||||
|
||||
### boxen(text, options?)
|
||||
|
||||
#### text
|
||||
|
||||
Type: `string`
|
||||
|
||||
Text inside the box.
|
||||
|
||||
#### options
|
||||
|
||||
Type: `object`
|
||||
|
||||
##### borderColor
|
||||
|
||||
Type: `string`\
|
||||
Values: `'black'` `'red'` `'green'` `'yellow'` `'blue'` `'magenta'` `'cyan'` `'white'` `'gray'` or a hex value like `'#ff0000'`
|
||||
|
||||
Color of the box border.
|
||||
|
||||
##### borderStyle
|
||||
|
||||
Type: `string | object`\
|
||||
Default: `'single'`\
|
||||
Values:
|
||||
- `'single'`
|
||||
```
|
||||
┌───┐
|
||||
│foo│
|
||||
└───┘
|
||||
```
|
||||
- `'double'`
|
||||
```
|
||||
╔═══╗
|
||||
║foo║
|
||||
╚═══╝
|
||||
```
|
||||
- `'round'` (`'single'` sides with round corners)
|
||||
```
|
||||
╭───╮
|
||||
│foo│
|
||||
╰───╯
|
||||
```
|
||||
- `'bold'`
|
||||
```
|
||||
┏━━━┓
|
||||
┃foo┃
|
||||
┗━━━┛
|
||||
```
|
||||
- `'singleDouble'` (`'single'` on top and bottom, `'double'` on right and left)
|
||||
```
|
||||
╓───╖
|
||||
║foo║
|
||||
╙───╜
|
||||
```
|
||||
- `'doubleSingle'` (`'double'` on top and bottom, `'single'` on right and left)
|
||||
```
|
||||
╒═══╕
|
||||
│foo│
|
||||
╘═══╛
|
||||
```
|
||||
- `'classic'`
|
||||
```
|
||||
+---+
|
||||
|foo|
|
||||
+---+
|
||||
```
|
||||
- `'arrow'`
|
||||
```
|
||||
↘↓↓↓↙
|
||||
→foo←
|
||||
↗↑↑↑↖
|
||||
```
|
||||
- `'none'`
|
||||
```
|
||||
foo
|
||||
```
|
||||
|
||||
Style of the box border.
|
||||
|
||||
Can be any of the above predefined styles or an object with the following keys:
|
||||
|
||||
```js
|
||||
{
|
||||
topLeft: '+',
|
||||
topRight: '+',
|
||||
bottomLeft: '+',
|
||||
bottomRight: '+',
|
||||
top: '-',
|
||||
bottom: '-',
|
||||
left: '|',
|
||||
right: '|'
|
||||
}
|
||||
```
|
||||
|
||||
##### dimBorder
|
||||
|
||||
Type: `boolean`\
|
||||
Default: `false`
|
||||
|
||||
Reduce opacity of the border.
|
||||
|
||||
##### title
|
||||
|
||||
Type: `string`
|
||||
|
||||
Display a title at the top of the box.
|
||||
If needed, the box will horizontally expand to fit the title.
|
||||
|
||||
Example:
|
||||
```js
|
||||
console.log(boxen('foo bar', {title: 'example'}));
|
||||
/*
|
||||
┌ example ┐
|
||||
│foo bar │
|
||||
└─────────┘
|
||||
*/
|
||||
```
|
||||
|
||||
##### titleAlignment
|
||||
|
||||
Type: `string`\
|
||||
Default: `'left'`
|
||||
|
||||
Align the title in the top bar.
|
||||
|
||||
Values:
|
||||
- `'left'`
|
||||
```js
|
||||
/*
|
||||
┌ example ──────┐
|
||||
│foo bar foo bar│
|
||||
└───────────────┘
|
||||
*/
|
||||
```
|
||||
- `'center'`
|
||||
```js
|
||||
/*
|
||||
┌─── example ───┐
|
||||
│foo bar foo bar│
|
||||
└───────────────┘
|
||||
*/
|
||||
```
|
||||
- `'right'`
|
||||
```js
|
||||
/*
|
||||
┌────── example ┐
|
||||
│foo bar foo bar│
|
||||
└───────────────┘
|
||||
*/
|
||||
```
|
||||
|
||||
##### width
|
||||
|
||||
Type: `number`
|
||||
|
||||
Set a fixed width for the box.
|
||||
|
||||
*Note:* This disables terminal overflow handling and may cause the box to look broken if the user's terminal is not wide enough.
|
||||
|
||||
```js
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('foo bar', {width: 15}));
|
||||
// ┌─────────────┐
|
||||
// │foo bar │
|
||||
// └─────────────┘
|
||||
```
|
||||
|
||||
##### height
|
||||
|
||||
Type: `number`
|
||||
|
||||
Set a fixed height for the box.
|
||||
|
||||
*Note:* This option will crop overflowing content.
|
||||
|
||||
```js
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('foo bar', {height: 5}));
|
||||
// ┌───────┐
|
||||
// │foo bar│
|
||||
// │ │
|
||||
// │ │
|
||||
// └───────┘
|
||||
```
|
||||
|
||||
##### fullscreen
|
||||
|
||||
Type: `boolean | (width: number, height: number) => [width: number, height: number]`
|
||||
|
||||
Whether or not to fit all available space within the terminal.
|
||||
|
||||
Pass a callback function to control box dimensions:
|
||||
|
||||
```js
|
||||
import boxen from 'boxen';
|
||||
|
||||
console.log(boxen('foo bar', {
|
||||
fullscreen: (width, height) => [width, height - 1],
|
||||
}));
|
||||
```
|
||||
|
||||
##### padding
|
||||
|
||||
Type: `number | object`\
|
||||
Default: `0`
|
||||
|
||||
Space between the text and box border.
|
||||
|
||||
Accepts a number or an object with any of the `top`, `right`, `bottom`, `left` properties. When a number is specified, the left/right padding is 3 times the top/bottom to make it look nice.
|
||||
|
||||
##### margin
|
||||
|
||||
Type: `number | object`\
|
||||
Default: `0`
|
||||
|
||||
Space around the box.
|
||||
|
||||
Accepts a number or an object with any of the `top`, `right`, `bottom`, `left` properties. When a number is specified, the left/right margin is 3 times the top/bottom to make it look nice.
|
||||
|
||||
##### float
|
||||
|
||||
Type: `string`\
|
||||
Default: `'left'`\
|
||||
Values: `'right'` `'center'` `'left'`
|
||||
|
||||
Float the box on the available terminal screen space.
|
||||
|
||||
##### backgroundColor
|
||||
|
||||
Type: `string`\
|
||||
Values: `'black'` `'red'` `'green'` `'yellow'` `'blue'` `'magenta'` `'cyan'` `'white'` `'gray'` or a hex value like `'#ff0000'`
|
||||
|
||||
Color of the background.
|
||||
|
||||
##### textAlignment
|
||||
|
||||
Type: `string`\
|
||||
Default: `'left'`\
|
||||
Values: `'left'` `'center'` `'right'`
|
||||
|
||||
Align the text in the box based on the widest line.
|
||||
|
||||
## Maintainer
|
||||
|
||||
- [Sindre Sorhus](https://github.com/sindresorhus)
|
||||
- [Caesarovich](https://github.com/Caesarovich)
|
||||
|
||||
## Related
|
||||
|
||||
- [boxen-cli](https://github.com/sindresorhus/boxen-cli) - CLI for this module
|
||||
- [cli-boxes](https://github.com/sindresorhus/cli-boxes) - Boxes for use in the terminal
|
||||
Reference in New Issue
Block a user