简易版chalk

简易版chalk

参考文档

  • chalk/chalk: 🖍 Terminal string styling done right (github.com)

  • 【MINI 系列】五颜六色的控制台)

  • ANSI转义序列 - 维基百科,自由的百科全书 (wikipedia.org)

“ANSI 转义序列(ANSI escape sequences)是一种带内信号的转义序列标准,用于控制视频文本终端上的光标位置、颜色和其他选项。在文本中嵌入确定的字节序列,大部分以 ESC 转义字符和"["字符开始,终端会把这些字节序列解释为相应的指令,而不是普通的字符编码。”

根据描述我们知道需要使用一些特殊的转义字符来实现不同字体风格、颜色、背景色。

1、字体风格

根据wiki选择图形再现(SGR)参数的描述编写 Ansi 码表,同时获取一下码表的key

在这里插入图片描述

/*** ESC 按键的 Ansi 码*/
export const ESC_CODE: string = "\u001B"/*** 图形再现参数的 Ansi 码表1(开启)*/
const Style1 = {// 前景色'foreground': '38;2;',// 背景色'background': '48;2;',// 加粗'bold': '1',// 暗淡'dim': '2',// 倾斜'italic': '3',// 下划线'underline': '4',// 闪烁'flick': '5',// 快速闪烁'fast_flick': '6',// 反转'inverse': '7',// 隐藏'hidden': '8',// 删除线'strikethrough': '9',// 上划线'overline': '53',
};/*** 图形再现参数的 Ansi 码表2(关闭)*/
const Style2 = {// 前景色'foreground': '39',// 背景色'background': '49',// 加粗'bold': '22',// 暗淡'dim': '22',// 倾斜'italic': '23',// 下划线'underline': '24',// 闪烁'flick': '25',// 快速闪烁'fast_flick': '25',// 反转'inverse': '27',// 隐藏'hidden': '28',// 删除线'strikethrough': '29',// 上划线'overline': '55',
};export type Style1 = keyof typeof Style1
export const EscapeSequence1 = (key: Style1, ...args: any[]) => {const code = Style1[key];// return String.raw`${ESC_CODE}[${code}${args.join(';')}m`;return `${ESC_CODE}[${code}${args.join(';')}m`;
}export type Style2 = keyof typeof Style2
export const EscapeSequence2 = (key: Style2) => {const code = Style2[key]// return String.raw`${ESC_CODE}[${code}m`;return `${ESC_CODE}[${code}m`;
}export type Styles = Style1 & Style2

2、颜色

这里不再像chalk一样支持3/4位颜色、8位颜色,而是仅仅支持真彩色(TrueColor),根据wiki颜色的描述补充 Ansi 码表的foregroundbackground

在这里插入图片描述

这里需要先判断一下终端是否支持真彩色(并未给出所有平台的判断方案)。

import process from "node:process";
import os from "node:os";
import {execSync} from 'child_process';/*** 判断是否支持当前环境是否支持 TrueColor* @returns {boolean} 是否支持 TrueColor*/
export default (): boolean => {if (process.platform === 'win32') {// Windows 10 build 14931 is the first release that supports 16m/TrueColor.const osRelease = os.release().split('.');return Number(osRelease[0]) >= 10 && Number(osRelease[2]) >= 14_931;} else if (process.platform === 'darwin') {const result = execSync('tput colors');const numColors = parseInt(result.toString().trim(), 10);return numColors >= 256;}return false;
}

颜色名称根据 CSS3 种的 147 个名称去定义。

/*** CSS3 标准中的 147 中颜色定义*/
export const ColorMapping = {"aliceblue": "#f0f8ff","antiquewhite": "#faebd7","aqua": "#00ffff","aquamarine": "#7fffd4","azure": "#f0ffff","beige": "#f5f5dc","bisque": "#ffe4c4","black": "#000000","blanchedalmond": "#ffebcd","blue": "#0000ff","blueviolet": "#8a2be2","brown": "#a52a2a","burlywood": "#deb887","cadetblue": "#5f9ea0","chartreuse": "#7fff00","chocolate": "#d2691e","coral": "#ff7f50","cornflowerblue": "#6495ed","cornsilk": "#fff8dc","crimson": "#dc143c","cyan": "#00ffff","darkblue": "#00008b","darkcyan": "#008b8b","darkgoldenrod": "#b8860b","darkgray": "#a9a9a9","darkgreen": "#006400","darkgrey": "#a9a9a9","darkkhaki": "#bdb76b","darkmagenta": "#8b008b","darkolivegreen": "#556b2f","darkorange": "#ff8c00","darkorchid": "#9932cc","darkred": "#8b0000","darksalmon": "#e9967a","darkseagreen": "#8fbc8f","darkslateblue": "#483d8b","darkslategray": "#2f4f4f","darkslategrey": "#2f4f4f","darkturquoise": "#00ced1","darkviolet": "#9400d3","deeppink": "#ff1493","deepskyblue": "#00bfff","dimgray": "#696969","dimgrey": "#696969","dodgerblue": "#1e90ff","firebrick": "#b22222","floralwhite": "#fffaf0","forestgreen": "#228b22","fuchsia": "#ff00ff","gainsboro": "#dcdcdc","ghostwhite": "#f8f8ff","gold": "#ffd700","goldenrod": "#daa520","gray": "#808080","green": "#008000","greenyellow": "#adff2f","grey": "#808080","honeydew": "#f0fff0","hotpink": "#ff69b4","indianred": "#cd5c5c","indigo": "#4b0082","ivory": "#fffff0","khaki": "#f0e68c","lavender": "#e6e6fa","lavenderblush": "#fff0f5","lawngreen": "#7cfc00","lemonchiffon": "#fffacd","lightblue": "#add8e6","lightcoral": "#f08080","lightcyan": "#e0ffff","lightgoldenrodyellow": "#fafad2","lightgray": "#d3d3d3","lightgreen": "#90ee90","lightgrey": "#d3d3d3","lightpink": "#ffb6c1","lightsalmon": "#ffa07a","lightseagreen": "#20b2aa","lightskyblue": "#87cefa","lightslategray": "#778899","lightslategrey": "#778899","lightsteelblue": "#b0c4de","lightyellow": "#ffffe0","lime": "#00ff00","limegreen": "#32cd32","linen": "#faf0e6","magenta": "#ff00ff","maroon": "#800000","mediumaquamarine": "#66cdaa","mediumblue": "#0000cd","mediumorchid": "#ba55d3","mediumpurple": "#9370db","mediumseagreen": "#3cb371","mediumslateblue": "#7b68ee","mediumspringgreen": "#00fa9a","mediumturquoise": "#48d1cc","mediumvioletred": "#c71585","midnightblue": "#191970","mintcream": "#f5fffa","mistyrose": "#ffe4e1","moccasin": "#ffe4b5","navajowhite": "#ffdead","navy": "#000080","oldlace": "#fdf5e6","olive": "#808000","olivedrab": "#6b8e23","orange": "#ffa500","orangered": "#ff4500","orchid": "#da70d6","palegoldenrod": "#eee8aa","palegreen": "#98fb98","paleturquoise": "#afeeee","palevioletred": "#db7093","papayawhip": "#ffefd5","peachpuff": "#ffdab9","peru": "#cd853f","pink": "#ffc0cb","plum": "#dda0dd","powderblue": "#b0e0e6","purple": "#800080","red": "#ff0000","rosybrown": "#bc8f8f","royalblue": "#4169e1","saddlebrown": "#8b4513","salmon": "#fa8072","sandybrown": "#f4a460","seagreen": "#2e8b57","seashell": "#fff5ee","sienna": "#a0522d","silver": "#c0c0c0","skyblue": "#87ceeb","slateblue": "#6a5acd","slategray": "#708090","slategrey": "#708090","snow": "#fffafa","springgreen": "#00ff7f","steelblue": "#4682b4","tan": "#d2b48c","teal": "#008080","thistle": "#d8bfd8","tomato": "#ff6347","turquoise": "#40e0d0","violet": "#ee82ee","wheat": "#f5deb3","white": "#ffffff","whitesmoke": "#f5f5f5","yellow": "#ffff00","yellowgreen": "#9acd32"
}export type Colors = keyof typeof ColorMappingexport const isColorName = (str: string) => {return (str in ColorMapping);
}

根据wiki上的描述,需要把16进制的颜色转换为RGB才能正确的设置样式,这里需要写一个工具类。

/*** 将16进制的颜色转换为RGB返回* @param hex - 16进制的颜色* @returns {number, number, number} 16进制的颜色的RGB表示*/
export const hexToRgb = (hex: string) => {const matches = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(hex)!;return {r: parseInt(matches[1], 16),g: parseInt(matches[2], 16),b: parseInt(matches[3], 16)}
}

3、实现简易版chalk

import supportTrueColor from "./supportTrueColor.js";
import {EscapeSequence1, EscapeSequence2, Styles} from "./ansi.js";
import {ColorMapping, Colors, isColorName} from "./color.js";
import {hexToRgb} from "./utils.js";type colorType = "foreground" | "background"export class Chalk {private prefix: stringprivate suffix: stringconstructor() {if (!supportTrueColor()) {throw new Error("Not Supported TrueColor!")}this.prefix = ''this.suffix = ''}private escapeSequence(key: Styles, ...args: any[]) {this.prefix += EscapeSequence1(key, ...args)this.suffix += EscapeSequence2(key)}private rgb(t: colorType, r: number, g: number, b: number): this;private rgb(t: colorType, r: number, g: number, b: number, ...args: string[]): string;private rgb(t: colorType, r: number, g: number, b: number, ...args: string[]): string | this {this.escapeSequence(t as Styles, r, g, b);if (args.length > 0) {return this.build(...args);}return this;}build(...args: string[]) {const text = this.prefix + args.join(' ') + this.suffix;this.prefix = ''this.suffix = ''return text;}// stylestyle(s: Styles): this;style(s: Styles, ...args: string[]): string;style(s: Styles, ...args: string[]): string | this {this.escapeSequence(s)if (args.length > 0) {return this.build(...args);}return this;}// colorcolor(name: Colors): this;color(name: Colors, ...args: string[]): string;color(name: string): this;color(name: string, ...args: string[]): string;color(name: Colors | string, ...args: string[]): string | this {const {r, g, b} = isColorName(name) ? hexToRgb(ColorMapping[name as Colors]) : hexToRgb(name);return this.rgb("foreground", r, g, b, ...args)}// bgColorbgColor(name: Colors): this;bgColor(name: Colors, ...args: string[]): string;bgColor(name: string): this;bgColor(name: string, ...args: string[]): string;bgColor(name: Colors | string, ...args: string[]): string | this {const {r, g, b} = isColorName(name) ? hexToRgb(ColorMapping[name as Colors]) : hexToRgb(name);return this.rgb("background", r, g, b, ...args)}
}export default new Chalk();// const chalk = new Chalk();
// console.log(chalk.color("#ff9600").bgColor("skyblue").style("bold", "hello chalk!"));
// console.log(chalk.color("red").bgColor("pink").style("bold").build("hello chalk!"));

最后贴一下项目地址:https://github.com/xumeng03/chalk

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/235309.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

LangChain - 02 - 快速开始之模型提示和解析

参考 LangSmith Many of the applications you build with LangChain will contain multiple steps with multiple invocations of LLM calls. As these applications get more and more complex, it becomes crucial to be able to inspect what exactly is going on inside …

轻度听力损失的儿童需要早期干预吗?

一些宝宝在做听力筛查时总是不通过,进一步听力诊断发现宝宝有轻度的听力损失,刚知道这个消息时,家长可担心了,总想着宝宝是不是听不到啊?但是一段时间后,有些家长又会忽略宝宝的听力问题,因为部…

探索 Vuex 的世界:状态管理的新视角(下)

🤍 前端开发工程师(主业)、技术博主(副业)、已过CET6 🍨 阿珊和她的猫_CSDN个人主页 🕠 牛客高级专题作者、在牛客打造高质量专栏《前端面试必备》 🍚 蓝桥云课签约作者、已在蓝桥云…

PyQt6 QColorDialog颜色对话框控件

锋哥原创的PyQt6视频教程: 2024版 PyQt6 Python桌面开发 视频教程(无废话版) 玩命更新中~_哔哩哔哩_bilibili2024版 PyQt6 Python桌面开发 视频教程(无废话版) 玩命更新中~共计50条视频,包括:2024版 PyQt6 Python桌面开发 视频教程(无废话版…

基于SSM框架的电脑测评系统论文

基于 SSM框架的电脑测评系统 摘要 随着信息技术在管理上越来越深入而广泛的应用,作为一个一般的用户都开始注重与自己的信息展示平台,实现基于SSM框架的电脑测评系统在技术上已成熟。本文介绍了基于SSM框架的电脑测评系统的开发全过程。通过分析用户对于…

大数据HCIE成神之路之数据预处理(3)——数值离散化

数值离散化 1.1 无监督连续变量的离散化 – 聚类划分1.1.1 实验任务1.1.1.1 实验背景1.1.1.2 实验目标1.1.1.3 实验数据解析 1.1.2 实验思路1.1.3 实验操作步骤1.1.4 结果验证 1.2 无监督连续变量的离散化 – 等宽划分1.2.1 实验任务1.2.1.1 实验背景1.2.1.2 实验目标1.2.1.3 实…

Open5GSUeRANSim2:对安装在同一个VM上的OPEN5GS和UERANSIM进行配置和抓取wireshark报文

参考链接: Configuring SCTP & NGAP with UERANSIM and Open5GS on a Single VM for the Open5GS & UERANSIM Series https://www.youtube.com/watch?vINgEX5L5fkE&listPLZqpS76PykwIoqMdUt6noAor7eJw83bbp&index5 Configuring RRC with UERANSI…

泛微e-cology XmlRpcServlet文件读取漏洞复现

漏洞介绍 泛微新一代移动办公平台e-cology不仅组织提供了一体化的协同工作平台,将组织事务逐渐实现全程电子化,改变传统纸质文件、实体签章的方式。泛微OA E-Cology 平台XmRpcServlet接口处存在任意文件读取漏洞,攻击者可通过该漏洞读取系统重要文件 (如数据库配置…

fastadmin表格右侧操作栏增加审核成功和审核失败按钮,点击提交ajax到后端

fastadmin表格右侧操作栏增加审核成功和审核失败按钮,点击提交ajax到后端 效果如下 js {field: operate, title: __(Operate), table: table, events

Linux c++开发-11-Socket TCP编程简单案例

服务端&#xff1a; #include <stdio.h> #include <stdlib.h> #include <string.h> #include <unistd.h> #include <netinet/in.h> #include <sys/types.h>#include <errno.h>int main(void) {//1.socketint server_sock socket(A…

传统行业与人工智能融合:材料、化学、物理、生物的发展与未来展望

导言 传统行业如材料科学、化学、物理、生物学一直是科学领域的重要支柱。随着人工智能的快速发展&#xff0c;这些领域也在不断融合创新。本文将深入研究这些领域与人工智能的发展过程、遇到的问题及解决过程、未来的可用范围&#xff0c;以及在各国的应用和未来的研究趋势。 …

【uniapp】uniapp中本地存储sqlite数据库保姆级使用教程(附完整代码和注释)

数据库请求接口封装 uniapp中提供了plus.sqlite接口&#xff0c;在这里我们对常用的数据库请求操作进行了二次封装 这里的dbName、dbPath、recordsTable 可以根据你的需求自己命名 module.exports {/** * type {String} 数据库名称*/dbName: salary,/*** 数据库地址* type {…

【【迭代七次的CORDIC算法-Verilog实现】】

迭代七次的CORDIC算法-Verilog实现求解正弦余弦函数 COEDIC.v module CORDIC #(parameter DATA_WIDTH 4d8 , // we set data widthparameter PIPELINE 4d8)(input clk ,input …

深入理解 Nginx 工作原理:Master-Worker 架构与性能优化

目录 前言1 Nginx 的 Master-Worker 架构2 Worker 进程的工作原理3 Master-Worker 架构的优势3.1 热部署的便利性3.2 进程间独立性3.3 系统稳定性和容错性提升3.4 系统风险降低 4 Worker 数量的设置5 Worker 连接数&#xff08;worker_connections&#xff09;结语 前言 Nginx…

nodejs微信小程序+python+PHP购物商城网站-计算机毕业设计推荐

目 录 摘 要 I ABSTRACT II 目 录 II 第1章 绪论 1 1.1背景及意义 1 1.2 国内外研究概况 1 1.3 研究的内容 1 第2章 相关技术 3 2.1 nodejs简介 4 2.2 express框架介绍 6 2.4 MySQL数据库 4 第3章 系统分析 5 3.1 需求分析 5 3.2 系统可行性分析 5 3.2.1技术可行性&#xff1a;…

Ubuntu 常用命令之 tar 命令用法介绍

tar 命令在 Ubuntu 系统中是用来打包和解包文件的工具。tar 命令可以将多个文件或目录打包成一个 tar 文件&#xff0c;也可以将 tar 文件解包成原来的文件或目录。 tar 命令的常用参数如下 c&#xff1a;创建一个新的 tar 文件。x&#xff1a;从 tar 文件中提取文件。v&…

198|鸭的喜剧,也是蝌蚪的悲剧

​ 第一次读鲁迅的《鸭的喜剧》&#xff0c;平平淡淡的文字&#xff0c;没有一丝辛辣&#xff0c;讲了一个给小朋友的故事。如果不知道&#xff0c;都不会觉得这是鲁迅的作品。 故事很简单&#xff1a;友人先是买了蝌蚪&#xff0c;想等蝌蚪长大听蛙鸣&#xff1b;后来买了四只…

机器学习之逻辑回归,一文掌握逻辑回归算法知识文集

&#x1f3c6;作者简介&#xff0c;普修罗双战士&#xff0c;一直追求不断学习和成长&#xff0c;在技术的道路上持续探索和实践。 &#x1f3c6;多年互联网行业从业经验&#xff0c;历任核心研发工程师&#xff0c;项目技术负责人。 &#x1f389;欢迎 &#x1f44d;点赞✍评论…

H5聊天系统聊天网站源码 群聊源码 无限建群创群

H5聊天系统聊天网站源码 群聊源码 无限建群创群 1.支持自助建群 管理群 修改群资料 2.支持自动登录 登陆成功可自助修改资料 3.后台可查看群组聊天消息记录 4.支持表情 动态表情 图片发布 5.支持消息语音提醒 测试环境&#xff1a;NginxMySQL5.6PHP5.6 1.将压缩包解压到…

VueCron使用方法

1&#xff09;什么是vueCron Vue Cron 是基于 Vue.js 的定时任务管理组件&#xff0c;它提供了一种简单易用的方式来设定和管理定时任务。Vue Cron 提供了一个类似于 Linux crontab 的界面&#xff0c;用户可以通过它来创建、编辑和删除定时任务。 2&#xff09;安装依赖及应…