(value: ColorValue, chain: string[] = [])
| 277 | const defs = theme.defs ?? {} |
| 278 | |
| 279 | const resolveColor = (value: ColorValue, chain: string[] = []): RGBA => { |
| 280 | if (value instanceof RGBA) return value |
| 281 | |
| 282 | if (typeof value === "number") { |
| 283 | return RGBA.fromIndex(value, ansiToRgba(value)) |
| 284 | } |
| 285 | |
| 286 | if (typeof value !== "string") { |
| 287 | return resolveColor(value[pick], chain) |
| 288 | } |
| 289 | |
| 290 | if (value === "transparent" || value === "none") { |
| 291 | return RGBA.fromInts(0, 0, 0, 0) |
| 292 | } |
| 293 | |
| 294 | if (value.startsWith("#")) { |
| 295 | return RGBA.fromHex(value) |
| 296 | } |
| 297 | |
| 298 | if (chain.includes(value)) { |
| 299 | throw new Error(`Circular color reference: ${[...chain, value].join(" -> ")}`) |
| 300 | } |
| 301 | |
| 302 | const next = defs[value] ?? theme.theme[value as ThemeColor] |
| 303 | if (next === undefined) { |
| 304 | throw new Error(`Color reference "${value}" not found in defs or theme`) |
| 305 | } |
| 306 | |
| 307 | return resolveColor(next, [...chain, value]) |
| 308 | } |
| 309 | |
| 310 | const resolved = Object.fromEntries( |
| 311 | Object.entries(theme.theme) |
no test coverage detected