import {Component} from "preact"; type Props = Record; type State = { delayIndex: number; intervalId: number | undefined; }; export class ThemeCycler extends Component { delayValues: number[] = [100, 250, 500, 1000, 2500, 5000, 10_000]; constructor(props: Props) { super(props); this.state = { delayIndex: 4, intervalId: undefined, }; } cycle = () => { const themeSelect = document.querySelector("#theme") ?? undefined; if (themeSelect === undefined) { return; } const themeOptions = Array.from(themeSelect.options); const nextIndex = themeOptions.findIndex((option) => option.selected) + 1; themeSelect.selectedIndex = // If the next option can't be found, we're at the end so start back at zero. themeOptions[nextIndex] === undefined ? 0 : nextIndex; // Emit a change event so the Tildes JS handles changing the theme. themeSelect.dispatchEvent(new Event("change")); }; decreaseDelay = () => { const {delayIndex, intervalId} = this.state; if (delayIndex <= 0) { return; } this.setState({delayIndex: delayIndex - 1}, () => { if (intervalId !== undefined) { this.startInterval(); } }); }; increaseDelay = () => { const {delayIndex, intervalId} = this.state; if (delayIndex >= this.delayValues.length - 1) { return; } this.setState({delayIndex: delayIndex + 1}, () => { if (intervalId !== undefined) { this.startInterval(); } }); }; startInterval = () => { const {delayIndex, intervalId} = this.state; if (intervalId !== undefined) { window.clearInterval(intervalId); } this.setState({ intervalId: window.setInterval(this.cycle, this.delayValues[delayIndex]), }); }; toggle = () => { const {intervalId} = this.state; if (intervalId === undefined) { this.startInterval(); this.cycle(); } else { window.clearInterval(intervalId); this.setState({intervalId: undefined}); } }; render() { const isEnabled = this.state.intervalId !== undefined; const delay = this.delayValues[this.state.delayIndex]; return (

Theme Cycler ({delay / 1000}s)

); } }