@basiclines/rampa 1.0.1 → 1.1.1
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/README.md +37 -1
- package/dist/index.js +90 -15
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -4,6 +4,19 @@ Generate mathematically accurate, accessible color palettes from a base color.
|
|
|
4
4
|
|
|
5
5
|
## Installation
|
|
6
6
|
|
|
7
|
+
### npm
|
|
8
|
+
|
|
9
|
+
```bash
|
|
10
|
+
npx @basiclines/rampa -C "#3b82f6"
|
|
11
|
+
```
|
|
12
|
+
|
|
13
|
+
Or install globally:
|
|
14
|
+
|
|
15
|
+
```bash
|
|
16
|
+
npm install -g @basiclines/rampa
|
|
17
|
+
rampa -C "#3b82f6"
|
|
18
|
+
```
|
|
19
|
+
|
|
7
20
|
### Homebrew (macOS/Linux)
|
|
8
21
|
|
|
9
22
|
```bash
|
|
@@ -44,6 +57,9 @@ rampa -C "#3b82f6" --size=5 -L 10:90
|
|
|
44
57
|
# Add complementary harmony
|
|
45
58
|
rampa -C "#3b82f6" --add=complementary
|
|
46
59
|
|
|
60
|
+
# Add hue-shifted ramp (45 degrees)
|
|
61
|
+
rampa -C "#3b82f6" --add=shift:45
|
|
62
|
+
|
|
47
63
|
# Output as CSS variables
|
|
48
64
|
rampa -C "#3b82f6" --output=css
|
|
49
65
|
```
|
|
@@ -108,7 +124,14 @@ Available blend modes: `normal`, `multiply`, `screen`, `overlay`, `darken`, `lig
|
|
|
108
124
|
|------|-------------|
|
|
109
125
|
| `--add` | Add harmony ramp (repeatable) |
|
|
110
126
|
|
|
111
|
-
Available
|
|
127
|
+
Available types:
|
|
128
|
+
- `complementary` — Opposite on color wheel (+180°)
|
|
129
|
+
- `triadic` — 3 colors, 120° apart
|
|
130
|
+
- `analogous` — Adjacent colors, 30° apart
|
|
131
|
+
- `split-complementary` — 2 colors near opposite
|
|
132
|
+
- `square` — 4 colors, 90° apart
|
|
133
|
+
- `compound` — Complementary + split
|
|
134
|
+
- `shift:N` — Custom hue rotation by N degrees (e.g., `shift:45`, `shift:-30`)
|
|
112
135
|
|
|
113
136
|
### Output
|
|
114
137
|
|
|
@@ -150,6 +173,19 @@ rampa -C "#3b82f6" --tint-color="#FF0000" --tint-opacity=15 --tint-blend=overlay
|
|
|
150
173
|
rampa -C "#3b82f6" --add=complementary --add=triadic
|
|
151
174
|
```
|
|
152
175
|
|
|
176
|
+
### Custom Hue Shifts
|
|
177
|
+
|
|
178
|
+
```bash
|
|
179
|
+
# Warm shift (+45°)
|
|
180
|
+
rampa -C "#3b82f6" --add=shift:45
|
|
181
|
+
|
|
182
|
+
# Cool shift (-30°)
|
|
183
|
+
rampa -C "#3b82f6" --add=shift:-30
|
|
184
|
+
|
|
185
|
+
# Multiple shifts
|
|
186
|
+
rampa -C "#3b82f6" --add=shift:30 --add=shift:60 --add=shift:90
|
|
187
|
+
```
|
|
188
|
+
|
|
153
189
|
### JSON Output
|
|
154
190
|
|
|
155
191
|
```bash
|
package/dist/index.js
CHANGED
|
@@ -9897,6 +9897,41 @@ function formatCss2(ramps) {
|
|
|
9897
9897
|
`);
|
|
9898
9898
|
}
|
|
9899
9899
|
|
|
9900
|
+
// src/utils/terminal-colors.ts
|
|
9901
|
+
function hasLimitedColorSupport() {
|
|
9902
|
+
return process.env.TERM_PROGRAM === "Apple_Terminal";
|
|
9903
|
+
}
|
|
9904
|
+
function rgbTo256(r4, g3, b2) {
|
|
9905
|
+
if (r4 === g3 && g3 === b2) {
|
|
9906
|
+
if (r4 < 8)
|
|
9907
|
+
return 16;
|
|
9908
|
+
if (r4 > 248)
|
|
9909
|
+
return 231;
|
|
9910
|
+
return Math.round((r4 - 8) / 10) + 232;
|
|
9911
|
+
}
|
|
9912
|
+
const rIndex = Math.round(r4 / 255 * 5);
|
|
9913
|
+
const gIndex = Math.round(g3 / 255 * 5);
|
|
9914
|
+
const bIndex = Math.round(b2 / 255 * 5);
|
|
9915
|
+
return 16 + 36 * rIndex + 6 * gIndex + bIndex;
|
|
9916
|
+
}
|
|
9917
|
+
function coloredSquare(r4, g3, b2) {
|
|
9918
|
+
if (hasLimitedColorSupport()) {
|
|
9919
|
+
const colorCode = rgbTo256(r4, g3, b2);
|
|
9920
|
+
return `\x1B[38;5;${colorCode}m■\x1B[0m`;
|
|
9921
|
+
}
|
|
9922
|
+
return `\x1B[38;2;${r4};${g3};${b2}m■\x1B[0m`;
|
|
9923
|
+
}
|
|
9924
|
+
function getColorLimitationNote() {
|
|
9925
|
+
if (hasLimitedColorSupport()) {
|
|
9926
|
+
const dim = "\x1B[2m";
|
|
9927
|
+
const yellow = "\x1B[33m";
|
|
9928
|
+
const reset = "\x1B[0m";
|
|
9929
|
+
return `${yellow}Note:${reset} ${dim}Using 256-color mode. macOS Terminal.app has limited truecolor support.${reset}
|
|
9930
|
+
${dim}For accurate color previews, use iTerm2, Warp, kitty, or another truecolor terminal.${reset}`;
|
|
9931
|
+
}
|
|
9932
|
+
return null;
|
|
9933
|
+
}
|
|
9934
|
+
|
|
9900
9935
|
// src/index.ts
|
|
9901
9936
|
if (process.argv.includes("--help") || process.argv.includes("-h")) {
|
|
9902
9937
|
showHelp();
|
|
@@ -9906,7 +9941,7 @@ function showHelp() {
|
|
|
9906
9941
|
const dim = "\x1B[2m";
|
|
9907
9942
|
const reset = "\x1B[0m";
|
|
9908
9943
|
const help = `
|
|
9909
|
-
rampa v1.
|
|
9944
|
+
rampa v1.1.1
|
|
9910
9945
|
Generate mathematically accurate color palettes from a base color
|
|
9911
9946
|
|
|
9912
9947
|
USAGE
|
|
@@ -9944,7 +9979,7 @@ HARMONIES
|
|
|
9944
9979
|
${cyan}--add <type>${reset} ${dim}Add harmony ramp (can repeat)${reset}
|
|
9945
9980
|
|
|
9946
9981
|
${dim}Types: complementary, triadic, analogous,${reset}
|
|
9947
|
-
${dim}split-complementary, square, compound
|
|
9982
|
+
${dim}split-complementary, square, compound, shift:<degrees>${reset}
|
|
9948
9983
|
|
|
9949
9984
|
OUTPUT
|
|
9950
9985
|
${cyan}-O, --output <format>${reset} ${dim}Output format (default: text)${reset}
|
|
@@ -9960,6 +9995,7 @@ EXAMPLES
|
|
|
9960
9995
|
${cyan}rampa -C "#3b82f6"${reset}
|
|
9961
9996
|
${cyan}rampa -C "#3b82f6" --size=5 -L 10:90${reset}
|
|
9962
9997
|
${cyan}rampa -C "#3b82f6" --add=complementary --add=triadic${reset}
|
|
9998
|
+
${cyan}rampa -C "#3b82f6" --add=shift:45 --add=shift:90${reset}
|
|
9963
9999
|
${cyan}rampa -C "#3b82f6" -O css${reset}
|
|
9964
10000
|
${cyan}rampa -C "#3b82f6" --tint-color="#FF0000" --tint-opacity=15${reset}
|
|
9965
10001
|
`;
|
|
@@ -10077,16 +10113,19 @@ Examples:
|
|
|
10077
10113
|
rampa -C "#3b82f6" --tint-color="#FF0000" --tint-opacity=20 --tint-blend=screen
|
|
10078
10114
|
`,
|
|
10079
10115
|
add: `
|
|
10080
|
-
--add <
|
|
10116
|
+
--add <type> Add harmony ramps (can be used multiple times)
|
|
10081
10117
|
|
|
10082
|
-
Available
|
|
10118
|
+
Available types:
|
|
10083
10119
|
${HARMONY_TYPES.join(", ")}
|
|
10120
|
+
shift:<degrees> - Custom hue rotation (e.g., shift:45, shift:-30)
|
|
10084
10121
|
|
|
10085
10122
|
Examples:
|
|
10086
10123
|
rampa -C "#3b82f6" --add=complementary
|
|
10087
10124
|
rampa -C "#3b82f6" --add=triadic
|
|
10088
10125
|
rampa -C "#3b82f6" --add=complementary --add=analogous
|
|
10089
|
-
rampa -C "#3b82f6" --add=
|
|
10126
|
+
rampa -C "#3b82f6" --add=shift:45 # Warm shift
|
|
10127
|
+
rampa -C "#3b82f6" --add=shift:-30 # Cool shift
|
|
10128
|
+
rampa -C "#3b82f6" --add=shift:45 --add=shift:90
|
|
10090
10129
|
`,
|
|
10091
10130
|
output: `
|
|
10092
10131
|
--output, -O <format> Output format
|
|
@@ -10140,7 +10179,7 @@ var validFormats = ["hex", "hsl", "rgb", "oklch"];
|
|
|
10140
10179
|
var main = defineCommand({
|
|
10141
10180
|
meta: {
|
|
10142
10181
|
name: "rampa",
|
|
10143
|
-
version: "1.
|
|
10182
|
+
version: "1.1.1",
|
|
10144
10183
|
description: "Generate mathematically accurate color palettes from a base color"
|
|
10145
10184
|
},
|
|
10146
10185
|
args: {
|
|
@@ -10214,7 +10253,7 @@ var main = defineCommand({
|
|
|
10214
10253
|
},
|
|
10215
10254
|
add: {
|
|
10216
10255
|
type: "string",
|
|
10217
|
-
description: "Add harmony ramp (repeatable: complementary, triadic, etc.)"
|
|
10256
|
+
description: "Add harmony ramp (repeatable: complementary, triadic, shift:N, etc.)"
|
|
10218
10257
|
},
|
|
10219
10258
|
output: {
|
|
10220
10259
|
type: "string",
|
|
@@ -10334,14 +10373,29 @@ var main = defineCommand({
|
|
|
10334
10373
|
}
|
|
10335
10374
|
const addValues = args.add ? Array.isArray(args.add) ? args.add : [args.add] : [];
|
|
10336
10375
|
const harmonies = [];
|
|
10337
|
-
|
|
10338
|
-
|
|
10339
|
-
|
|
10376
|
+
const hueShifts = [];
|
|
10377
|
+
for (const value of addValues) {
|
|
10378
|
+
if (value.startsWith("shift:")) {
|
|
10379
|
+
const shiftStr = value.slice(6);
|
|
10380
|
+
const shift = parseFloat(shiftStr);
|
|
10381
|
+
if (isNaN(shift)) {
|
|
10382
|
+
console.error(`Error: Invalid shift value "${shiftStr}" - must be a number
|
|
10340
10383
|
`);
|
|
10341
|
-
|
|
10342
|
-
|
|
10343
|
-
|
|
10344
|
-
|
|
10384
|
+
showFlagHelp("add");
|
|
10385
|
+
}
|
|
10386
|
+
const normalized = (shift % 360 + 360) % 360;
|
|
10387
|
+
if (!hueShifts.includes(normalized)) {
|
|
10388
|
+
hueShifts.push(normalized);
|
|
10389
|
+
}
|
|
10390
|
+
} else {
|
|
10391
|
+
if (!isValidHarmonyType(value)) {
|
|
10392
|
+
console.error(`Error: Invalid harmony type "${value}"
|
|
10393
|
+
`);
|
|
10394
|
+
showFlagHelp("add");
|
|
10395
|
+
}
|
|
10396
|
+
if (!harmonies.includes(value)) {
|
|
10397
|
+
harmonies.push(value);
|
|
10398
|
+
}
|
|
10345
10399
|
}
|
|
10346
10400
|
}
|
|
10347
10401
|
if (!tintColor && tintOpacity > 0) {
|
|
@@ -10431,11 +10485,32 @@ var main = defineCommand({
|
|
|
10431
10485
|
});
|
|
10432
10486
|
});
|
|
10433
10487
|
}
|
|
10488
|
+
for (const shift of hueShifts) {
|
|
10489
|
+
const baseChroma = chroma_js_default(validatedColor);
|
|
10490
|
+
const [h2, s2, l2] = baseChroma.hsl();
|
|
10491
|
+
const shiftedHue = ((h2 || 0) + shift) % 360;
|
|
10492
|
+
const shiftedBaseColor = chroma_js_default.hsl(shiftedHue, s2, l2).hex();
|
|
10493
|
+
const shiftedRampColors = generateColorRamp(buildConfig(shiftedBaseColor));
|
|
10494
|
+
const formattedShiftedColors = shiftedRampColors.map((c4) => formatColor2(c4, outputFormat));
|
|
10495
|
+
ramps.push({
|
|
10496
|
+
name: `shift-${Math.round(shift)}`,
|
|
10497
|
+
baseColor: formatColor2(shiftedBaseColor, outputFormat),
|
|
10498
|
+
config: buildRampConfig(),
|
|
10499
|
+
colors: formattedShiftedColors
|
|
10500
|
+
});
|
|
10501
|
+
}
|
|
10434
10502
|
if (outputType === "json") {
|
|
10435
10503
|
console.log(formatJson(ramps));
|
|
10436
10504
|
} else if (outputType === "css") {
|
|
10437
10505
|
console.log(formatCss2(ramps));
|
|
10438
10506
|
} else {
|
|
10507
|
+
if (args.preview) {
|
|
10508
|
+
const limitationNote = getColorLimitationNote();
|
|
10509
|
+
if (limitationNote) {
|
|
10510
|
+
console.log(limitationNote);
|
|
10511
|
+
console.log("");
|
|
10512
|
+
}
|
|
10513
|
+
}
|
|
10439
10514
|
ramps.forEach((ramp, rampIndex) => {
|
|
10440
10515
|
if (rampIndex > 0 || ramps.length > 1) {
|
|
10441
10516
|
if (rampIndex > 0)
|
|
@@ -10446,7 +10521,7 @@ var main = defineCommand({
|
|
|
10446
10521
|
if (args.preview) {
|
|
10447
10522
|
const c4 = chroma_js_default(color);
|
|
10448
10523
|
const [r4, g3, b2] = c4.rgb();
|
|
10449
|
-
const square =
|
|
10524
|
+
const square = coloredSquare(r4, g3, b2);
|
|
10450
10525
|
console.log(`${square} ${color}`);
|
|
10451
10526
|
} else {
|
|
10452
10527
|
console.log(color);
|