@sayknow-cli/utils 0.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/types/abortable.d.ts +27 -0
- package/dist/types/async.d.ts +6 -0
- package/dist/types/cli.d.ts +118 -0
- package/dist/types/color.d.ts +82 -0
- package/dist/types/dirs.d.ts +163 -0
- package/dist/types/env.d.ts +68 -0
- package/dist/types/fetch-retry.d.ts +80 -0
- package/dist/types/format.d.ts +37 -0
- package/dist/types/frontmatter.d.ts +25 -0
- package/dist/types/fs-error.d.ts +31 -0
- package/dist/types/glob.d.ts +28 -0
- package/dist/types/hook-fetch.d.ts +16 -0
- package/dist/types/index.d.ts +30 -0
- package/dist/types/json.d.ts +4 -0
- package/dist/types/logger.d.ts +66 -0
- package/dist/types/mermaid-ascii.d.ts +11 -0
- package/dist/types/mime.d.ts +29 -0
- package/dist/types/peek-file.d.ts +9 -0
- package/dist/types/postmortem.d.ts +29 -0
- package/dist/types/procmgr.d.ts +35 -0
- package/dist/types/prompt.d.ts +18 -0
- package/dist/types/ptree.d.ts +108 -0
- package/dist/types/ring.d.ts +93 -0
- package/dist/types/safe-stderr.d.ts +1 -0
- package/dist/types/sanitize-text.d.ts +14 -0
- package/dist/types/snowflake.d.ts +25 -0
- package/dist/types/spawn-env.d.ts +4 -0
- package/dist/types/stream.d.ts +68 -0
- package/dist/types/tab-spacing.d.ts +9 -0
- package/dist/types/temp.d.ts +14 -0
- package/dist/types/type-guards.d.ts +3 -0
- package/dist/types/which.d.ts +37 -0
- package/package.json +61 -0
- package/src/abortable.ts +73 -0
- package/src/async.ts +50 -0
- package/src/cli.ts +439 -0
- package/src/color.ts +204 -0
- package/src/dirs.ts +539 -0
- package/src/env.ts +278 -0
- package/src/fetch-retry.ts +298 -0
- package/src/format.ts +112 -0
- package/src/frontmatter.ts +154 -0
- package/src/fs-error.ts +56 -0
- package/src/glob.ts +189 -0
- package/src/hook-fetch.ts +30 -0
- package/src/index.ts +50 -0
- package/src/json.ts +10 -0
- package/src/logger.ts +392 -0
- package/src/mermaid-ascii.ts +31 -0
- package/src/mime.ts +159 -0
- package/src/peek-file.ts +114 -0
- package/src/postmortem.ts +197 -0
- package/src/procmgr.ts +209 -0
- package/src/prompt.ts +471 -0
- package/src/ptree.ts +390 -0
- package/src/ring.ts +169 -0
- package/src/safe-stderr.ts +15 -0
- package/src/sanitize-text.ts +38 -0
- package/src/snowflake.ts +136 -0
- package/src/spawn-env.ts +23 -0
- package/src/stream.ts +403 -0
- package/src/tab-spacing.ts +312 -0
- package/src/temp.ts +77 -0
- package/src/type-guards.ts +11 -0
- package/src/which.ts +232 -0
package/src/color.ts
ADDED
|
@@ -0,0 +1,204 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Color manipulation utilities for hex colors.
|
|
3
|
+
*
|
|
4
|
+
* @example
|
|
5
|
+
* ```ts
|
|
6
|
+
* import { hexToHsv, hsvToHex } from "@sayknow-cli/utils";
|
|
7
|
+
*
|
|
8
|
+
* // Work with HSV directly
|
|
9
|
+
*
|
|
10
|
+
* // Or work with HSV directly
|
|
11
|
+
* const hsv = hexToHsv("#4ade80");
|
|
12
|
+
* hsv.h = (hsv.h + 90) % 360;
|
|
13
|
+
* const newHex = hsvToHex(hsv);
|
|
14
|
+
* ```
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
export interface HSV {
|
|
18
|
+
/** Hue in degrees (0-360) */
|
|
19
|
+
h: number;
|
|
20
|
+
/** Saturation (0-1) */
|
|
21
|
+
s: number;
|
|
22
|
+
/** Value/brightness (0-1) */
|
|
23
|
+
v: number;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
export interface RGB {
|
|
27
|
+
/** Red (0-255) */
|
|
28
|
+
r: number;
|
|
29
|
+
/** Green (0-255) */
|
|
30
|
+
g: number;
|
|
31
|
+
/** Blue (0-255) */
|
|
32
|
+
b: number;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* Parse a hex color string to RGB.
|
|
37
|
+
* Supports #RGB, #RRGGBB formats.
|
|
38
|
+
*/
|
|
39
|
+
export function hexToRgb(hex: string): RGB {
|
|
40
|
+
const h = hex.startsWith("#") ? hex.slice(1) : hex;
|
|
41
|
+
if (h.length === 3) {
|
|
42
|
+
return {
|
|
43
|
+
r: parseInt(h[0] + h[0], 16),
|
|
44
|
+
g: parseInt(h[1] + h[1], 16),
|
|
45
|
+
b: parseInt(h[2] + h[2], 16),
|
|
46
|
+
};
|
|
47
|
+
}
|
|
48
|
+
return {
|
|
49
|
+
r: parseInt(h.slice(0, 2), 16),
|
|
50
|
+
g: parseInt(h.slice(2, 4), 16),
|
|
51
|
+
b: parseInt(h.slice(4, 6), 16),
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Convert RGB to hex color string.
|
|
57
|
+
*/
|
|
58
|
+
export function rgbToHex(rgb: RGB): string {
|
|
59
|
+
const toHex = (n: number) =>
|
|
60
|
+
Math.max(0, Math.min(255, Math.round(n)))
|
|
61
|
+
.toString(16)
|
|
62
|
+
.padStart(2, "0");
|
|
63
|
+
return `#${toHex(rgb.r)}${toHex(rgb.g)}${toHex(rgb.b)}`;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
/**
|
|
67
|
+
* Convert RGB to HSV.
|
|
68
|
+
*/
|
|
69
|
+
export function rgbToHsv(rgb: RGB): HSV {
|
|
70
|
+
const r = rgb.r / 255;
|
|
71
|
+
const g = rgb.g / 255;
|
|
72
|
+
const b = rgb.b / 255;
|
|
73
|
+
|
|
74
|
+
const max = Math.max(r, g, b);
|
|
75
|
+
const min = Math.min(r, g, b);
|
|
76
|
+
const d = max - min;
|
|
77
|
+
|
|
78
|
+
let h = 0;
|
|
79
|
+
if (d !== 0) {
|
|
80
|
+
if (max === r) h = ((g - b) / d + (g < b ? 6 : 0)) / 6;
|
|
81
|
+
else if (max === g) h = ((b - r) / d + 2) / 6;
|
|
82
|
+
else h = ((r - g) / d + 4) / 6;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
return {
|
|
86
|
+
h: h * 360,
|
|
87
|
+
s: max === 0 ? 0 : d / max,
|
|
88
|
+
v: max,
|
|
89
|
+
};
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
/**
|
|
93
|
+
* Convert HSV to RGB.
|
|
94
|
+
*/
|
|
95
|
+
export function hsvToRgb(hsv: HSV): RGB {
|
|
96
|
+
const { s, v } = hsv;
|
|
97
|
+
const h = ((hsv.h % 360) + 360) % 360; // Normalize to 0-360
|
|
98
|
+
|
|
99
|
+
const i = Math.floor(h / 60);
|
|
100
|
+
const f = h / 60 - i;
|
|
101
|
+
const p = v * (1 - s);
|
|
102
|
+
const q = v * (1 - f * s);
|
|
103
|
+
const t = v * (1 - (1 - f) * s);
|
|
104
|
+
|
|
105
|
+
let r: number, g: number, b: number;
|
|
106
|
+
switch (i % 6) {
|
|
107
|
+
case 0:
|
|
108
|
+
r = v;
|
|
109
|
+
g = t;
|
|
110
|
+
b = p;
|
|
111
|
+
break;
|
|
112
|
+
case 1:
|
|
113
|
+
r = q;
|
|
114
|
+
g = v;
|
|
115
|
+
b = p;
|
|
116
|
+
break;
|
|
117
|
+
case 2:
|
|
118
|
+
r = p;
|
|
119
|
+
g = v;
|
|
120
|
+
b = t;
|
|
121
|
+
break;
|
|
122
|
+
case 3:
|
|
123
|
+
r = p;
|
|
124
|
+
g = q;
|
|
125
|
+
b = v;
|
|
126
|
+
break;
|
|
127
|
+
case 4:
|
|
128
|
+
r = t;
|
|
129
|
+
g = p;
|
|
130
|
+
b = v;
|
|
131
|
+
break;
|
|
132
|
+
default:
|
|
133
|
+
r = v;
|
|
134
|
+
g = p;
|
|
135
|
+
b = q;
|
|
136
|
+
break;
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
return {
|
|
140
|
+
r: Math.round(r * 255),
|
|
141
|
+
g: Math.round(g * 255),
|
|
142
|
+
b: Math.round(b * 255),
|
|
143
|
+
};
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
/**
|
|
147
|
+
* Convert hex color to HSV.
|
|
148
|
+
*/
|
|
149
|
+
export function hexToHsv(hex: string): HSV {
|
|
150
|
+
return rgbToHsv(hexToRgb(hex));
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* Convert HSV to hex color.
|
|
155
|
+
*/
|
|
156
|
+
export function hsvToHex(hsv: HSV): string {
|
|
157
|
+
return rgbToHex(hsvToRgb(hsv));
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
/**
|
|
161
|
+
* Shift the hue of a hex color by a given number of degrees.
|
|
162
|
+
*/
|
|
163
|
+
export function shiftHue(hex: string, degrees: number): string {
|
|
164
|
+
const hsv = hexToHsv(hex);
|
|
165
|
+
hsv.h = (hsv.h + degrees) % 360;
|
|
166
|
+
if (hsv.h < 0) hsv.h += 360;
|
|
167
|
+
return hsvToHex(hsv);
|
|
168
|
+
}
|
|
169
|
+
export interface HSVAdjustment {
|
|
170
|
+
/** Hue shift in degrees (additive) */
|
|
171
|
+
h?: number;
|
|
172
|
+
/** Saturation multiplier */
|
|
173
|
+
s?: number;
|
|
174
|
+
/** Value/brightness multiplier */
|
|
175
|
+
v?: number;
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/**
|
|
179
|
+
* Adjust HSV components of a hex color.
|
|
180
|
+
*
|
|
181
|
+
* @param hex - Hex color string (#RGB or #RRGGBB)
|
|
182
|
+
* @param adj - Adjustments: h is additive degrees, s and v are multipliers
|
|
183
|
+
* @returns New hex color string
|
|
184
|
+
*
|
|
185
|
+
* @example
|
|
186
|
+
* ```ts
|
|
187
|
+
* // Shift hue +60°, reduce saturation to 71%
|
|
188
|
+
* adjustHsv("#00ff88", { h: 60, s: 0.71 }) // "#4a9eff"
|
|
189
|
+
* ```
|
|
190
|
+
*/
|
|
191
|
+
export function adjustHsv(hex: string, adj: HSVAdjustment): string {
|
|
192
|
+
const hsv = hexToHsv(hex);
|
|
193
|
+
if (adj.h !== undefined) {
|
|
194
|
+
hsv.h = (hsv.h + adj.h) % 360;
|
|
195
|
+
if (hsv.h < 0) hsv.h += 360;
|
|
196
|
+
}
|
|
197
|
+
if (adj.s !== undefined) {
|
|
198
|
+
hsv.s = Math.max(0, Math.min(1, hsv.s * adj.s));
|
|
199
|
+
}
|
|
200
|
+
if (adj.v !== undefined) {
|
|
201
|
+
hsv.v = Math.max(0, Math.min(1, hsv.v * adj.v));
|
|
202
|
+
}
|
|
203
|
+
return hsvToHex(hsv);
|
|
204
|
+
}
|