Add option to generate 256 color palette from first 16 colors

Needs more work to test and possibly implement reporting and setting
of the nullable color table colors.

Fixes #9426
This commit is contained in:
Jake Stewart
2026-01-27 21:48:42 +08:00
committed by Kovid Goyal
parent 99d986c821
commit 1a62cde212
12 changed files with 965 additions and 1490 deletions

View File

@@ -14,6 +14,7 @@
#include <xlocale.h>
#endif
static const color_type NULL_COLOR_VALUE = 0xffffffff;
static uint32_t FG_BG_256[256] = {
0x000000, // 0
@@ -121,12 +122,139 @@ set_mark_colors(ColorProfile *self, PyObject *opts) {
return true;
}
static void
color_type_to_lab(color_type color, float *lab) {
float r = ((color >> 16) & 0xff) / 255.0f;
float g = ((color >> 8) & 0xff) / 255.0f;
float b = (color & 0xff) / 255.0f;
r = r > 0.04045f ? powf((r + 0.055f) / 1.055f, 2.4f) : r / 12.92f;
g = g > 0.04045f ? powf((g + 0.055f) / 1.055f, 2.4f) : g / 12.92f;
b = b > 0.04045f ? powf((b + 0.055f) / 1.055f, 2.4f) : b / 12.92f;
float x = (r * 0.4124564f + g * 0.3575761f + b * 0.1804375f) / 0.95047f;
float y = (r * 0.2126729f + g * 0.7151522f + b * 0.0721750f);
float z = (r * 0.0193339f + g * 0.1191920f + b * 0.9503041f) / 1.08883f;
x = x > 0.008856f ? cbrtf(x) : 7.787f * x + 16.0f / 116.0f;
y = y > 0.008856f ? cbrtf(y) : 7.787f * y + 16.0f / 116.0f;
z = z > 0.008856f ? cbrtf(z) : 7.787f * z + 16.0f / 116.0f;
lab[0] = 116.0f * y - 16.0f;
lab[1] = 500.0f * (x - y);
lab[2] = 200.0f * (y - z);
}
static color_type
lab_to_color_type(float *lab) {
float y = (lab[0] + 16.0f) / 116.0f;
float x = lab[1] / 500.0f + y;
float z = y - lab[2] / 200.0f;
float x3 = x * x * x, y3 = y * y * y, z3 = z * z * z;
x = (x3 > 0.008856f ? x3 : (x - 16.0f / 116.0f) / 7.787f) * 0.95047f;
y = y3 > 0.008856f ? y3 : (y - 16.0f / 116.0f) / 7.787f;
z = (z3 > 0.008856f ? z3 : (z - 16.0f / 116.0f) / 7.787f) * 1.08883f;
float r = x * 3.2404542f - y * 1.5371385f - z * 0.4985314f;
float g = -x * 0.9692660f + y * 1.8760108f + z * 0.0415560f;
float b = x * 0.0556434f - y * 0.2040259f + z * 1.0572252f;
r = r > 0.0031308f ? 1.055f * powf(r, 1.0f / 2.4f) - 0.055f : 12.92f * r;
g = g > 0.0031308f ? 1.055f * powf(g, 1.0f / 2.4f) - 0.055f : 12.92f * g;
b = b > 0.0031308f ? 1.055f * powf(b, 1.0f / 2.4f) - 0.055f : 12.92f * b;
uint8_t rb = (uint8_t)(fminf(fmaxf(r, 0.0f), 1.0f) * 255.0f + 0.5f);
uint8_t gb = (uint8_t)(fminf(fmaxf(g, 0.0f), 1.0f) * 255.0f + 0.5f);
uint8_t bb = (uint8_t)(fminf(fmaxf(b, 0.0f), 1.0f) * 255.0f + 0.5f);
return (rb << 16) | (gb << 8) | bb;
}
static void
lerp_lab(float t, float *a, float *b, float *out) {
out[0] = a[0] + t * (b[0] - a[0]);
out[1] = a[1] + t * (b[1] - a[1]);
out[2] = a[2] + t * (b[2] - a[2]);
}
// For more information, see
// https://gist.github.com/jake-stewart/0a8ea46159a7da2c808e5be2177e1783
static void
generate_256_palette(color_type *color_table, color_type bg, color_type fg, bool semantic) {
float base8_lab[8][3];
color_type_to_lab(bg, base8_lab[0]);
color_type_to_lab(fg, base8_lab[7]);
for (int i = 1; i < 7; i++) color_type_to_lab(color_table[i], base8_lab[i]);
bool is_light_theme = base8_lab[7][0] < base8_lab[0][0];
bool invert = is_light_theme && !semantic;
if (invert) {
float tmp[3];
memcpy(tmp, base8_lab[0], sizeof(tmp));
memcpy(base8_lab[0], base8_lab[7], sizeof(tmp));
memcpy(base8_lab[7], tmp, sizeof(tmp));
}
int idx = 16;
for (int r = 0; r < 6; r++) {
float c0[3], c1[3], c2[3], c3[3];
float tr = r / 5.0f;
lerp_lab(tr, base8_lab[0], base8_lab[1], c0);
lerp_lab(tr, base8_lab[2], base8_lab[3], c1);
lerp_lab(tr, base8_lab[4], base8_lab[5], c2);
lerp_lab(tr, base8_lab[6], base8_lab[7], c3);
for (int g = 0; g < 6; g++) {
float c4[3], c5[3];
float tg = g / 5.0f;
lerp_lab(tg, c0, c1, c4);
lerp_lab(tg, c2, c3, c5);
for (int b = 0; b < 6; b++) {
if (color_table[idx] == NULL_COLOR_VALUE) {
float c6[3];
lerp_lab(b / 5.0f, c4, c5, c6);
color_table[idx] = lab_to_color_type(c6);
}
idx++;
}
}
}
for (int i = 0; i < 24; i++) {
float t = (i + 1) / 25.0f;
float lab[3];
lerp_lab(t, base8_lab[0], base8_lab[7], lab);
if (color_table[idx] == NULL_COLOR_VALUE) {
color_table[idx] = lab_to_color_type(lab);
}
idx++;
}
}
static void
fixed_color_palette(color_type *color_table) {
init_FG_BG_table();
for (unsigned i = 16; i < arraysz(FG_BG_256); i++) {
if (color_table[i] == NULL_COLOR_VALUE) color_table[i] = FG_BG_256[i];
}
}
static bool
palette_generation_is_dynamic(PyObject *opts, bool *semantic) {
bool ans = false; *semantic = false;
if (opts) {
RAII_PyObject(policy, PyObject_GetAttrString(opts, "palette_generate")); if (!policy) return ans;
ans = PyUnicode_CompareWithASCIIString(policy, "fixed") != 0;
*semantic = ans && PyUnicode_CompareWithASCIIString(policy, "semantic") == 0;
}
return ans;
}
static bool
set_colortable(ColorProfile *self, PyObject *opts) {
RAII_PyObject(ct, PyObject_GetAttrString(opts, "color_table"));
if (!ct) return false;
RAII_PyObject(ret, PyObject_CallMethod(ct, "buffer_info", NULL));
if (!ret) return false;
RAII_PyObject(ct, PyObject_GetAttrString(opts, "color_table")); if (!ct) return false;
RAII_PyObject(ret, PyObject_CallMethod(ct, "buffer_info", NULL)); if (!ret) return false;
bool semantic_generation, dynamic_palette = palette_generation_is_dynamic(opts, &semantic_generation);
unsigned long *color_table = PyLong_AsVoidPtr(PyTuple_GET_ITEM(ret, 0));
size_t count = PyLong_AsSize_t(PyTuple_GET_ITEM(ret, 1));
if (!color_table || count != arraysz(FG_BG_256)) { PyErr_SetString(PyExc_TypeError, "color_table has incorrect length"); return false; }
@@ -134,6 +262,9 @@ set_colortable(ColorProfile *self, PyObject *opts) {
size_t itemsize = PyLong_AsSize_t(r2);
if (itemsize != sizeof(unsigned long)) { PyErr_Format(PyExc_TypeError, "color_table has incorrect itemsize: %zu", itemsize); return false; }
for (size_t i = 0; i < arraysz(FG_BG_256); i++) self->color_table[i] = color_table[i];
if (dynamic_palette) generate_256_palette(
self->color_table, self->configured.default_bg.rgb, self->configured.default_fg.rgb, semantic_generation);
else fixed_color_palette(self->color_table);
memcpy(self->orig_color_table, self->color_table, arraysz(self->color_table) * sizeof(self->color_table[0]));
return true;
}
@@ -155,7 +286,7 @@ new_cp(PyTypeObject *type, PyObject *args, PyObject *kwds) {
if (!set_colortable(self, opts)) return NULL;
} else {
memcpy(self->color_table, FG_BG_256, sizeof(FG_BG_256));
memcpy(self->orig_color_table, FG_BG_256, sizeof(FG_BG_256));
memcpy(self->orig_color_table, self->color_table, sizeof(FG_BG_256));
}
self->dirty = true;
Py_INCREF(ans);
@@ -187,10 +318,12 @@ copy_color_profile(ColorProfile *dest, ColorProfile *src) {
}
static void
patch_color_table(const char *key, PyObject *profiles, PyObject *spec, size_t which, int change_configured) {
patch_color_table(const char *key, PyObject *profiles, PyObject *spec, size_t which, int change_configured, bool *has_null_values) {
PyObject *v = PyDict_GetItemString(spec, key);
if (v && PyLong_Check(v)) {
color_type color = PyLong_AsUnsignedLong(v);
if (v) {
color_type color = NULL_COLOR_VALUE;
if (PyLong_Check(v)) color = PyLong_AsUnsignedLong(v);
else *has_null_values = true;
for (Py_ssize_t j = 0; j < PyTuple_GET_SIZE(profiles); j++) {
ColorProfile *self = (ColorProfile*)PyTuple_GET_ITEM(profiles, j);
self->color_table[which] = color;
@@ -217,9 +350,10 @@ patch_color_profiles(PyObject *module UNUSED, PyObject *args) {
PyObject *spec, *transparent_background_colors, *profiles, *v; ColorProfile *self; int change_configured;
if (!PyArg_ParseTuple(args, "O!O!O!p", &PyDict_Type, &spec, &PyTuple_Type, &transparent_background_colors, &PyTuple_Type, &profiles, &change_configured)) return NULL;
char key[32] = {0};
bool has_null_values = false;
for (size_t i = 0; i < arraysz(FG_BG_256); i++) {
snprintf(key, sizeof(key) - 1, "color%zu", i);
patch_color_table(key, profiles, spec, i, change_configured);
patch_color_table(key, profiles, spec, i, change_configured, &has_null_values);
}
for (size_t i = 1; i <= MARK_MASK; i++) {
#define S(which, i) snprintf(key, sizeof(key) - 1, "mark%zu_" #which, i); patch_mark_color(key, profiles, spec, mark_##which##s, i)
@@ -254,6 +388,22 @@ patch_color_profiles(PyObject *module UNUSED, PyObject *args) {
set_transparent_background_colors(self->overriden_transparent_colors, transparent_background_colors);
if (change_configured) set_transparent_background_colors(self->configured_transparent_colors, transparent_background_colors);
}
if (has_null_values) {
bool semantic, dynamic = palette_generation_is_dynamic(global_state.options_object, &semantic);
for (Py_ssize_t j = 0; j < PyTuple_GET_SIZE(profiles); j++) {
ColorProfile *self = (ColorProfile*)PyTuple_GET_ITEM(profiles, j);
if (dynamic) {
generate_256_palette(
self->color_table, self->configured.default_bg.rgb, self->configured.default_fg.rgb, semantic);
if (change_configured) generate_256_palette(
self->orig_color_table, self->configured.default_bg.rgb, self->configured.default_fg.rgb, semantic);
} else {
fixed_color_palette(self->color_table);
if (change_configured) fixed_color_palette(self->orig_color_table);
}
}
}
if (PyErr_Occurred()) return NULL;
Py_RETURN_NONE;
}
@@ -1226,6 +1376,7 @@ int init_ColorProfile(PyObject *module) {\
Py_INCREF(&Color_Type);
if (PyModule_AddFunctions(module, module_methods) != 0) return false;
PyModule_AddIntMacro(module, NULL_COLOR_VALUE);
return 1;
}

View File

@@ -253,12 +253,12 @@ def patch_colors(
background_image_options: BackgroundImageOptions | None = None
) -> None:
boss = get_boss()
opts = get_options()
if windows is None:
windows = tuple(boss.all_windows)
bg_colors_before = {w.id: w.screen.color_profile.default_bg for w in windows}
profiles = tuple(w.screen.color_profile for w in windows if w)
patch_color_profiles(spec, transparent_background_colors, profiles, configured)
opts = get_options()
if configured:
patch_options_with_color_spec(opts, spec, transparent_background_colors, background_image_options)
os_window_ids = set()

View File

@@ -10,6 +10,7 @@ from collections.abc import Callable, Iterator
from typing import Any, get_type_hints
from kitty.conf.types import Definition, MultiOption, Option, ParserFuncType, unset
from kitty.fast_data_types import NULL_COLOR_VALUE
from kitty.options.utils import parse_options_for_map
from kitty.simple_cli_definitions import serialize_as_go_string
from kitty.types import _T
@@ -116,7 +117,10 @@ def generate_class(defn: Definition, loc: str) -> tuple[str, str]:
t(f' ans[{option.name!r}] = {func.__name__}(val)')
tc_imports.add((func.__module__, func.__name__))
cnum = int(option.name[5:])
color_table[cnum] = f'0x{func(option.defval_as_string).__int__():06x}'
if option.defval_as_string == 'none':
color_table[cnum] = f'0x{NULL_COLOR_VALUE:x}'
else:
color_table[cnum] = f'0x{func(option.defval_as_string).__int__():06x}'
continue
else:
func, typ = option_type_data(option)
@@ -267,6 +271,8 @@ def generate_class(defn: Definition, loc: str) -> tuple[str, str]:
a(' k = int(q)')
a(' if 0 <= k <= 255:')
a(' x = self.color_table[k]')
a(f' if x == 0x{NULL_COLOR_VALUE:x}:')
a(' return None')
a(' return Color((x >> 16) & 255, (x >> 8) & 255, x & 255)')
a(' raise AttributeError(key)')
a('')
@@ -276,7 +282,10 @@ def generate_class(defn: Definition, loc: str) -> tuple[str, str]:
a(' if q.isdigit():')
a(' k = int(q)')
a(' if 0 <= k <= 255:')
a(' self.color_table[k] = int(val)')
a(' if val is None:')
a(f' self.color_table[k] = 0x{NULL_COLOR_VALUE:x}')
a(' else:')
a(' self.color_table[k] = int(val)')
a(' return')
a(' object.__setattr__(self, key, val)')

View File

@@ -169,6 +169,7 @@ def load_config(*paths: str, overrides: Iterable[str] | None = None, accumulate_
effective_config_lines.append(line)
overrides = tuple(overrides) if overrides is not None else ()
opts_dict, found_paths = _load_config(
defaults, partial(parse_config, accumulate_bad_lines=accumulate_bad_lines, effective_config_lines=add_effective_config_line),
merge_result_dicts, *paths, overrides=overrides)

View File

@@ -260,7 +260,7 @@ typedef struct {
PyObject_HEAD
bool dirty;
uint32_t color_table[256], orig_color_table[256];
color_type color_table[256], orig_color_table[256];
TransparentDynamicColor configured_transparent_colors[8], overriden_transparent_colors[8];
struct { DynamicColors dynamic_colors; uint32_t color_table[256]; TransparentDynamicColor transparent_colors[8]; } *color_stack;
unsigned int color_stack_idx, color_stack_sz;

View File

@@ -14,6 +14,7 @@ from kitty.typing_compat import EdgeLiteral, NotRequired, ReadableBuffer, Writea
# Constants {{{
SCALE_BITS: int
NULL_COLOR_VALUE: int
WIDTH_BITS: int
SUBSCALE_BITS: int
COLOR_IS_SPECIAL: int

File diff suppressed because it is too large Load Diff

488
kitty/options/parse.py generated
View File

@@ -190,724 +190,724 @@ class Parser:
ans['color15'] = to_color(val)
def color16(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color16'] = to_color(val)
ans['color16'] = to_color_or_none(val)
def color17(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color17'] = to_color(val)
ans['color17'] = to_color_or_none(val)
def color18(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color18'] = to_color(val)
ans['color18'] = to_color_or_none(val)
def color19(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color19'] = to_color(val)
ans['color19'] = to_color_or_none(val)
def color20(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color20'] = to_color(val)
ans['color20'] = to_color_or_none(val)
def color21(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color21'] = to_color(val)
ans['color21'] = to_color_or_none(val)
def color22(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color22'] = to_color(val)
ans['color22'] = to_color_or_none(val)
def color23(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color23'] = to_color(val)
ans['color23'] = to_color_or_none(val)
def color24(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color24'] = to_color(val)
ans['color24'] = to_color_or_none(val)
def color25(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color25'] = to_color(val)
ans['color25'] = to_color_or_none(val)
def color26(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color26'] = to_color(val)
ans['color26'] = to_color_or_none(val)
def color27(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color27'] = to_color(val)
ans['color27'] = to_color_or_none(val)
def color28(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color28'] = to_color(val)
ans['color28'] = to_color_or_none(val)
def color29(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color29'] = to_color(val)
ans['color29'] = to_color_or_none(val)
def color30(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color30'] = to_color(val)
ans['color30'] = to_color_or_none(val)
def color31(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color31'] = to_color(val)
ans['color31'] = to_color_or_none(val)
def color32(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color32'] = to_color(val)
ans['color32'] = to_color_or_none(val)
def color33(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color33'] = to_color(val)
ans['color33'] = to_color_or_none(val)
def color34(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color34'] = to_color(val)
ans['color34'] = to_color_or_none(val)
def color35(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color35'] = to_color(val)
ans['color35'] = to_color_or_none(val)
def color36(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color36'] = to_color(val)
ans['color36'] = to_color_or_none(val)
def color37(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color37'] = to_color(val)
ans['color37'] = to_color_or_none(val)
def color38(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color38'] = to_color(val)
ans['color38'] = to_color_or_none(val)
def color39(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color39'] = to_color(val)
ans['color39'] = to_color_or_none(val)
def color40(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color40'] = to_color(val)
ans['color40'] = to_color_or_none(val)
def color41(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color41'] = to_color(val)
ans['color41'] = to_color_or_none(val)
def color42(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color42'] = to_color(val)
ans['color42'] = to_color_or_none(val)
def color43(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color43'] = to_color(val)
ans['color43'] = to_color_or_none(val)
def color44(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color44'] = to_color(val)
ans['color44'] = to_color_or_none(val)
def color45(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color45'] = to_color(val)
ans['color45'] = to_color_or_none(val)
def color46(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color46'] = to_color(val)
ans['color46'] = to_color_or_none(val)
def color47(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color47'] = to_color(val)
ans['color47'] = to_color_or_none(val)
def color48(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color48'] = to_color(val)
ans['color48'] = to_color_or_none(val)
def color49(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color49'] = to_color(val)
ans['color49'] = to_color_or_none(val)
def color50(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color50'] = to_color(val)
ans['color50'] = to_color_or_none(val)
def color51(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color51'] = to_color(val)
ans['color51'] = to_color_or_none(val)
def color52(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color52'] = to_color(val)
ans['color52'] = to_color_or_none(val)
def color53(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color53'] = to_color(val)
ans['color53'] = to_color_or_none(val)
def color54(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color54'] = to_color(val)
ans['color54'] = to_color_or_none(val)
def color55(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color55'] = to_color(val)
ans['color55'] = to_color_or_none(val)
def color56(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color56'] = to_color(val)
ans['color56'] = to_color_or_none(val)
def color57(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color57'] = to_color(val)
ans['color57'] = to_color_or_none(val)
def color58(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color58'] = to_color(val)
ans['color58'] = to_color_or_none(val)
def color59(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color59'] = to_color(val)
ans['color59'] = to_color_or_none(val)
def color60(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color60'] = to_color(val)
ans['color60'] = to_color_or_none(val)
def color61(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color61'] = to_color(val)
ans['color61'] = to_color_or_none(val)
def color62(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color62'] = to_color(val)
ans['color62'] = to_color_or_none(val)
def color63(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color63'] = to_color(val)
ans['color63'] = to_color_or_none(val)
def color64(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color64'] = to_color(val)
ans['color64'] = to_color_or_none(val)
def color65(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color65'] = to_color(val)
ans['color65'] = to_color_or_none(val)
def color66(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color66'] = to_color(val)
ans['color66'] = to_color_or_none(val)
def color67(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color67'] = to_color(val)
ans['color67'] = to_color_or_none(val)
def color68(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color68'] = to_color(val)
ans['color68'] = to_color_or_none(val)
def color69(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color69'] = to_color(val)
ans['color69'] = to_color_or_none(val)
def color70(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color70'] = to_color(val)
ans['color70'] = to_color_or_none(val)
def color71(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color71'] = to_color(val)
ans['color71'] = to_color_or_none(val)
def color72(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color72'] = to_color(val)
ans['color72'] = to_color_or_none(val)
def color73(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color73'] = to_color(val)
ans['color73'] = to_color_or_none(val)
def color74(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color74'] = to_color(val)
ans['color74'] = to_color_or_none(val)
def color75(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color75'] = to_color(val)
ans['color75'] = to_color_or_none(val)
def color76(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color76'] = to_color(val)
ans['color76'] = to_color_or_none(val)
def color77(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color77'] = to_color(val)
ans['color77'] = to_color_or_none(val)
def color78(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color78'] = to_color(val)
ans['color78'] = to_color_or_none(val)
def color79(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color79'] = to_color(val)
ans['color79'] = to_color_or_none(val)
def color80(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color80'] = to_color(val)
ans['color80'] = to_color_or_none(val)
def color81(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color81'] = to_color(val)
ans['color81'] = to_color_or_none(val)
def color82(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color82'] = to_color(val)
ans['color82'] = to_color_or_none(val)
def color83(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color83'] = to_color(val)
ans['color83'] = to_color_or_none(val)
def color84(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color84'] = to_color(val)
ans['color84'] = to_color_or_none(val)
def color85(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color85'] = to_color(val)
ans['color85'] = to_color_or_none(val)
def color86(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color86'] = to_color(val)
ans['color86'] = to_color_or_none(val)
def color87(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color87'] = to_color(val)
ans['color87'] = to_color_or_none(val)
def color88(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color88'] = to_color(val)
ans['color88'] = to_color_or_none(val)
def color89(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color89'] = to_color(val)
ans['color89'] = to_color_or_none(val)
def color90(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color90'] = to_color(val)
ans['color90'] = to_color_or_none(val)
def color91(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color91'] = to_color(val)
ans['color91'] = to_color_or_none(val)
def color92(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color92'] = to_color(val)
ans['color92'] = to_color_or_none(val)
def color93(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color93'] = to_color(val)
ans['color93'] = to_color_or_none(val)
def color94(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color94'] = to_color(val)
ans['color94'] = to_color_or_none(val)
def color95(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color95'] = to_color(val)
ans['color95'] = to_color_or_none(val)
def color96(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color96'] = to_color(val)
ans['color96'] = to_color_or_none(val)
def color97(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color97'] = to_color(val)
ans['color97'] = to_color_or_none(val)
def color98(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color98'] = to_color(val)
ans['color98'] = to_color_or_none(val)
def color99(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color99'] = to_color(val)
ans['color99'] = to_color_or_none(val)
def color100(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color100'] = to_color(val)
ans['color100'] = to_color_or_none(val)
def color101(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color101'] = to_color(val)
ans['color101'] = to_color_or_none(val)
def color102(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color102'] = to_color(val)
ans['color102'] = to_color_or_none(val)
def color103(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color103'] = to_color(val)
ans['color103'] = to_color_or_none(val)
def color104(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color104'] = to_color(val)
ans['color104'] = to_color_or_none(val)
def color105(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color105'] = to_color(val)
ans['color105'] = to_color_or_none(val)
def color106(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color106'] = to_color(val)
ans['color106'] = to_color_or_none(val)
def color107(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color107'] = to_color(val)
ans['color107'] = to_color_or_none(val)
def color108(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color108'] = to_color(val)
ans['color108'] = to_color_or_none(val)
def color109(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color109'] = to_color(val)
ans['color109'] = to_color_or_none(val)
def color110(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color110'] = to_color(val)
ans['color110'] = to_color_or_none(val)
def color111(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color111'] = to_color(val)
ans['color111'] = to_color_or_none(val)
def color112(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color112'] = to_color(val)
ans['color112'] = to_color_or_none(val)
def color113(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color113'] = to_color(val)
ans['color113'] = to_color_or_none(val)
def color114(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color114'] = to_color(val)
ans['color114'] = to_color_or_none(val)
def color115(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color115'] = to_color(val)
ans['color115'] = to_color_or_none(val)
def color116(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color116'] = to_color(val)
ans['color116'] = to_color_or_none(val)
def color117(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color117'] = to_color(val)
ans['color117'] = to_color_or_none(val)
def color118(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color118'] = to_color(val)
ans['color118'] = to_color_or_none(val)
def color119(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color119'] = to_color(val)
ans['color119'] = to_color_or_none(val)
def color120(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color120'] = to_color(val)
ans['color120'] = to_color_or_none(val)
def color121(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color121'] = to_color(val)
ans['color121'] = to_color_or_none(val)
def color122(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color122'] = to_color(val)
ans['color122'] = to_color_or_none(val)
def color123(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color123'] = to_color(val)
ans['color123'] = to_color_or_none(val)
def color124(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color124'] = to_color(val)
ans['color124'] = to_color_or_none(val)
def color125(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color125'] = to_color(val)
ans['color125'] = to_color_or_none(val)
def color126(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color126'] = to_color(val)
ans['color126'] = to_color_or_none(val)
def color127(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color127'] = to_color(val)
ans['color127'] = to_color_or_none(val)
def color128(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color128'] = to_color(val)
ans['color128'] = to_color_or_none(val)
def color129(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color129'] = to_color(val)
ans['color129'] = to_color_or_none(val)
def color130(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color130'] = to_color(val)
ans['color130'] = to_color_or_none(val)
def color131(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color131'] = to_color(val)
ans['color131'] = to_color_or_none(val)
def color132(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color132'] = to_color(val)
ans['color132'] = to_color_or_none(val)
def color133(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color133'] = to_color(val)
ans['color133'] = to_color_or_none(val)
def color134(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color134'] = to_color(val)
ans['color134'] = to_color_or_none(val)
def color135(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color135'] = to_color(val)
ans['color135'] = to_color_or_none(val)
def color136(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color136'] = to_color(val)
ans['color136'] = to_color_or_none(val)
def color137(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color137'] = to_color(val)
ans['color137'] = to_color_or_none(val)
def color138(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color138'] = to_color(val)
ans['color138'] = to_color_or_none(val)
def color139(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color139'] = to_color(val)
ans['color139'] = to_color_or_none(val)
def color140(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color140'] = to_color(val)
ans['color140'] = to_color_or_none(val)
def color141(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color141'] = to_color(val)
ans['color141'] = to_color_or_none(val)
def color142(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color142'] = to_color(val)
ans['color142'] = to_color_or_none(val)
def color143(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color143'] = to_color(val)
ans['color143'] = to_color_or_none(val)
def color144(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color144'] = to_color(val)
ans['color144'] = to_color_or_none(val)
def color145(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color145'] = to_color(val)
ans['color145'] = to_color_or_none(val)
def color146(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color146'] = to_color(val)
ans['color146'] = to_color_or_none(val)
def color147(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color147'] = to_color(val)
ans['color147'] = to_color_or_none(val)
def color148(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color148'] = to_color(val)
ans['color148'] = to_color_or_none(val)
def color149(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color149'] = to_color(val)
ans['color149'] = to_color_or_none(val)
def color150(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color150'] = to_color(val)
ans['color150'] = to_color_or_none(val)
def color151(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color151'] = to_color(val)
ans['color151'] = to_color_or_none(val)
def color152(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color152'] = to_color(val)
ans['color152'] = to_color_or_none(val)
def color153(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color153'] = to_color(val)
ans['color153'] = to_color_or_none(val)
def color154(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color154'] = to_color(val)
ans['color154'] = to_color_or_none(val)
def color155(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color155'] = to_color(val)
ans['color155'] = to_color_or_none(val)
def color156(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color156'] = to_color(val)
ans['color156'] = to_color_or_none(val)
def color157(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color157'] = to_color(val)
ans['color157'] = to_color_or_none(val)
def color158(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color158'] = to_color(val)
ans['color158'] = to_color_or_none(val)
def color159(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color159'] = to_color(val)
ans['color159'] = to_color_or_none(val)
def color160(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color160'] = to_color(val)
ans['color160'] = to_color_or_none(val)
def color161(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color161'] = to_color(val)
ans['color161'] = to_color_or_none(val)
def color162(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color162'] = to_color(val)
ans['color162'] = to_color_or_none(val)
def color163(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color163'] = to_color(val)
ans['color163'] = to_color_or_none(val)
def color164(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color164'] = to_color(val)
ans['color164'] = to_color_or_none(val)
def color165(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color165'] = to_color(val)
ans['color165'] = to_color_or_none(val)
def color166(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color166'] = to_color(val)
ans['color166'] = to_color_or_none(val)
def color167(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color167'] = to_color(val)
ans['color167'] = to_color_or_none(val)
def color168(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color168'] = to_color(val)
ans['color168'] = to_color_or_none(val)
def color169(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color169'] = to_color(val)
ans['color169'] = to_color_or_none(val)
def color170(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color170'] = to_color(val)
ans['color170'] = to_color_or_none(val)
def color171(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color171'] = to_color(val)
ans['color171'] = to_color_or_none(val)
def color172(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color172'] = to_color(val)
ans['color172'] = to_color_or_none(val)
def color173(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color173'] = to_color(val)
ans['color173'] = to_color_or_none(val)
def color174(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color174'] = to_color(val)
ans['color174'] = to_color_or_none(val)
def color175(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color175'] = to_color(val)
ans['color175'] = to_color_or_none(val)
def color176(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color176'] = to_color(val)
ans['color176'] = to_color_or_none(val)
def color177(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color177'] = to_color(val)
ans['color177'] = to_color_or_none(val)
def color178(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color178'] = to_color(val)
ans['color178'] = to_color_or_none(val)
def color179(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color179'] = to_color(val)
ans['color179'] = to_color_or_none(val)
def color180(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color180'] = to_color(val)
ans['color180'] = to_color_or_none(val)
def color181(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color181'] = to_color(val)
ans['color181'] = to_color_or_none(val)
def color182(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color182'] = to_color(val)
ans['color182'] = to_color_or_none(val)
def color183(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color183'] = to_color(val)
ans['color183'] = to_color_or_none(val)
def color184(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color184'] = to_color(val)
ans['color184'] = to_color_or_none(val)
def color185(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color185'] = to_color(val)
ans['color185'] = to_color_or_none(val)
def color186(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color186'] = to_color(val)
ans['color186'] = to_color_or_none(val)
def color187(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color187'] = to_color(val)
ans['color187'] = to_color_or_none(val)
def color188(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color188'] = to_color(val)
ans['color188'] = to_color_or_none(val)
def color189(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color189'] = to_color(val)
ans['color189'] = to_color_or_none(val)
def color190(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color190'] = to_color(val)
ans['color190'] = to_color_or_none(val)
def color191(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color191'] = to_color(val)
ans['color191'] = to_color_or_none(val)
def color192(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color192'] = to_color(val)
ans['color192'] = to_color_or_none(val)
def color193(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color193'] = to_color(val)
ans['color193'] = to_color_or_none(val)
def color194(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color194'] = to_color(val)
ans['color194'] = to_color_or_none(val)
def color195(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color195'] = to_color(val)
ans['color195'] = to_color_or_none(val)
def color196(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color196'] = to_color(val)
ans['color196'] = to_color_or_none(val)
def color197(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color197'] = to_color(val)
ans['color197'] = to_color_or_none(val)
def color198(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color198'] = to_color(val)
ans['color198'] = to_color_or_none(val)
def color199(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color199'] = to_color(val)
ans['color199'] = to_color_or_none(val)
def color200(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color200'] = to_color(val)
ans['color200'] = to_color_or_none(val)
def color201(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color201'] = to_color(val)
ans['color201'] = to_color_or_none(val)
def color202(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color202'] = to_color(val)
ans['color202'] = to_color_or_none(val)
def color203(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color203'] = to_color(val)
ans['color203'] = to_color_or_none(val)
def color204(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color204'] = to_color(val)
ans['color204'] = to_color_or_none(val)
def color205(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color205'] = to_color(val)
ans['color205'] = to_color_or_none(val)
def color206(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color206'] = to_color(val)
ans['color206'] = to_color_or_none(val)
def color207(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color207'] = to_color(val)
ans['color207'] = to_color_or_none(val)
def color208(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color208'] = to_color(val)
ans['color208'] = to_color_or_none(val)
def color209(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color209'] = to_color(val)
ans['color209'] = to_color_or_none(val)
def color210(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color210'] = to_color(val)
ans['color210'] = to_color_or_none(val)
def color211(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color211'] = to_color(val)
ans['color211'] = to_color_or_none(val)
def color212(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color212'] = to_color(val)
ans['color212'] = to_color_or_none(val)
def color213(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color213'] = to_color(val)
ans['color213'] = to_color_or_none(val)
def color214(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color214'] = to_color(val)
ans['color214'] = to_color_or_none(val)
def color215(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color215'] = to_color(val)
ans['color215'] = to_color_or_none(val)
def color216(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color216'] = to_color(val)
ans['color216'] = to_color_or_none(val)
def color217(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color217'] = to_color(val)
ans['color217'] = to_color_or_none(val)
def color218(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color218'] = to_color(val)
ans['color218'] = to_color_or_none(val)
def color219(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color219'] = to_color(val)
ans['color219'] = to_color_or_none(val)
def color220(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color220'] = to_color(val)
ans['color220'] = to_color_or_none(val)
def color221(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color221'] = to_color(val)
ans['color221'] = to_color_or_none(val)
def color222(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color222'] = to_color(val)
ans['color222'] = to_color_or_none(val)
def color223(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color223'] = to_color(val)
ans['color223'] = to_color_or_none(val)
def color224(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color224'] = to_color(val)
ans['color224'] = to_color_or_none(val)
def color225(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color225'] = to_color(val)
ans['color225'] = to_color_or_none(val)
def color226(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color226'] = to_color(val)
ans['color226'] = to_color_or_none(val)
def color227(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color227'] = to_color(val)
ans['color227'] = to_color_or_none(val)
def color228(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color228'] = to_color(val)
ans['color228'] = to_color_or_none(val)
def color229(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color229'] = to_color(val)
ans['color229'] = to_color_or_none(val)
def color230(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color230'] = to_color(val)
ans['color230'] = to_color_or_none(val)
def color231(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color231'] = to_color(val)
ans['color231'] = to_color_or_none(val)
def color232(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color232'] = to_color(val)
ans['color232'] = to_color_or_none(val)
def color233(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color233'] = to_color(val)
ans['color233'] = to_color_or_none(val)
def color234(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color234'] = to_color(val)
ans['color234'] = to_color_or_none(val)
def color235(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color235'] = to_color(val)
ans['color235'] = to_color_or_none(val)
def color236(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color236'] = to_color(val)
ans['color236'] = to_color_or_none(val)
def color237(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color237'] = to_color(val)
ans['color237'] = to_color_or_none(val)
def color238(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color238'] = to_color(val)
ans['color238'] = to_color_or_none(val)
def color239(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color239'] = to_color(val)
ans['color239'] = to_color_or_none(val)
def color240(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color240'] = to_color(val)
ans['color240'] = to_color_or_none(val)
def color241(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color241'] = to_color(val)
ans['color241'] = to_color_or_none(val)
def color242(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color242'] = to_color(val)
ans['color242'] = to_color_or_none(val)
def color243(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color243'] = to_color(val)
ans['color243'] = to_color_or_none(val)
def color244(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color244'] = to_color(val)
ans['color244'] = to_color_or_none(val)
def color245(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color245'] = to_color(val)
ans['color245'] = to_color_or_none(val)
def color246(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color246'] = to_color(val)
ans['color246'] = to_color_or_none(val)
def color247(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color247'] = to_color(val)
ans['color247'] = to_color_or_none(val)
def color248(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color248'] = to_color(val)
ans['color248'] = to_color_or_none(val)
def color249(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color249'] = to_color(val)
ans['color249'] = to_color_or_none(val)
def color250(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color250'] = to_color(val)
ans['color250'] = to_color_or_none(val)
def color251(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color251'] = to_color(val)
ans['color251'] = to_color_or_none(val)
def color252(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color252'] = to_color(val)
ans['color252'] = to_color_or_none(val)
def color253(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color253'] = to_color(val)
ans['color253'] = to_color_or_none(val)
def color254(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color254'] = to_color(val)
ans['color254'] = to_color_or_none(val)
def color255(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['color255'] = to_color(val)
ans['color255'] = to_color_or_none(val)
def command_on_bell(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['command_on_bell'] = to_cmdline(val)
@@ -1168,6 +1168,14 @@ class Parser:
def open_url_with(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['open_url_with'] = to_cmdline(val)
def palette_generate(self, val: str, ans: dict[str, typing.Any]) -> None:
val = val.lower()
if val not in self.choices_for_palette_generate:
raise ValueError(f"The value {val} is not a valid choice for palette_generate")
ans["palette_generate"] = val
choices_for_palette_generate = frozenset(('fixed', 'semantic', 'legacy'))
def paste_actions(self, val: str, ans: dict[str, typing.Any]) -> None:
ans['paste_actions'] = paste_actions(val)

312
kitty/options/types.py generated
View File

@@ -25,6 +25,7 @@ choices_for_default_pointer_shape = typing.Literal['arrow', 'beam', 'text', 'poi
choices_for_linux_display_server = typing.Literal['auto', 'wayland', 'x11']
choices_for_macos_colorspace = typing.Literal['srgb', 'default', 'displayp3']
choices_for_macos_show_window_title_in = typing.Literal['all', 'menubar', 'none', 'window']
choices_for_palette_generate = typing.Literal['fixed', 'semantic', 'legacy']
choices_for_placement_strategy = typing.Literal['top-left', 'top', 'top-right', 'left', 'center', 'right', 'bottom-left', 'bottom', 'bottom-right']
choices_for_pointer_shape_when_grabbed = choices_for_default_pointer_shape
choices_for_scrollbar = typing.Literal['scrolled', 'always', 'never', 'hovered', 'scrolled-and-hovered']
@@ -408,6 +409,7 @@ option_names = (
'narrow_symbols',
'notify_on_cmd_finish',
'open_url_with',
'palette_generate',
'paste_actions',
'pixel_scroll',
'placement_strategy',
@@ -612,6 +614,7 @@ class Options:
mouse_hide_wait: MouseHideWait = MouseHideWait(hide_wait=0.0, show_wait=0.0, show_threshold=40, scroll_show=True) if is_macos else MouseHideWait(hide_wait=3.0, show_wait=0.0, show_threshold=40, scroll_show=True)
notify_on_cmd_finish: NotifyOnCmdFinish = NotifyOnCmdFinish(when='never', duration=5.0, action='notify', cmdline=(), clear_on=('focus', 'next'))
open_url_with: list[str] = ['default']
palette_generate: choices_for_palette_generate = 'fixed'
paste_actions: frozenset[str] = frozenset({'confirm', 'quote-urls-at-prompt'})
pixel_scroll: bool = True
placement_strategy: choices_for_placement_strategy = 'center'
@@ -729,36 +732,36 @@ class Options:
color_table: "array[int]" = array("L", (
0x000000, 0xcc0403, 0x19cb00, 0xcecb00, 0x0d73cc, 0xcb1ed1, 0x0dcdcd, 0xdddddd,
0x767676, 0xf2201f, 0x23fd00, 0xfffd00, 0x1a8fff, 0xfd28ff, 0x14ffff, 0xffffff,
0x000000, 0x00005f, 0x000087, 0x0000af, 0x0000d7, 0x0000ff, 0x005f00, 0x005f5f,
0x005f87, 0x005faf, 0x005fd7, 0x005fff, 0x008700, 0x00875f, 0x008787, 0x0087af,
0x0087d7, 0x0087ff, 0x00af00, 0x00af5f, 0x00af87, 0x00afaf, 0x00afd7, 0x00afff,
0x00d700, 0x00d75f, 0x00d787, 0x00d7af, 0x00d7d7, 0x00d7ff, 0x00ff00, 0x00ff5f,
0x00ff87, 0x00ffaf, 0x00ffd7, 0x00ffff, 0x5f0000, 0x5f005f, 0x5f0087, 0x5f00af,
0x5f00d7, 0x5f00ff, 0x5f5f00, 0x5f5f5f, 0x5f5f87, 0x5f5faf, 0x5f5fd7, 0x5f5fff,
0x5f8700, 0x5f875f, 0x5f8787, 0x5f87af, 0x5f87d7, 0x5f87ff, 0x5faf00, 0x5faf5f,
0x5faf87, 0x5fafaf, 0x5fafd7, 0x5fafff, 0x5fd700, 0x5fd75f, 0x5fd787, 0x5fd7af,
0x5fd7d7, 0x5fd7ff, 0x5fff00, 0x5fff5f, 0x5fff87, 0x5fffaf, 0x5fffd7, 0x5fffff,
0x870000, 0x87005f, 0x870087, 0x8700af, 0x8700d7, 0x8700ff, 0x875f00, 0x875f5f,
0x875f87, 0x875faf, 0x875fd7, 0x875fff, 0x878700, 0x87875f, 0x878787, 0x8787af,
0x8787d7, 0x8787ff, 0x87af00, 0x87af5f, 0x87af87, 0x87afaf, 0x87afd7, 0x87afff,
0x87d700, 0x87d75f, 0x87d787, 0x87d7af, 0x87d7d7, 0x87d7ff, 0x87ff00, 0x87ff5f,
0x87ff87, 0x87ffaf, 0x87ffd7, 0x87ffff, 0xaf0000, 0xaf005f, 0xaf0087, 0xaf00af,
0xaf00d7, 0xaf00ff, 0xaf5f00, 0xaf5f5f, 0xaf5f87, 0xaf5faf, 0xaf5fd7, 0xaf5fff,
0xaf8700, 0xaf875f, 0xaf8787, 0xaf87af, 0xaf87d7, 0xaf87ff, 0xafaf00, 0xafaf5f,
0xafaf87, 0xafafaf, 0xafafd7, 0xafafff, 0xafd700, 0xafd75f, 0xafd787, 0xafd7af,
0xafd7d7, 0xafd7ff, 0xafff00, 0xafff5f, 0xafff87, 0xafffaf, 0xafffd7, 0xafffff,
0xd70000, 0xd7005f, 0xd70087, 0xd700af, 0xd700d7, 0xd700ff, 0xd75f00, 0xd75f5f,
0xd75f87, 0xd75faf, 0xd75fd7, 0xd75fff, 0xd78700, 0xd7875f, 0xd78787, 0xd787af,
0xd787d7, 0xd787ff, 0xd7af00, 0xd7af5f, 0xd7af87, 0xd7afaf, 0xd7afd7, 0xd7afff,
0xd7d700, 0xd7d75f, 0xd7d787, 0xd7d7af, 0xd7d7d7, 0xd7d7ff, 0xd7ff00, 0xd7ff5f,
0xd7ff87, 0xd7ffaf, 0xd7ffd7, 0xd7ffff, 0xff0000, 0xff005f, 0xff0087, 0xff00af,
0xff00d7, 0xff00ff, 0xff5f00, 0xff5f5f, 0xff5f87, 0xff5faf, 0xff5fd7, 0xff5fff,
0xff8700, 0xff875f, 0xff8787, 0xff87af, 0xff87d7, 0xff87ff, 0xffaf00, 0xffaf5f,
0xffaf87, 0xffafaf, 0xffafd7, 0xffafff, 0xffd700, 0xffd75f, 0xffd787, 0xffd7af,
0xffd7d7, 0xffd7ff, 0xffff00, 0xffff5f, 0xffff87, 0xffffaf, 0xffffd7, 0xffffff,
0x080808, 0x121212, 0x1c1c1c, 0x262626, 0x303030, 0x3a3a3a, 0x444444, 0x4e4e4e,
0x585858, 0x626262, 0x6c6c6c, 0x767676, 0x808080, 0x8a8a8a, 0x949494, 0x9e9e9e,
0xa8a8a8, 0xb2b2b2, 0xbcbcbc, 0xc6c6c6, 0xd0d0d0, 0xdadada, 0xe4e4e4, 0xeeeeee,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff,
))
config_paths: tuple[str, ...] = ()
all_config_paths: tuple[str, ...] = ()
@@ -817,6 +820,8 @@ class Options:
k = int(q)
if 0 <= k <= 255:
x = self.color_table[k]
if x == 0xffffffff:
return None
return Color((x >> 16) & 255, (x >> 8) & 255, x & 255)
raise AttributeError(key)
@@ -826,7 +831,10 @@ class Options:
if q.isdigit():
k = int(q)
if 0 <= k <= 255:
self.color_table[k] = int(val)
if val is None:
self.color_table[k] = 0xffffffff
else:
self.color_table[k] = int(val)
return
object.__setattr__(self, key, val)
@@ -1138,7 +1146,247 @@ nullable_colors = frozenset({
'tab_bar_background',
'tab_bar_margin_color',
'selection_foreground',
'selection_background'
'selection_background',
'color16',
'color17',
'color18',
'color19',
'color20',
'color21',
'color22',
'color23',
'color24',
'color25',
'color26',
'color27',
'color28',
'color29',
'color30',
'color31',
'color32',
'color33',
'color34',
'color35',
'color36',
'color37',
'color38',
'color39',
'color40',
'color41',
'color42',
'color43',
'color44',
'color45',
'color46',
'color47',
'color48',
'color49',
'color50',
'color51',
'color52',
'color53',
'color54',
'color55',
'color56',
'color57',
'color58',
'color59',
'color60',
'color61',
'color62',
'color63',
'color64',
'color65',
'color66',
'color67',
'color68',
'color69',
'color70',
'color71',
'color72',
'color73',
'color74',
'color75',
'color76',
'color77',
'color78',
'color79',
'color80',
'color81',
'color82',
'color83',
'color84',
'color85',
'color86',
'color87',
'color88',
'color89',
'color90',
'color91',
'color92',
'color93',
'color94',
'color95',
'color96',
'color97',
'color98',
'color99',
'color100',
'color101',
'color102',
'color103',
'color104',
'color105',
'color106',
'color107',
'color108',
'color109',
'color110',
'color111',
'color112',
'color113',
'color114',
'color115',
'color116',
'color117',
'color118',
'color119',
'color120',
'color121',
'color122',
'color123',
'color124',
'color125',
'color126',
'color127',
'color128',
'color129',
'color130',
'color131',
'color132',
'color133',
'color134',
'color135',
'color136',
'color137',
'color138',
'color139',
'color140',
'color141',
'color142',
'color143',
'color144',
'color145',
'color146',
'color147',
'color148',
'color149',
'color150',
'color151',
'color152',
'color153',
'color154',
'color155',
'color156',
'color157',
'color158',
'color159',
'color160',
'color161',
'color162',
'color163',
'color164',
'color165',
'color166',
'color167',
'color168',
'color169',
'color170',
'color171',
'color172',
'color173',
'color174',
'color175',
'color176',
'color177',
'color178',
'color179',
'color180',
'color181',
'color182',
'color183',
'color184',
'color185',
'color186',
'color187',
'color188',
'color189',
'color190',
'color191',
'color192',
'color193',
'color194',
'color195',
'color196',
'color197',
'color198',
'color199',
'color200',
'color201',
'color202',
'color203',
'color204',
'color205',
'color206',
'color207',
'color208',
'color209',
'color210',
'color211',
'color212',
'color213',
'color214',
'color215',
'color216',
'color217',
'color218',
'color219',
'color220',
'color221',
'color222',
'color223',
'color224',
'color225',
'color226',
'color227',
'color228',
'color229',
'color230',
'color231',
'color232',
'color233',
'color234',
'color235',
'color236',
'color237',
'color238',
'color239',
'color240',
'color241',
'color242',
'color243',
'color244',
'color245',
'color246',
'color247',
'color248',
'color249',
'color250',
'color251',
'color252',
'color253',
'color254',
'color255'
})
special_colors = frozenset({

View File

@@ -151,6 +151,7 @@ typedef struct Options {
float box_drawing_scale[4];
double momentum_scroll;
double window_drag_tolerance;
bool generate_256_palette;
} Options;
typedef struct WindowLogoRenderData {

View File

@@ -1,7 +1,6 @@
#!/usr/bin/env python
# License: GPL v3 Copyright: 2016, Kovid Goyal <kovid at kovidgoyal.net>
from kitty.config import defaults
from kitty.fast_data_types import DECAWM, DECCOLM, DECOM, IRM, VT_PARSER_BUFFER_SIZE, Color, ColorProfile, Cursor
from kitty.marks import marker_from_function, marker_from_regex, marker_from_text
from kitty.window import pagerhist
@@ -1594,26 +1593,30 @@ class TestScreen(BaseTest):
t('=fleur', 'move')
def test_color_profile(self):
c = ColorProfile(defaults)
opts = self.set_options({'palette_generate': 'fixed'})
c = ColorProfile(opts)
for i in range(8):
col = getattr(defaults, f'color{i}')
col = getattr(opts, f'color{i}')
self.ae(c.as_color(i << 8 | 1), col)
for i in range(16, 256):
self.assertIsNone(getattr(opts, f'color{i}'))
self.ae(c.as_color(255 << 8 | 1), Color(0xee, 0xee, 0xee))
s = self.create_screen()
s.color_profile.reload_from_opts(defaults)
s.color_profile.reload_from_opts(opts)
def q(send, expected=None):
s.callbacks.clear()
parse_bytes(s, b'\x1b]21;' + ';'.join(f'{k}={v}' for k, v in send.items()).encode() + b'\a')
self.ae(s.callbacks.color_control_responses, [expected] if expected else [])
q({k: '?' for k in 'background foreground 213 unknown'.split()}, {
'background': defaults.background, 'foreground': defaults.foreground, '213': defaults.color213, 'unknown': '?'})
'background': opts.background, 'foreground': opts.foreground,
'213': Color(255, 135, 255), 'unknown': '?'})
q({'background':'aquamarine'})
q({'background':'?', 'selection_background': '?'}, {
'background': Color.parse_color('Aquamarine'), 'selection_background': s.color_profile.highlight_bg})
q({'selection_background': ''})
self.assertIsNone(s.color_profile.highlight_bg)
q({'selection_background': '?'}, {'selection_background': ''})
s.color_profile.reload_from_opts(defaults)
s.color_profile.reload_from_opts(opts)
q({'transparent_background_color9': '?'}, {'transparent_background_color9': '?'})
q({'transparent_background_color2': '?'}, {'transparent_background_color2': ''})
q({'transparent_background_color2': 'red@0.5'})

View File

@@ -16,6 +16,246 @@ var nullable_colors = map[string]bool{
// generated by gen-config.py do not edit
// NULLABLE_COLORS_START
"active_border_color": true,
"color100": true,
"color101": true,
"color102": true,
"color103": true,
"color104": true,
"color105": true,
"color106": true,
"color107": true,
"color108": true,
"color109": true,
"color110": true,
"color111": true,
"color112": true,
"color113": true,
"color114": true,
"color115": true,
"color116": true,
"color117": true,
"color118": true,
"color119": true,
"color120": true,
"color121": true,
"color122": true,
"color123": true,
"color124": true,
"color125": true,
"color126": true,
"color127": true,
"color128": true,
"color129": true,
"color130": true,
"color131": true,
"color132": true,
"color133": true,
"color134": true,
"color135": true,
"color136": true,
"color137": true,
"color138": true,
"color139": true,
"color140": true,
"color141": true,
"color142": true,
"color143": true,
"color144": true,
"color145": true,
"color146": true,
"color147": true,
"color148": true,
"color149": true,
"color150": true,
"color151": true,
"color152": true,
"color153": true,
"color154": true,
"color155": true,
"color156": true,
"color157": true,
"color158": true,
"color159": true,
"color16": true,
"color160": true,
"color161": true,
"color162": true,
"color163": true,
"color164": true,
"color165": true,
"color166": true,
"color167": true,
"color168": true,
"color169": true,
"color17": true,
"color170": true,
"color171": true,
"color172": true,
"color173": true,
"color174": true,
"color175": true,
"color176": true,
"color177": true,
"color178": true,
"color179": true,
"color18": true,
"color180": true,
"color181": true,
"color182": true,
"color183": true,
"color184": true,
"color185": true,
"color186": true,
"color187": true,
"color188": true,
"color189": true,
"color19": true,
"color190": true,
"color191": true,
"color192": true,
"color193": true,
"color194": true,
"color195": true,
"color196": true,
"color197": true,
"color198": true,
"color199": true,
"color20": true,
"color200": true,
"color201": true,
"color202": true,
"color203": true,
"color204": true,
"color205": true,
"color206": true,
"color207": true,
"color208": true,
"color209": true,
"color21": true,
"color210": true,
"color211": true,
"color212": true,
"color213": true,
"color214": true,
"color215": true,
"color216": true,
"color217": true,
"color218": true,
"color219": true,
"color22": true,
"color220": true,
"color221": true,
"color222": true,
"color223": true,
"color224": true,
"color225": true,
"color226": true,
"color227": true,
"color228": true,
"color229": true,
"color23": true,
"color230": true,
"color231": true,
"color232": true,
"color233": true,
"color234": true,
"color235": true,
"color236": true,
"color237": true,
"color238": true,
"color239": true,
"color24": true,
"color240": true,
"color241": true,
"color242": true,
"color243": true,
"color244": true,
"color245": true,
"color246": true,
"color247": true,
"color248": true,
"color249": true,
"color25": true,
"color250": true,
"color251": true,
"color252": true,
"color253": true,
"color254": true,
"color255": true,
"color26": true,
"color27": true,
"color28": true,
"color29": true,
"color30": true,
"color31": true,
"color32": true,
"color33": true,
"color34": true,
"color35": true,
"color36": true,
"color37": true,
"color38": true,
"color39": true,
"color40": true,
"color41": true,
"color42": true,
"color43": true,
"color44": true,
"color45": true,
"color46": true,
"color47": true,
"color48": true,
"color49": true,
"color50": true,
"color51": true,
"color52": true,
"color53": true,
"color54": true,
"color55": true,
"color56": true,
"color57": true,
"color58": true,
"color59": true,
"color60": true,
"color61": true,
"color62": true,
"color63": true,
"color64": true,
"color65": true,
"color66": true,
"color67": true,
"color68": true,
"color69": true,
"color70": true,
"color71": true,
"color72": true,
"color73": true,
"color74": true,
"color75": true,
"color76": true,
"color77": true,
"color78": true,
"color79": true,
"color80": true,
"color81": true,
"color82": true,
"color83": true,
"color84": true,
"color85": true,
"color86": true,
"color87": true,
"color88": true,
"color89": true,
"color90": true,
"color91": true,
"color92": true,
"color93": true,
"color94": true,
"color95": true,
"color96": true,
"color97": true,
"color98": true,
"color99": true,
"cursor": true,
"cursor_text_color": true,
"cursor_trail_color": true,