forked from Shinonome/caelestia-cli
internal: refactor scheme
Also use a single file to store scheme data
This commit is contained in:
@@ -1,120 +0,0 @@
|
||||
import os
|
||||
from pathlib import Path
|
||||
|
||||
config_dir = Path(os.getenv("XDG_CONFIG_HOME", Path.home() / ".config"))
|
||||
data_dir = Path(os.getenv("XDG_DATA_HOME", Path.home() / ".local/share"))
|
||||
state_dir = Path(os.getenv("XDG_STATE_HOME", Path.home() / ".local/state"))
|
||||
|
||||
c_config_dir = config_dir / "caelestia"
|
||||
c_data_dir = data_dir / "caelestia"
|
||||
c_state_dir = state_dir / "caelestia"
|
||||
|
||||
scheme_name_path = c_state_dir / "scheme/name.txt"
|
||||
scheme_flavour_path = c_state_dir / "scheme/flavour.txt"
|
||||
scheme_colours_path = c_state_dir / "scheme/colours.txt"
|
||||
scheme_mode_path = c_state_dir / "scheme/mode.txt"
|
||||
scheme_variant_path = c_state_dir / "scheme/variant.txt"
|
||||
|
||||
scheme_data_path = Path(__file__).parent / "data/schemes"
|
||||
|
||||
scheme_variants = [
|
||||
"tonalspot",
|
||||
"vibrant",
|
||||
"expressive",
|
||||
"fidelity",
|
||||
"fruitsalad",
|
||||
"monochrome",
|
||||
"neutral",
|
||||
"rainbow",
|
||||
"content",
|
||||
]
|
||||
|
||||
scheme_names: list[str] = None
|
||||
scheme_flavours: list[str] = None
|
||||
scheme_modes: list[str] = None
|
||||
|
||||
scheme_name: str = None
|
||||
scheme_flavour: str = None
|
||||
scheme_colours: dict[str, str] = None
|
||||
scheme_mode: str = None
|
||||
scheme_variant: str = None
|
||||
|
||||
|
||||
def get_scheme_path() -> Path:
|
||||
return (scheme_data_path / get_scheme_name() / get_scheme_flavour() / get_scheme_mode()).with_suffix(".txt")
|
||||
|
||||
|
||||
def get_scheme_names() -> list[str]:
|
||||
global scheme_names
|
||||
|
||||
if scheme_names is None:
|
||||
scheme_names = [f.name for f in scheme_data_path.iterdir() if f.is_dir()]
|
||||
|
||||
return scheme_names
|
||||
|
||||
|
||||
def get_scheme_flavours() -> list[str]:
|
||||
global scheme_flavours
|
||||
|
||||
if scheme_flavours is None:
|
||||
scheme_flavours = [f.name for f in (scheme_data_path / get_scheme_name()).iterdir() if f.is_dir()]
|
||||
|
||||
return scheme_flavours
|
||||
|
||||
|
||||
def get_scheme_modes() -> list[str]:
|
||||
global scheme_modes
|
||||
|
||||
if scheme_modes is None:
|
||||
scheme_modes = [
|
||||
f.stem for f in (scheme_data_path / get_scheme_name() / get_scheme_flavour()).iterdir() if f.is_file()
|
||||
]
|
||||
|
||||
return scheme_modes
|
||||
|
||||
|
||||
def get_scheme_name() -> str:
|
||||
global scheme_name
|
||||
|
||||
if scheme_name is None:
|
||||
scheme_name = scheme_name_path.read_text().strip() if scheme_name_path.exists() else "catppuccin"
|
||||
|
||||
return scheme_name
|
||||
|
||||
|
||||
def get_scheme_flavour() -> str:
|
||||
global scheme_flavour
|
||||
|
||||
if scheme_flavour is None:
|
||||
scheme_flavour = scheme_flavour_path.read_text().strip() if scheme_flavour_path.exists() else "mocha"
|
||||
|
||||
return scheme_flavour
|
||||
|
||||
|
||||
def get_scheme_colours() -> dict[str, str]:
|
||||
global scheme_colours
|
||||
|
||||
if scheme_colours is None:
|
||||
scheme_colours = {
|
||||
k.strip(): v.strip() for k, v in (line.split(" ") for line in get_scheme_path().read_text().splitlines())
|
||||
}
|
||||
|
||||
return scheme_colours
|
||||
|
||||
|
||||
def get_scheme_mode() -> str:
|
||||
global scheme_mode
|
||||
|
||||
if scheme_mode is None:
|
||||
scheme_mode = scheme_mode_path.read_text().strip() if scheme_mode_path.exists() else "dark"
|
||||
|
||||
return scheme_mode
|
||||
|
||||
|
||||
def get_scheme_variant() -> str:
|
||||
global scheme_variant
|
||||
|
||||
if scheme_variant is None:
|
||||
scheme_variant = scheme_variant_path.read_text().strip() if scheme_variant_path.exists() else "tonalspot"
|
||||
|
||||
return scheme_variant
|
||||
@@ -1,6 +1,5 @@
|
||||
import argparse
|
||||
|
||||
from caelestia.data import get_scheme_names, scheme_variants
|
||||
from caelestia.subcommands import (
|
||||
clipboard,
|
||||
emoji,
|
||||
@@ -14,6 +13,7 @@ from caelestia.subcommands import (
|
||||
wallpaper,
|
||||
wsaction,
|
||||
)
|
||||
from caelestia.utils.scheme import get_scheme_names, scheme_variants
|
||||
|
||||
|
||||
def parse_args() -> (argparse.ArgumentParser, argparse.Namespace):
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import subprocess
|
||||
from argparse import Namespace
|
||||
|
||||
from caelestia import data
|
||||
from caelestia.utils import paths
|
||||
|
||||
|
||||
class Command:
|
||||
@@ -25,7 +25,7 @@ class Command:
|
||||
self.shell()
|
||||
|
||||
def shell(self, *args: list[str]) -> str:
|
||||
return subprocess.check_output(["qs", "-p", data.c_data_dir / "shell", *args], text=True)
|
||||
return subprocess.check_output(["qs", "-p", paths.c_data_dir / "shell", *args], text=True)
|
||||
|
||||
def print_ipc(self) -> None:
|
||||
print(self.shell("ipc", "show"), end="")
|
||||
|
||||
@@ -5,7 +5,7 @@ import socket
|
||||
socket_path = f"{os.getenv('XDG_RUNTIME_DIR')}/hypr/{os.getenv('HYPRLAND_INSTANCE_SIGNATURE')}/.socket.sock"
|
||||
|
||||
|
||||
def message(msg: str, json: bool = True) -> str or dict[str, any]:
|
||||
def message(msg: str, json: bool = True) -> str | dict[str, any]:
|
||||
with socket.socket(socket.AF_UNIX, socket.SOCK_STREAM) as sock:
|
||||
sock.connect(socket_path)
|
||||
|
||||
|
||||
@@ -0,0 +1,13 @@
|
||||
import os
|
||||
from pathlib import Path
|
||||
|
||||
config_dir = Path(os.getenv("XDG_CONFIG_HOME", Path.home() / ".config"))
|
||||
data_dir = Path(os.getenv("XDG_DATA_HOME", Path.home() / ".local/share"))
|
||||
state_dir = Path(os.getenv("XDG_STATE_HOME", Path.home() / ".local/state"))
|
||||
|
||||
c_config_dir = config_dir / "caelestia"
|
||||
c_data_dir = data_dir / "caelestia"
|
||||
c_state_dir = state_dir / "caelestia"
|
||||
|
||||
scheme_path = c_state_dir / "scheme.json"
|
||||
scheme_data_path = Path(__file__).parent.parent / "data/schemes"
|
||||
@@ -0,0 +1,194 @@
|
||||
import json
|
||||
from pathlib import Path
|
||||
|
||||
from caelestia.utils.paths import scheme_data_path, scheme_path
|
||||
|
||||
|
||||
class Scheme:
|
||||
_name: str
|
||||
_flavour: str
|
||||
_mode: str
|
||||
_variant: str
|
||||
_colours: dict[str, str]
|
||||
|
||||
def __init__(self, json: dict[str, any] | None) -> None:
|
||||
if json is None:
|
||||
self._name = "catppuccin"
|
||||
self._flavour = "mocha"
|
||||
self._mode = "dark"
|
||||
self._variant = "tonalspot"
|
||||
self._colours = read_colours_from_file(self.get_colours_path())
|
||||
else:
|
||||
self._name = json["name"]
|
||||
self._flavour = json["flavour"]
|
||||
self._mode = json["mode"]
|
||||
self._variant = json["variant"]
|
||||
self._colours = json["colours"]
|
||||
|
||||
@property
|
||||
def name(self) -> str:
|
||||
return self._name
|
||||
|
||||
@name.setter
|
||||
def name(self, name: str) -> None:
|
||||
if name == self._name:
|
||||
return
|
||||
|
||||
if name not in get_scheme_names():
|
||||
raise ValueError(f"Invalid scheme name: {name}")
|
||||
|
||||
self._name = name
|
||||
self._check_flavour()
|
||||
self._check_mode()
|
||||
self._update_colours()
|
||||
self.save()
|
||||
|
||||
@property
|
||||
def flavour(self) -> str:
|
||||
return self._flavour
|
||||
|
||||
@flavour.setter
|
||||
def flavour(self, flavour: str) -> None:
|
||||
if flavour == self._flavour:
|
||||
return
|
||||
|
||||
if flavour not in get_scheme_flavours():
|
||||
raise ValueError(f"Invalid scheme flavour: {flavour}")
|
||||
|
||||
self._flavour = flavour
|
||||
self._check_mode()
|
||||
self._update_colours()
|
||||
self.save()
|
||||
|
||||
@property
|
||||
def mode(self) -> str:
|
||||
return self._mode
|
||||
|
||||
@mode.setter
|
||||
def mode(self, mode: str) -> None:
|
||||
if mode == self._mode:
|
||||
return
|
||||
|
||||
if mode not in get_scheme_modes():
|
||||
raise ValueError(f"Invalid scheme mode: {mode}")
|
||||
|
||||
self._mode = mode
|
||||
self._update_colours()
|
||||
self.save()
|
||||
|
||||
@property
|
||||
def variant(self) -> str:
|
||||
return self._variant
|
||||
|
||||
@variant.setter
|
||||
def variant(self, variant: str) -> None:
|
||||
self._variant = variant
|
||||
|
||||
@property
|
||||
def colours(self) -> dict[str, str]:
|
||||
return self._colours
|
||||
|
||||
def get_colours_path(self) -> Path:
|
||||
return (scheme_data_path / self.name / self.flavour / self.mode).with_suffix(".txt")
|
||||
|
||||
def save(self) -> None:
|
||||
scheme_path.parent.mkdir(parents=True, exist_ok=True)
|
||||
with scheme_path.open("w") as f:
|
||||
json.dump(
|
||||
{
|
||||
"name": self.name,
|
||||
"flavour": self.flavour,
|
||||
"mode": self.mode,
|
||||
"variant": self.variant,
|
||||
"colours": self.colours,
|
||||
},
|
||||
f,
|
||||
)
|
||||
|
||||
def _check_flavour(self) -> None:
|
||||
global scheme_flavours
|
||||
scheme_flavours = None
|
||||
if self._flavour not in get_scheme_flavours():
|
||||
self._flavour = get_scheme_flavours()[0]
|
||||
|
||||
def _check_mode(self) -> None:
|
||||
global scheme_modes
|
||||
scheme_modes = None
|
||||
if self._mode not in get_scheme_modes():
|
||||
self._mode = get_scheme_modes()[0]
|
||||
|
||||
def _update_colours(self) -> None:
|
||||
self._colours = read_colours_from_file(self.get_colours_path())
|
||||
|
||||
|
||||
scheme_variants = [
|
||||
"tonalspot",
|
||||
"vibrant",
|
||||
"expressive",
|
||||
"fidelity",
|
||||
"fruitsalad",
|
||||
"monochrome",
|
||||
"neutral",
|
||||
"rainbow",
|
||||
"content",
|
||||
]
|
||||
|
||||
scheme_names: list[str] = None
|
||||
scheme_flavours: list[str] = None
|
||||
scheme_modes: list[str] = None
|
||||
|
||||
scheme: Scheme = None
|
||||
|
||||
|
||||
def read_colours_from_file(path: Path) -> dict[str, str]:
|
||||
return {k.strip(): v.strip() for k, v in (line.split(" ") for line in path.read_text().splitlines())}
|
||||
|
||||
|
||||
def get_scheme_path() -> Path:
|
||||
return get_scheme().get_colours_path()
|
||||
|
||||
|
||||
def get_scheme() -> Scheme:
|
||||
global scheme
|
||||
|
||||
if scheme is None:
|
||||
try:
|
||||
scheme_json = json.loads(scheme_path.read_text())
|
||||
scheme = Scheme(scheme_json)
|
||||
except (IOError, json.JSONDecodeError):
|
||||
scheme = Scheme(None)
|
||||
|
||||
return scheme
|
||||
|
||||
|
||||
def get_scheme_names() -> list[str]:
|
||||
global scheme_names
|
||||
|
||||
if scheme_names is None:
|
||||
scheme_names = [f.name for f in scheme_data_path.iterdir() if f.is_dir()]
|
||||
scheme_names.append("dynamic")
|
||||
|
||||
return scheme_names
|
||||
|
||||
|
||||
def get_scheme_flavours() -> list[str]:
|
||||
global scheme_flavours
|
||||
|
||||
if scheme_flavours is None:
|
||||
name = get_scheme().name
|
||||
if name == "dynamic":
|
||||
scheme_flavours = ["default", "alt1", "alt2"]
|
||||
else:
|
||||
scheme_flavours = [f.name for f in (scheme_data_path / name).iterdir() if f.is_dir()]
|
||||
|
||||
return scheme_flavours
|
||||
|
||||
|
||||
def get_scheme_modes() -> list[str]:
|
||||
global scheme_modes
|
||||
|
||||
if scheme_modes is None:
|
||||
scheme = get_scheme()
|
||||
scheme_modes = [f.stem for f in (scheme_data_path / scheme.name / scheme.flavour).iterdir() if f.is_file()]
|
||||
|
||||
return scheme_modes
|
||||
|
||||
Reference in New Issue
Block a user