Files
aurora-curator/src/components/Icons.tsx
T
Renamr Scaffold 03390b43f1 Add a Settings area with 4 color themes (Aurora, Light, Ocean, Sunset)
Requested directly: "lets add some themeing into it now, perhaps
under the configuration, have white/black, and some more colors."
There was no existing app-wide Settings/Configuration surface -
every prior setting lived in its own panel-specific modal (Fetch
Data Settings, subtitle provider settings) - so this adds the
app's first one: a palette-icon button in the sidebar footer opens
a new Settings modal with a 2x2 grid of theme swatches.

Four themes: Aurora (the existing dark teal/green look, unchanged,
stays the default), Light (a clean white/black theme - the literal
"white/black" ask), Ocean (a cool blue-toned dark variant), and
Sunset (a warm amber-toned dark variant) - the "some more colors"
part. Picking one applies instantly via a `data-theme` attribute on
<html> and persists through new get_theme/save_theme commands
(added to settings.rs/lib.rs alongside delivery 25's movie-naming-
scheme fix), applied on every future launch by a boot-time effect
in App.tsx so it takes effect even if Settings is never reopened.

theme.css's variable set was expanded to cover every place a color
was previously hardcoded outside the existing --dock/--surface/etc.
variables, so the whole app actually re-themes instead of leaving
dark boxes behind on the Light theme: button resting/hover/active
shades, the Load-files popup background, the primary button's hover
tint, the header's gradient stops, and five levels of white-tint
row/button hover highlights (RenamePanel.css/Header.css) all moved
to new variables (--btn-bg*, --popup-bg, --accent-hover, --header-
grad-a/b, --tint-02/03/05/06/16) with theme-specific values - the
light theme in particular needed dark tints instead of white ones
for hover states to stay visible on a white background.

Verified with a new Playwright script covering: default theme on a
fresh install, the Settings modal listing all 4 themes with the
right one marked selected, clicking a theme applying it immediately
(actual computed background color and CSS variable checked, not
just the data-theme attribute) and saving it, and a previously-saved
theme applying on boot before Settings is ever opened. Screenshots
taken of all 4 themes across the main view and the Naming Scheme
editor (whose buttons/popups were part of the hardcoded-color
cleanup) to confirm visually. All prior verification suites (47
checks across naming-scheme/match-fetch/hash-files/movie-scheme),
`cargo test --workspace` (162 tests), and `npm run build` still
pass clean.
2026-08-30 05:24:48 +00:00

179 lines
4.5 KiB
TypeScript

// Small line-icon set for the sidebar panels. The original app used bitmap icon
// resources (ResourceManager.getIcon("panel.rename") etc.) that aren't available to
// port directly, so these are fresh SVGs matching the same one-glyph-per-panel idea.
import type { SVGProps } from "react";
const base: SVGProps<SVGSVGElement> = {
width: 18,
height: 18,
viewBox: "0 0 24 24",
fill: "none",
stroke: "currentColor",
strokeWidth: 1.8,
strokeLinecap: "round",
strokeLinejoin: "round",
};
export function RenameIcon() {
return (
<svg {...base}>
<path d="M4 7h9l3 3-3 3H4z" />
<path d="M20 17h-9l-3-3 3-3h9" />
</svg>
);
}
export function EpisodesIcon() {
return (
<svg {...base}>
<rect x="3.5" y="5" width="17" height="15" rx="2" />
<path d="M3.5 9.5h17M8 3v4M16 3v4" />
</svg>
);
}
export function SubtitlesIcon() {
return (
<svg {...base}>
<rect x="3" y="5.5" width="18" height="13" rx="2" />
<path d="M7 14h4M13 14h4M7 10.5h10" />
</svg>
);
}
export function SfvIcon() {
return (
<svg {...base}>
<path d="M12 3l7 3v6c0 4.5-3 7.5-7 9-4-1.5-7-4.5-7-9V6z" />
<path d="M9 12l2 2 4-4" />
</svg>
);
}
export function FilterIcon() {
return (
<svg {...base}>
<path d="M4 5h16l-6 7.5V19l-4 2v-8.5z" />
</svg>
);
}
export function ListIcon() {
return (
<svg {...base}>
<path d="M8 6h12M8 12h12M8 18h12" />
<circle cx="4" cy="6" r="1.2" fill="currentColor" stroke="none" />
<circle cx="4" cy="12" r="1.2" fill="currentColor" stroke="none" />
<circle cx="4" cy="18" r="1.2" fill="currentColor" stroke="none" />
</svg>
);
}
export function GearIcon() {
return (
<svg {...{ ...base, width: 16, height: 16 }}>
<circle cx="12" cy="12" r="3" />
<path d="M12 3v2.5M12 18.5V21M21 12h-2.5M5.5 12H3M18.4 5.6l-1.8 1.8M7.4 16.6l-1.8 1.8M18.4 18.4l-1.8-1.8M7.4 7.4 5.6 5.6" />
</svg>
);
}
export function LoadIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<path d="M4 15v3a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2v-3M12 3v12M7 10l5 5 5-5" />
</svg>
);
}
export function UpIcon() {
return (
<svg {...{ ...base, width: 13, height: 13 }}>
<path d="M6 15l6-6 6 6" />
</svg>
);
}
export function DownIcon() {
return (
<svg {...{ ...base, width: 13, height: 13 }}>
<path d="M6 9l6 6 6-6" />
</svg>
);
}
export function RemoveIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<path d="M5 5l14 14M19 5L5 19" />
</svg>
);
}
export function ClearIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<path d="M4 7h16M9 7V5a1 1 0 0 1 1-1h4a1 1 0 0 1 1 1v2M6 7l1 12a2 2 0 0 0 2 2h6a2 2 0 0 0 2-2l1-12" />
</svg>
);
}
export function HistoryIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<path d="M4 12a8 8 0 1 0 2.6-5.9" />
<path d="M4 4v4h4M12 8v4l3 2" />
</svg>
);
}
export function PresetsIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<path d="M4 6h16M4 12h10M4 18h7" />
<circle cx="19" cy="15" r="2.5" />
</svg>
);
}
export function FetchIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<circle cx="11" cy="11" r="6.5" />
<path d="M20 20l-4.3-4.3" />
</svg>
);
}
export function KeyIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<circle cx="8" cy="15" r="4" />
<path d="M11 12l9-9M16 5l3 3M13 8l3 3" />
</svg>
);
}
export function HashIcon() {
return (
<svg {...{ ...base, width: 15, height: 15 }}>
<path d="M9 3.5L6.5 20.5M17.5 3.5L15 20.5M4 8.5h16M3 15.5h16" />
</svg>
);
}
// Used for the app-wide Settings entry (theme picker) in the sidebar footer -
// deliberately a palette rather than reusing GearIcon, which already means something
// different (the per-file Naming Scheme editor's trigger button in the Rename panel).
export function PaletteIcon() {
return (
<svg {...{ ...base, width: 16, height: 16 }}>
<path d="M12 3.5c-4.7 0-8.5 3.8-8.5 8.5s3.8 8.5 8.5 8.5c1 0 1.7-.8 1.7-1.7 0-.45-.17-.86-.46-1.16-.29-.31-.46-.72-.46-1.17 0-.94.76-1.7 1.7-1.7h2c2.6 0 4.7-2.1 4.7-4.7 0-4.15-4.1-7.55-9.19-7.55Z" />
<circle cx="7.7" cy="11" r="1.15" fill="currentColor" stroke="none" />
<circle cx="10.2" cy="7.3" r="1.15" fill="currentColor" stroke="none" />
<circle cx="14.4" cy="7.6" r="1.15" fill="currentColor" stroke="none" />
<circle cx="16.6" cy="11.2" r="1.15" fill="currentColor" stroke="none" />
</svg>
);
}