import { LitElement, PropertyValues, html, nothing } from "lit";
import { customElement, property } from "lit/decorators.js";
import { translateText } from "../Utils";
const ACTIVE_CARD =
"bg-blue-500/20 border-blue-500/50 shadow-[0_0_15px_rgba(59,130,246,0.2)]";
const INACTIVE_CARD =
"bg-white/5 border-white/10 hover:bg-white/10 hover:border-white/20";
const INPUT_CLASS =
"w-full text-center rounded bg-black/60 text-white text-sm font-bold border border-white/20 focus:outline-none focus:border-blue-500 p-1 my-1";
const CARD_LABEL_CLASS =
"text-xs uppercase font-bold tracking-wider leading-tight break-words hyphens-auto";
function cardClass(active: boolean, extra = ""): string {
return `w-full h-full rounded-xl border cursor-pointer transition-all duration-200 active:scale-95 ${extra} ${active ? ACTIVE_CARD : INACTIVE_CARD}`;
}
@customElement("toggle-input-card")
export class ToggleInputCard extends LitElement {
@property({ attribute: false }) labelKey = "";
@property({ type: Boolean, attribute: false }) checked = false;
@property({ attribute: false }) inputId?: string;
@property({ attribute: false }) inputType = "number";
@property({ attribute: false }) inputMin?: number | string;
@property({ attribute: false }) inputMax?: number | string;
@property({ attribute: false }) inputStep?: number | string;
@property({ attribute: false }) inputValue?: number | string;
@property({ attribute: false }) inputAriaLabel?: string;
@property({ attribute: false }) inputPlaceholder?: string;
@property({ attribute: false }) defaultInputValue?: number | string;
@property({ attribute: false }) minValidOnEnable?: number;
@property({ attribute: false }) onToggle?: (
checked: boolean,
value: number | string | undefined,
) => void;
@property({ attribute: false }) onInput?: (e: Event) => void;
@property({ attribute: false }) onChange?: (e: Event) => void;
@property({ attribute: false }) onKeyDown?: (e: KeyboardEvent) => void;
createRenderRoot() {
return this;
}
protected updated(changedProperties: PropertyValues) {
if (!changedProperties.has("checked")) return;
const previousChecked = changedProperties.get("checked");
if (previousChecked === false && this.checked) {
const input = this.querySelector("input");
if (input) {
input.focus();
input.select();
}
}
}
private toOptionalNumber(
value: number | string | undefined,
): number | undefined {
if (typeof value === "number") {
return Number.isFinite(value) ? value : undefined;
}
if (typeof value === "string") {
const trimmed = value.trim();
if (!trimmed) return undefined;
const numeric = Number(trimmed);
return Number.isFinite(numeric) ? numeric : undefined;
}
return undefined;
}
private resolveValueOnEnable(): number | string | undefined {
const currentValue = this.inputValue;
if (
currentValue === undefined ||
currentValue === null ||
currentValue === ""
) {
return this.defaultInputValue;
}
if (this.minValidOnEnable === undefined) {
return currentValue;
}
const numericValue = this.toOptionalNumber(currentValue);
if (numericValue === undefined || numericValue < this.minValidOnEnable) {
return this.defaultInputValue;
}
return numericValue;
}
private emitToggle() {
const nextChecked = !this.checked;
const nextValue = nextChecked ? this.resolveValueOnEnable() : undefined;
this.onToggle?.(nextChecked, nextValue);
}
private handleCardClick = () => {
this.emitToggle();
};
render() {
return html`
${this.checked
? html`
`
: nothing}
`;
}
}