Comparing version 1.1.1 to 1.2.0
# Change log | ||
## 1.2.0 (2021-12-27) | ||
- added supports the environment variables `NO_COLOR` `FORCE_COLOR` and flags `--no-color` `--color` | ||
- added aliases `ansi` for `ansi256` and `bgAnsi` for `bgAnsi256` | ||
- added to readme the compare of most popular ANSI libraries | ||
## 1.1.1 (2021-12-27) | ||
- add the class Ansis to create more independent instances to increase the performance by benchmark | ||
- added the class Ansis to create more independent instances to increase the performance by benchmark | ||
- improve performance | ||
@@ -10,5 +15,5 @@ - code refactoring | ||
## 1.1.0 (2021-12-25) | ||
- add supports the use of `open` and `close` properties for each style | ||
- fix codes for methods ansi256() and bgAnsi256() | ||
- add demo to npm package | ||
- added supports the use of `open` and `close` properties for each style | ||
- added demo to npm package | ||
- fixed codes for methods ansi256() and bgAnsi256() | ||
- update package.json | ||
@@ -15,0 +20,0 @@ - update readme |
{ | ||
"name": "ansis", | ||
"version": "1.1.1", | ||
"version": "1.2.0", | ||
"description": "Color styling of text for ANSI terminals using the SGR codes defined in the ECMA-48 standard.", | ||
@@ -19,3 +19,4 @@ "keywords": [ | ||
"log", | ||
"logging" | ||
"logging", | ||
"NO_COLOR" | ||
], | ||
@@ -22,0 +23,0 @@ "license": "ISC", |
151
README.md
@@ -9,7 +9,6 @@ <h1 align="center"> | ||
--- | ||
[![npm version](https://badge.fury.io/js/ansis.svg)](https://www.npmjs.com/package/ansis) | ||
[![npm](https://img.shields.io/npm/v/ansis?logo=npm&color=brightgreen "npm package")](https://www.npmjs.com/package/ansis "download npm package") | ||
[![codecov](https://codecov.io/gh/webdiscus/ansis/branch/master/graph/badge.svg?token=H7SFJONX1X)](https://codecov.io/gh/webdiscus/ansis) | ||
[![node](https://img.shields.io/npm/dm/ansis)](https://www.npmjs.com/package/ansis) | ||
Color styling of text for ANSI terminals using the SGR (Select Graphic Rendition) codes defined in the [ECMA-48](https://www.ecma-international.org/publications-and-standards/standards/ecma-48/) standard.\ | ||
@@ -48,2 +47,3 @@ This is improved and faster implementation for `Node.js`. | ||
- supports 256 color and Truecolor | ||
- supports the environment variables [`NO_COLOR`](https://no-color.org) `FORCE_COLOR` and flags `--no-color` `--color` | ||
- supports styles like: `bold` `red` `yellowBright` `bgGreen` `bgCyanBright` ect. | ||
@@ -156,3 +156,8 @@ - supports chained styles, e.g.: | ||
``` | ||
> Aliases | ||
> | ||
> `ansis.ansi()` is alias for `ansis.ansi256()`\ | ||
> `ansis.bgAnsi()` is alias for `ansis.bgAnsi256()` | ||
## Truecolor | ||
@@ -172,2 +177,27 @@ | ||
## Compare most popular ANSI libraries | ||
| Library | Standard<br>style / color<br>naming | Chain<br>styles | Nested<br>styles | New<br>Line | ANSI 256<br>colors | Truecolor<br>RGB / HEX | NO_COLOR | | ||
|------------------------------|-------------------|-----------------|------------------|-------------|---------------------------------|------------------------|:---------------------------------------------------------| | ||
| [`colors.js`][colors.js] | no, e.g.<br>`brightRed` | yes | yes | yes | - | - | only<br>`FORCE_COLOR`<br>`--no-color`<br>`--color` | | ||
| [`colorette`][colorette] | yes<br>(16 colors) | - | yes | - | - | - | yes | | ||
| [`picocolors`][picocolors] | yes<br>(8 colors) | - | yes | - | - | - | yes | | ||
| [`cli-color`][cli-color] | yes<br>(16 colors) | yes | yes | - | `.xterm(num)` | - | yes | | ||
| [`color-cli`][color-cli] | no, e.g.<br>`red_bbt` | yes | buggy | yes | `.x<num>` | - | only<br>`--no-color`<br>`--color` | | ||
| [`ansi-colors`][ansi-colors] | yes<br>(16 colors) | yes | yes | yes | - | - | only<br>`FORCE_COLOR` | | ||
| [`kleur`][kleur] | yes<br>(8 colors) | yes* | yes | - | - | - | yes | | ||
| [`chalk`][chalk] | yes<br>(16 colors) | yes | yes | yes | `.ansi256(num)` | `.hex()` `.rgb()` | yes | | ||
| **+ ansis** | yes<br>(16 colors) | yes | yes | yes | `.ansi256(num)`<br>`.ansi(num)` | `.hex()` `.rgb()` | yes | | ||
### Column description | ||
- **Standard style and color naming**: `red` `redBright` `bgRed` `bgRedBright` etc., see above the **Foreground / Background colors**. | ||
- **Chain styles**: `ansis.red.bold.underline('text')`.\ | ||
`kleur` use the chain of functions: `kleur.red().bold().underline('text')`. | ||
- **Nested styles**: | ||
```js | ||
c.red(`red ${c.green(`green ${c.underline(`underline`)} green`)} red`) | ||
- **New Line**: correct break of escape sequences at `end of line`\ | ||
<img width="128" src="doc/img/break-style-nl.png" alt="new line"> | ||
- **NO_COLOR**: supports the environment variables [`NO_COLOR`](https://no-color.org) `FORCE_COLOR` and flags `--no-color` `--color` | ||
## Benchmark | ||
@@ -186,3 +216,2 @@ | ||
> ### Tested on | ||
@@ -202,12 +231,12 @@ > | ||
```diff | ||
colors-js 1,152,114 ops/sec | ||
colorette 4,548,418 ops/sec | ||
picocolors 3,832,593 ops/sec | ||
cli-color 471,929 ops/sec | ||
color-cli 110,282 ops/sec | ||
ansi-colors 1,272,164 ops/sec | ||
kleur/colors 2,278,569 ops/sec | ||
kleur 2,223,929 ops/sec | ||
chalk 2,255,589 ops/sec | ||
+ ansis 2,674,316 ops/sec | ||
colors-js 1,158,572 ops/sec | ||
colorette 4,572,582 ops/sec | ||
picocolors 3,841,124 ops/sec | ||
cli-color 470,320 ops/sec | ||
color-cli 109,811 ops/sec | ||
ansi-colors 1,265,615 ops/sec | ||
kleur/colors 2,281,415 ops/sec | ||
kleur 2,228,639 ops/sec | ||
chalk 2,287,146 ops/sec | ||
+ ansis 2,669,734 ops/sec | ||
``` | ||
@@ -220,12 +249,12 @@ | ||
```diff | ||
colors-js 475,774 ops/sec | ||
colorette 1,174,392 ops/sec | ||
picocolors 5,724,714 ops/sec | ||
cli-color 220,577 ops/sec | ||
color-cli 73,535 ops/sec | ||
ansi-colors 727,414 ops/sec | ||
kleur/colors 1,275,337 ops/sec | ||
kleur 3,843,212 ops/sec | ||
chalk 3,144,045 ops/sec | ||
+ ansis 4,360,629 ops/sec | ||
colors-js 471,395 ops/sec | ||
colorette 1,103,314 ops/sec | ||
picocolors 5,725,578 ops/sec | ||
cli-color 221,282 ops/sec | ||
color-cli 73,725 ops/sec | ||
ansi-colors 716,280 ops/sec | ||
kleur/colors 1,259,858 ops/sec | ||
kleur 3,829,838 ops/sec | ||
chalk 3,165,933 ops/sec | ||
+ ansis 4,483,217 ops/sec | ||
``` | ||
@@ -256,12 +285,12 @@ | ||
```diff | ||
colors-js 165,202 ops/sec | ||
colorette 712,604 ops/sec | ||
picocolors 939,536 ops/sec | ||
cli-color 64,758 ops/sec | ||
color-cli 13,833 ops/sec | ||
ansi-colors 258,930 ops/sec | ||
kleur/colors 563,266 ops/sec | ||
kleur 646,985 ops/sec | ||
chalk 385,590 ops/sec | ||
+ ansis 554,813 ops/sec | ||
colors-js 166,425 ops/sec | ||
colorette 695,350 ops/sec | ||
picocolors 942,592 ops/sec | ||
cli-color 65,561 ops/sec | ||
color-cli 13,800 ops/sec | ||
ansi-colors 260,316 ops/sec | ||
kleur/colors 561,111 ops/sec | ||
kleur 648,195 ops/sec | ||
chalk 497,292 ops/sec | ||
+ ansis 558,575 ops/sec | ||
@@ -275,15 +304,47 @@ ``` | ||
```diff | ||
colors-js 89,529 ops/sec | ||
colorette 243,237 ops/sec | ||
picocolors 242,528 ops/sec | ||
cli-color 41,897 ops/sec | ||
color-cli 14,245 ops/sec | ||
ansi-colors 120,991 ops/sec | ||
kleur/colors 233,875 ops/sec | ||
kleur 220,233 ops/sec | ||
chalk 157,450 ops/sec | ||
+ ansis 205,393 ops/sec | ||
colors-js 89,633 ops/sec | ||
colorette 243,139 ops/sec | ||
picocolors 243,975 ops/sec | ||
cli-color 41,657 ops/sec | ||
color-cli 14,264 ops/sec | ||
ansi-colors 121,451 ops/sec | ||
kleur/colors 234,132 ops/sec | ||
kleur 221,446 ops/sec | ||
chalk 189,960 ops/sec | ||
+ ansis 211,868 ops/sec | ||
``` | ||
### Deep nested styles | ||
```js | ||
c.green( | ||
`green ${c.cyan( | ||
`cyan ${c.red( | ||
`red ${c.yellow( | ||
`yellow ${c.blue( | ||
`blue ${c.magenta( | ||
`magenta ${c.underline( | ||
`underline ${c.italic(`italic`)} underline` | ||
)} magenta` | ||
)} blue` | ||
)} yellow` | ||
)} red` | ||
)} cyan` | ||
)} green` | ||
); | ||
``` | ||
```diff | ||
colors-js 451,592 ops/sec | ||
colorette 1,131,757 ops/sec | ||
picocolors 1,002,649 ops/sec | ||
cli-color 213,441 ops/sec | ||
color-cli 40,340 ops/sec | ||
ansi-colors 362,733 ops/sec | ||
kleur/colors 478,547 ops/sec | ||
kleur 464,004 ops/sec | ||
chalk 565,965 ops/sec | ||
+ ansis 882,220 ops/sec | ||
``` | ||
### HEX colors | ||
@@ -303,4 +364,4 @@ Only two libraries support truecolors methods: `ansis` and `chalk` | ||
kleur (not supported) | ||
chalk 2,746,362 ops/sec | ||
+ ansis 4,584,357 ops/sec | ||
chalk 2,891,684 ops/sec | ||
+ ansis 4,944,572 ops/sec | ||
``` | ||
@@ -307,0 +368,0 @@ |
@@ -1,62 +0,29 @@ | ||
const esc = ([open, close]) => ({ open: `\x1b[${open}m`, close: `\x1b[${close}m` }); | ||
/** | ||
* @param {Object?} processTest Used by unit test only. | ||
* @returns {boolean} | ||
*/ | ||
export const isSupported = (processTest) => { | ||
const proc = processTest ? processTest : process || {}; | ||
const env = proc.env || {}; | ||
const argv = proc.argv || []; | ||
const stdout = proc.stdout && proc.stdout.isTTY; | ||
//const stderr = proc.stderr && proc.stderr.isTTY; | ||
export const codes = { | ||
// commands | ||
reset: [0, 0], | ||
inverse: [7, 27], | ||
hidden: [8, 28], | ||
const isDisabled = 'NO_COLOR' in env || argv.includes('--no-color') || argv.includes('--color=false'); | ||
const isForced = 'FORCE_COLOR' in env || argv.includes('--color'); | ||
// styles | ||
bold: [1, 22], | ||
dim: [2, 22], // alias for faint | ||
faint: [2, 22], | ||
italic: [3, 23], | ||
underline: [4, 24], | ||
doubleUnderline: [21, 24], | ||
strikethrough: [9, 29], | ||
strike: [9, 29], // alias for strikethrough | ||
frame: [51, 54], | ||
encircle: [52, 54], | ||
overline: [53, 55], | ||
const isTerm = env.TERM !== 'dumb' && /^screen|^xterm|^vt100|^vt220|^rxvt|color|ansi|cygwin|linux/i.test(env.TERM); | ||
const isCompatibleTerminal = (stdout && isTerm) || proc.platform === 'win32'; | ||
const isCI = 'CI' in env; | ||
// foreground colors | ||
black: [30, 39], | ||
red: [31, 39], | ||
green: [32, 39], | ||
yellow: [33, 39], | ||
blue: [34, 39], | ||
magenta: [35, 39], | ||
cyan: [36, 39], | ||
white: [37, 39], | ||
gray: [90, 39], // alias for blackBright | ||
blackBright: [90, 39], | ||
redBright: [91, 39], | ||
greenBright: [92, 39], | ||
yellowBright: [93, 39], | ||
blueBright: [94, 39], | ||
magentaBright: [95, 39], | ||
cyanBright: [96, 39], | ||
whiteBright: [97, 39], | ||
// background colors | ||
bgBlack: [40, 49], | ||
bgRed: [41, 49], | ||
bgGreen: [42, 49], | ||
bgYellow: [43, 49], | ||
bgBlue: [44, 49], | ||
bgMagenta: [45, 49], | ||
bgCyan: [46, 49], | ||
bgWhite: [47, 49], | ||
bgBlackBright: [100, 49], | ||
bgRedBright: [101, 49], | ||
bgGreenBright: [102, 49], | ||
bgYellowBright: [103, 49], | ||
bgBlueBright: [104, 49], | ||
bgMagentaBright: [105, 49], | ||
bgCyanBright: [106, 49], | ||
bgWhiteBright: [107, 49], | ||
return !isDisabled && (isForced || isCompatibleTerminal || isCI); | ||
}; | ||
export const ansiCodes = { | ||
// commands | ||
export const supported = isSupported(); | ||
const noColorProps = { open: '', close: '' }; | ||
const esc = supported ? ([open, close]) => ({ open: `\x1b[${open}m`, close: `\x1b[${close}m` }) : () => noColorProps; | ||
export const baseCodes = { | ||
// misc | ||
reset: esc([0, 0]), | ||
@@ -116,1 +83,8 @@ inverse: esc([7, 27]), | ||
}; | ||
export const extendedCodes = { | ||
ansi256: supported ? (code) => ({ open: `\x1B[38;5;${code}m`, close: '\x1B[39m' }) : () => noColorProps, | ||
bgAnsi256: supported ? (code) => ({ open: `\x1B[48;5;${code}m`, close: '\x1B[49m' }) : () => noColorProps, | ||
rgb: supported ? (r, g, b) => ({ open: `\x1B[38;2;${r};${g};${b}m`, close: '\x1B[39m' }) : () => noColorProps, | ||
bgRgb: supported ? (r, g, b) => ({ open: `\x1B[48;2;${r};${g};${b}m`, close: '\x1B[49m' }) : () => noColorProps, | ||
}; |
@@ -39,3 +39,2 @@ interface StyleProperties { | ||
* @param {number} code in range [0, 255]. | ||
* @return {AnsisInstance} | ||
*/ | ||
@@ -45,2 +44,8 @@ ansi256: (code: number) => AnsisInstance; | ||
/** | ||
* Alias to ansi256. | ||
* @param {number} code in range [0, 255]. | ||
*/ | ||
ansi: (code: number) => AnsisInstance; | ||
/** | ||
* Set RGB values for foreground color. | ||
@@ -77,2 +82,8 @@ * | ||
/** | ||
* Alias to bgAnsi256. | ||
* @param {number} code in range [0, 255]. | ||
*/ | ||
bgAnsi: (code: number) => AnsisInstance; | ||
/** | ||
* Set RGB values for background color. | ||
@@ -79,0 +90,0 @@ * |
import { clamp, hexToRgb, strReplaceAll } from './utils.js'; | ||
import { ansiCodes } from './ansi-codes.js'; | ||
import { baseCodes, extendedCodes } from './ansi-codes.js'; | ||
/** | ||
* All methods are implemented in prototype of the `styleProxy` object. | ||
* Note: all methods are implemented in prototype of the `styleProxy` object. | ||
* @implements {AnsisInstance} | ||
@@ -76,4 +76,4 @@ */ | ||
*/ | ||
for (let name in ansiCodes) { | ||
const { open, close } = ansiCodes[name]; | ||
for (let name in baseCodes) { | ||
const { open, close } = baseCodes[name]; | ||
styles[name] = { | ||
@@ -102,5 +102,6 @@ get() { | ||
get() { | ||
return (num) => { | ||
num = clamp(num, 0, 255); | ||
return createStyle(`\x1B[38;5;${num}m`, '\x1B[39m', this.props); | ||
return (code) => { | ||
code = clamp(code, 0, 255); | ||
const { open, close } = extendedCodes.ansi256(code); | ||
return createStyle(open, close, this.props); | ||
}; | ||
@@ -111,2 +112,8 @@ }, | ||
/** | ||
* Alias to ansi256. | ||
* @type {AnsisInstance.ansi256} | ||
*/ | ||
styles.ansi = styles.ansi256; | ||
/** | ||
* @type {AnsisInstance.bgAnsi256} | ||
@@ -116,5 +123,6 @@ */ | ||
get() { | ||
return (num) => { | ||
num = clamp(num, 0, 255); | ||
return createStyle(`\x1B[48;5;${num}m`, '\x1B[49m', this.props); | ||
return (code) => { | ||
code = clamp(code, 0, 255); | ||
const { open, close } = extendedCodes.bgAnsi256(code); | ||
return createStyle(open, close, this.props); | ||
}; | ||
@@ -125,2 +133,8 @@ }, | ||
/** | ||
* Alias to bgAnsi256. | ||
* @type {AnsisInstance.bgAnsi256} | ||
*/ | ||
styles.bgAnsi = styles.bgAnsi256; | ||
/** | ||
* @type {AnsisInstance.rgb} | ||
@@ -134,3 +148,4 @@ */ | ||
b = clamp(b, 0, 255); | ||
return createStyle(`\x1B[38;2;${r};${g};${b}m`, '\x1B[39m', this.props); | ||
const { open, close } = extendedCodes.rgb(r, g, b); | ||
return createStyle(open, close, this.props); | ||
}; | ||
@@ -146,4 +161,4 @@ }, | ||
return (hex) => { | ||
const [r, g, b] = hexToRgb(hex); | ||
return createStyle(`\x1B[38;2;${r};${g};${b}m`, '\x1B[39m', this.props); | ||
const { open, close } = extendedCodes.rgb(...hexToRgb(hex)); | ||
return createStyle(open, close, this.props); | ||
}; | ||
@@ -162,3 +177,4 @@ }, | ||
b = clamp(b, 0, 255); | ||
return createStyle(`\x1B[48;2;${r};${g};${b}m`, '\x1B[49m', this.props); | ||
const { open, close } = extendedCodes.bgRgb(r, g, b); | ||
return createStyle(open, close, this.props); | ||
}; | ||
@@ -174,4 +190,4 @@ }, | ||
return (hex) => { | ||
const [r, g, b] = hexToRgb(hex); | ||
return createStyle(`\x1B[48;2;${r};${g};${b}m`, '\x1B[49m', this.props); | ||
const { open, close } = extendedCodes.bgRgb(...hexToRgb(hex)); | ||
return createStyle(open, close, this.props); | ||
}; | ||
@@ -178,0 +194,0 @@ }, |
@@ -1,18 +0,1 @@ | ||
import tty from 'tty'; | ||
// todo Add supports NO_COLOR | ||
// export const isSupported = () => { | ||
// if (!process) return false; | ||
// | ||
// const env = process.env || {}; | ||
// const argv = process.argv || []; | ||
// const isDisabled = 'NO_COLOR' in env || argv.includes('--no-color'); | ||
// const isForced = 'FORCE_COLOR' in env || argv.includes('--color'); | ||
// | ||
// const isCompatibleTerminal = (tty.isatty(1) && env.TERM && env.TERM !== 'dumb') || process.platform === 'win32'; | ||
// const isCI = 'CI' in env; | ||
// | ||
// return !isDisabled && (isForced || isCompatibleTerminal || isCI); | ||
// }; | ||
/** | ||
@@ -19,0 +2,0 @@ * Convert hex color string to RGB values. |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
33378
388
541