Added color reducer. Performed state management refactor to prevent circular behavior.

This commit is contained in:
Jay
2025-08-06 14:26:55 -04:00
parent c27a5258d3
commit e011bd0763
21 changed files with 2592 additions and 799 deletions
+143
View File
@@ -0,0 +1,143 @@
import type { Dispatch } from "react";
import * as colorlib from "colorlib";
import type { SetterValueOrCallback } from "@/types";
export interface ColorState {
color: colorlib.Color;
}
export type ColorAction =
| { type: "SET_COLOR"; payload: colorlib.Color }
| { type: "SET_RGB"; payload: colorlib.RGB }
| { type: "SET_HSV"; payload: colorlib.HSV }
| { type: "SET_HCL"; payload: colorlib.HCL }
| { type: "SET_HEX"; payload: colorlib.Hex }
| {
type: "SET_VALUE";
component: colorlib.Component;
payload: SetterValueOrCallback<number>;
};
export function colorReducer(
state: ColorState,
action: ColorAction,
): ColorState {
let comp;
switch (action.type) {
case "SET_COLOR":
return { ...state, color: action.payload };
case "SET_RGB":
let rgb = action.payload;
return { ...state, color: colorlib.Color.from_rgb(rgb.r, rgb.g, rgb.b) };
case "SET_HSV":
let hsv = action.payload;
return { ...state, color: colorlib.Color.from_hsv(hsv.h, hsv.s, hsv.v) };
case "SET_HCL":
let hcl = action.payload;
return { ...state, color: colorlib.Color.from_hcl(hcl.h, hcl.c, hcl.l) };
case "SET_HEX":
let hex = action.payload;
return { ...state, color: colorlib.Color.from_hex(hex.to_code()) };
case "SET_VALUE":
comp = action.component;
let valOrFn = action.payload;
if (typeof valOrFn === "function") {
let prev = state.color.get(comp);
return { ...state, color: state.color.update(comp, valOrFn(prev)) };
} else {
return { ...state, color: state.color.update(comp, valOrFn) };
}
default:
return state;
}
}
type Setter = (valOrCallback: SetterValueOrCallback<number>) => void;
export interface CommonColorActions {
setColor: (color: colorlib.Color) => void;
}
export interface RGBColorActions {
setRGB: (rgb: colorlib.RGB) => void;
setR: Setter;
setG: Setter;
setB: Setter;
}
export interface HSVColorActions {
setHSV: (hsv: colorlib.HSV) => void;
setH: Setter;
setS: Setter;
setV: Setter;
}
export interface HCLColorActions {
setHCL: (hcl: colorlib.HCL) => void;
setH: Setter;
setC: Setter;
setL: Setter;
}
export interface HexColorActions {
setHex: (hex: colorlib.Hex) => void;
}
export interface ColorActions {
common: CommonColorActions;
rgb: RGBColorActions;
hsv: HSVColorActions;
hcl: HCLColorActions;
hex: HexColorActions;
}
export function createColorActions(
dispatch: Dispatch<ColorAction>,
): ColorActions {
const Comp = colorlib.Component;
const setValue = (
comp: colorlib.Component,
payload: SetterValueOrCallback<number>,
) => dispatch({ type: "SET_VALUE", component: comp, payload });
return {
common: {
setColor: (payload) => dispatch({ type: "SET_COLOR", payload }),
},
rgb: {
setRGB: (rgb) => dispatch({ type: "SET_RGB", payload: rgb }),
setR: (val) => setValue(Comp.RGB_R, val),
setG: (val) => setValue(Comp.RGB_G, val),
setB: (val) => setValue(Comp.RGB_B, val),
},
hsv: {
setHSV: (hsv) => dispatch({ type: "SET_HSV", payload: hsv }),
setH: (val) => setValue(Comp.HSV_H, val),
setS: (val) => setValue(Comp.HSV_S, val),
setV: (val) => setValue(Comp.HSV_V, val),
},
hcl: {
setHCL: (hcl) => dispatch({ type: "SET_HCL", payload: hcl }),
setH: (val) => setValue(Comp.HCL_H, val),
setC: (val) => setValue(Comp.HCL_C, val),
setL: (val) => setValue(Comp.HCL_L, val),
},
hex: {
setHex: (hex) => dispatch({ type: "SET_HEX", payload: hex }),
},
};
}