Updated Complete Tailwindcss Classes
This commit is contained in:
+76
-63
@@ -53,47 +53,48 @@ const descId = p.description ? `${fieldId}-desc` : undefined;
|
||||
const errId = `${fieldId}-err`;
|
||||
|
||||
const inputBase = cva(
|
||||
"py-2.5 sm:py-3 px-4 block w-full border-gray-200 rounded-lg sm:text-sm focus:border-blue-500 focus:ring-blue-500 disabled:opacity-50 disabled:pointer-events-none dark:bg-neutral-900 dark:border-neutral-700 dark:text-neutral-400 dark:placeholder-neutral-500 dark:focus:ring-neutral-600",
|
||||
"wr:py-2.5 wr:sm:py-3 wr:px-4 wr:block wr:w-full wr:border-gray-200 wr:rounded-lg wr:sm:text-sm wr:focus:border-blue-500 wr:focus:ring-blue-500 wr:disabled:opacity-50 wr:disabled:pointer-events-none wr:dark:bg-neutral-900 wr:dark:border-neutral-700 wr:dark:text-neutral-400 wr:dark:placeholder-neutral-500 wr:dark:focus:ring-neutral-600",
|
||||
{
|
||||
variants: {
|
||||
size: {
|
||||
sm: "h-10 px-3 text-sm",
|
||||
md: "h-11 px-3 text-sm",
|
||||
lg: "h-12 px-4 text-base",
|
||||
sm: "wr:h-10 wr:px-3 wr:text-sm",
|
||||
md: "wr:h-11 wr:px-3 wr:text-sm",
|
||||
lg: "wr:h-12 wr:px-4 wr:text-base",
|
||||
},
|
||||
withIconLeft: { true: "pl-10" },
|
||||
withIconRight: { true: "pr-10" },
|
||||
withIconLeft: { true: "wr:pl-10" },
|
||||
withIconRight: { true: "wr:pr-10" },
|
||||
},
|
||||
},
|
||||
);
|
||||
|
||||
const selectBase = cva(
|
||||
"py-3 px-4 pe-9 block w-full border-gray-200 rounded-lg text-sm focus:border-blue-500 focus:ring-blue-500 disabled:opacity-50 disabled:pointer-events-none dark:bg-neutral-900 dark:border-neutral-700 dark:text-neutral-400 dark:placeholder-neutral-500 dark:focus:ring-neutral-600",
|
||||
"wr:py-3 wr:px-4 wr:pe-9 wr:block wr:w-full wr:border-gray-200 wr:rounded-lg wr:text-sm wr:focus:border-blue-500 wr:focus:ring-blue-500 wr:disabled:opacity-50 wr:disabled:pointer-events-none wr:dark:bg-neutral-900 wr:dark:border-neutral-700 wr:dark:text-neutral-400 wr:dark:placeholder-neutral-500 wr:dark:focus:ring-neutral-600",
|
||||
{
|
||||
variants: {
|
||||
size: {
|
||||
sm: "h-10 px-3 text-sm",
|
||||
md: "h-11 px-3 text-sm",
|
||||
lg: "h-12 px-4 text-base",
|
||||
sm: "wr:h-10 wr:px-3 wr:text-sm",
|
||||
md: "wr:h-11 wr:px-3 wr:text-sm",
|
||||
lg: "wr:h-12 wr:px-4 wr:text-base",
|
||||
},
|
||||
withIconLeft: { true: "pl-10" },
|
||||
withIconRight: { true: "pr-10" },
|
||||
withIconLeft: { true: "wr:pl-10" },
|
||||
withIconRight: { true: "wr:pr-10" },
|
||||
},
|
||||
},
|
||||
);
|
||||
|
||||
const iconSize =
|
||||
p.size === "sm" ? "size-4" : p.size === "lg" ? "size-5" : "size-5";
|
||||
const labelCls = "block text-sm font-medium mb-2 dark:text-white";
|
||||
const helpCls = "mt-2 text-sm text-gray-500 dark:text-neutral-500";
|
||||
const errCls = "text-sm text-red-600 mt-2";
|
||||
const groupCls = "relative flex items-stretch";
|
||||
p.size === "sm" ? "wr:size-4" : p.size === "lg" ? "wr:size-5" : "wr:size-5";
|
||||
const labelCls =
|
||||
"wr:block wr:text-sm wr:font-medium wr:mb-2 wr:dark:text-white";
|
||||
const helpCls = "wr:mt-2 wr:text-sm wr:text-gray-500 wr:dark:text-neutral-500";
|
||||
const errCls = "wr:text-sm wr:text-red-600 wr:mt-2";
|
||||
const groupCls = "wr:relative wr:flex wr:items-stretch";
|
||||
const addonBase =
|
||||
"px-4 inline-flex items-center min-w-fit rounded-md border border-gray-200 bg-gray-50 text-sm text-gray-500 dark:bg-neutral-700 dark:border-neutral-700 dark:text-neutral-400";
|
||||
const controlWrap = "relative";
|
||||
"wr:px-4 wr:inline-flex wr:items-center wr:min-w-fit wr:rounded-md wr:border wr:border-gray-200 wr:bg-gray-50 wr:text-sm wr:text-gray-500 wr:dark:bg-neutral-700 wr:dark:border-neutral-700 wr:dark:text-neutral-400";
|
||||
const controlWrap = "wr:relative";
|
||||
---
|
||||
|
||||
<div class={cn("space-y-1.5", p.class)} data-field={p.name}>
|
||||
<div class={cn("wr:space-y-1.5", p.class)} data-field={p.name}>
|
||||
{
|
||||
p.label &&
|
||||
[
|
||||
@@ -108,7 +109,8 @@ const controlWrap = "relative";
|
||||
"select",
|
||||
].includes(p.kind ?? "text") && (
|
||||
<label for={fieldId} class={labelCls}>
|
||||
{p.label} {p.required && <span class="text-danger">*</span>}
|
||||
{p.label}{" "}
|
||||
{p.required && <span class="wr:text-danger">*</span>}
|
||||
</label>
|
||||
)
|
||||
}
|
||||
@@ -119,14 +121,16 @@ const controlWrap = "relative";
|
||||
) && (
|
||||
<div class={groupCls}>
|
||||
{p.prefixText && (
|
||||
<span class={cn(addonBase, "border-r-0 rounded-r-none")}>
|
||||
<span
|
||||
class={cn(addonBase, "wr:border-r-0 wr:rounded-r-none")}
|
||||
>
|
||||
{p.prefixText}
|
||||
</span>
|
||||
)}
|
||||
|
||||
<div class={cn(controlWrap, "flex-1")}>
|
||||
<div class={cn(controlWrap, "wr:flex-1")}>
|
||||
{p.iconLeft && (
|
||||
<span class="absolute inset-y-0 left-0 flex items-center pl-3 pointer-events-none text-muted-foreground">
|
||||
<span class="wr:absolute wr:inset-y-0 wr:left-0 wr:flex wr:items-center wr:pl-3 wr:pointer-events-none wr:text-muted-foreground">
|
||||
<Icon name={p.iconLeft} class={iconSize} />
|
||||
</span>
|
||||
)}
|
||||
@@ -142,10 +146,10 @@ const controlWrap = "relative";
|
||||
withIconRight:
|
||||
!!p.iconRight || p.kind === "password",
|
||||
}),
|
||||
p.prefixText && "rounded-l-none",
|
||||
p.suffixText && "rounded-r-none",
|
||||
p.prefixText && "wr:rounded-l-none",
|
||||
p.suffixText && "wr:rounded-r-none",
|
||||
p.error &&
|
||||
"border-danger focus-visible:ring-danger/40",
|
||||
"wr:border-danger wr:focus-visible:ring-danger/40",
|
||||
)}
|
||||
data-control
|
||||
placeholder={p.placeholder}
|
||||
@@ -168,7 +172,7 @@ const controlWrap = "relative";
|
||||
{p.kind === "password" && (
|
||||
<button
|
||||
type="button"
|
||||
class="absolute inset-y-0 right-0 pr-3 flex items-center text-muted-foreground hover:text-foreground"
|
||||
class="wr:absolute wr:inset-y-0 wr:right-0 wr:pr-3 wr:flex wr:items-center wr:text-muted-foreground hover:wr:text-foreground"
|
||||
onclick={`const i = this.previousElementSibling; i.type = i.type === 'password' ? 'text' : 'password';`}
|
||||
>
|
||||
<Icon name="mdi:eye" class={iconSize} />
|
||||
@@ -176,14 +180,16 @@ const controlWrap = "relative";
|
||||
)}
|
||||
|
||||
{p.iconRight && (
|
||||
<span class="absolute inset-y-0 right-0 pr-3 flex items-center pointer-events-none text-muted-foreground">
|
||||
<span class="wr:absolute wr:inset-y-0 wr:right-0 wr:pr-3 wr:flex wr:items-center wr:pointer-events-none wr:text-muted-foreground">
|
||||
<Icon name={p.iconRight} class={iconSize} />
|
||||
</span>
|
||||
)}
|
||||
</div>
|
||||
|
||||
{p.suffixText && (
|
||||
<span class={cn(addonBase, "border-l-0 rounded-l-none")}>
|
||||
<span
|
||||
class={cn(addonBase, "wr:border-l-0 wr:rounded-l-none")}
|
||||
>
|
||||
{p.suffixText}
|
||||
</span>
|
||||
)}
|
||||
@@ -195,14 +201,16 @@ const controlWrap = "relative";
|
||||
p.kind === "file" && (
|
||||
<div class={groupCls}>
|
||||
{p.prefixText && (
|
||||
<span class={cn(addonBase, "border-r-0 rounded-r-none")}>
|
||||
<span
|
||||
class={cn(addonBase, "wr:border-r-0 wr:rounded-r-none")}
|
||||
>
|
||||
{p.prefixText}
|
||||
</span>
|
||||
)}
|
||||
|
||||
<div class={cn(controlWrap, "flex-1")}>
|
||||
<div class={cn(controlWrap, "wr:flex-1")}>
|
||||
{p.iconLeft && (
|
||||
<span class="absolute inset-y-0 left-0 flex items-center pl-3 pointer-events-none text-muted-foreground">
|
||||
<span class="wr:absolute wr:inset-y-0 wr:left-0 wr:flex wr:items-center wr:pl-3 wr:pointer-events-none wr:text-muted-foreground">
|
||||
<Icon name={p.iconLeft} class={iconSize} />
|
||||
</span>
|
||||
)}
|
||||
@@ -212,11 +220,11 @@ const controlWrap = "relative";
|
||||
name={p.name}
|
||||
type={(p.kind as any) ?? "text"}
|
||||
class={cn(
|
||||
"block w-full border border-gray-200 shadow-sm rounded-lg text-sm focus:z-10 focus:border-blue-500 focus:ring-blue-500 disabled:opacity-50 disabled:pointer-events-none dark:bg-neutral-900 dark:border-neutral-700 dark:text-neutral-400 file:bg-gray-50 file:border-0 file:me-4 file:py-3 file:px-4 dark:file:bg-neutral-700 dark:file:text-neutral-400",
|
||||
p.prefixText && "rounded-l-none",
|
||||
p.suffixText && "rounded-r-none",
|
||||
"wr:block wr:w-full wr:border wr:border-gray-200 wr:shadow-sm wr:rounded-lg wr:text-sm wr:focus:z-10 wr:focus:border-blue-500 wr:focus:ring-blue-500 wr:disabled:opacity-50 wr:disabled:pointer-events-none wr:dark:bg-neutral-900 wr:dark:border-neutral-700 wr:dark:text-neutral-400 wr:file:bg-gray-50 wr:file:border-0 wr:file:me-4 wr:file:py-3 wr:file:px-4 wr:dark:file:bg-neutral-700 wr:dark:file:text-neutral-400",
|
||||
p.prefixText && "wr:rounded-l-none",
|
||||
p.suffixText && "wr:rounded-r-none",
|
||||
p.error &&
|
||||
"border-danger focus-visible:ring-danger/40",
|
||||
"wr:border-danger wr:focus-visible:ring-danger/40",
|
||||
)}
|
||||
data-control
|
||||
multiple
|
||||
@@ -238,14 +246,16 @@ const controlWrap = "relative";
|
||||
/>
|
||||
|
||||
{p.iconRight && (
|
||||
<span class="absolute inset-y-0 right-0 pr-3 flex items-center pointer-events-none text-muted-foreground">
|
||||
<span class="wr:absolute wr:inset-y-0 wr:right-0 wr:pr-3 wr:flex wr:items-center wr:pointer-events-none wr:text-muted-foreground">
|
||||
<Icon name={p.iconRight} class={iconSize} />
|
||||
</span>
|
||||
)}
|
||||
</div>
|
||||
|
||||
{p.suffixText && (
|
||||
<span class={cn(addonBase, "border-l-0 rounded-l-none")}>
|
||||
<span
|
||||
class={cn(addonBase, "wr:border-l-0 wr:rounded-l-none")}
|
||||
>
|
||||
{p.suffixText}
|
||||
</span>
|
||||
)}
|
||||
@@ -271,13 +281,14 @@ const controlWrap = "relative";
|
||||
.join(" ") || undefined
|
||||
}
|
||||
class={cn(
|
||||
"py-2.5 sm:py-3 px-4 block w-full border-gray-200 rounded-lg sm:text-sm focus:border-blue-500 focus:ring-blue-500 disabled:opacity-50 disabled:pointer-events-none dark:bg-neutral-900 dark:border-neutral-700 dark:text-neutral-400 dark:placeholder-neutral-500 dark:focus:ring-neutral-600",
|
||||
"wr:py-2.5 wr:sm:py-3 wr:px-4 wr:block wr:w-full wr:border-gray-200 wr:rounded-lg wr:sm:text-sm wr:focus:border-blue-500 wr:focus:ring-blue-500 wr:disabled:opacity-50 wr:disabled:pointer-events-none wr:dark:bg-neutral-900 wr:dark:border-neutral-700 wr:dark:text-neutral-400 wr:dark:placeholder-neutral-500 wr:dark:focus:ring-neutral-600",
|
||||
p.size === "sm"
|
||||
? "text-sm p-3"
|
||||
? "wr:text-sm wr:p-3"
|
||||
: p.size === "lg"
|
||||
? "text-base p-4"
|
||||
: "text-sm p-3",
|
||||
p.error && "border-danger focus-visible:ring-danger/40",
|
||||
? "wr:text-base wr:p-4"
|
||||
: "wr:text-sm wr:p-3",
|
||||
p.error &&
|
||||
"wr:border-danger wr:focus-visible:ring-danger/40",
|
||||
)}
|
||||
data-initial={typeof p.value === "string" ? p.value : ""}
|
||||
/>
|
||||
@@ -303,8 +314,9 @@ const controlWrap = "relative";
|
||||
}
|
||||
class={cn(
|
||||
selectBase({ size: p.size ?? "md" }),
|
||||
"appearance-none bg-none pr-9",
|
||||
p.error && "border-danger focus-visible:ring-danger/40",
|
||||
"wr:appearance-none wr:bg-none wr:pr-9",
|
||||
p.error &&
|
||||
"wr:border-danger wr:focus-visible:ring-danger/40",
|
||||
)}
|
||||
>
|
||||
{!p.multiple && p.placeholder && (
|
||||
@@ -326,7 +338,7 @@ const controlWrap = "relative";
|
||||
</option>
|
||||
))}
|
||||
</select>
|
||||
<span class="pointer-events-none absolute inset-y-0 right-0 pr-3 flex items-center text-muted-foreground">
|
||||
<span class="wr:pointer-events-none wr:absolute wr:inset-y-0 wr:right-0 wr:pr-3 wr:flex wr:items-center wr:text-muted-foreground">
|
||||
<Icon name="mdi:chevron-down" class={iconSize} />
|
||||
</span>
|
||||
</div>
|
||||
@@ -335,12 +347,12 @@ const controlWrap = "relative";
|
||||
|
||||
{
|
||||
p.kind === "checkbox" && (
|
||||
<label class="flex items-center gap-3">
|
||||
<label class="wr:flex wr:items-center wr:gap-3">
|
||||
<input
|
||||
id={fieldId}
|
||||
name={p.name}
|
||||
type="checkbox"
|
||||
class="shrink-0 mt-0.5 border-gray-200 rounded-sm text-blue-600 focus:ring-blue-500 checked:border-blue-500 disabled:opacity-50 disabled:pointer-events-none dark:bg-neutral-800 dark:border-neutral-700 dark:checked:bg-blue-500 dark:checked:border-blue-500 dark:focus:ring-offset-gray-800"
|
||||
class="wr:shrink-0 wr:mt-0.5 wr:border-gray-200 wr:rounded-sm wr:text-blue-600 wr:focus:ring-blue-500 wr:checked:border-blue-500 wr:disabled:opacity-50 wr:disabled:pointer-events-none wr:dark:bg-neutral-800 wr:dark:border-neutral-700 wr:dark:checked:bg-blue-500 wr:dark:checked:border-blue-500 wr:dark:focus:ring-offset-gray-800"
|
||||
checked={!!p.value}
|
||||
disabled={p.disabled}
|
||||
data-control
|
||||
@@ -353,7 +365,9 @@ const controlWrap = "relative";
|
||||
/>
|
||||
<div>
|
||||
{p.label && (
|
||||
<span class="text-sm text-foreground">{p.label}</span>
|
||||
<span class="wr:text-sm wr:text-foreground">
|
||||
{p.label}
|
||||
</span>
|
||||
)}
|
||||
{p.description && (
|
||||
<p id={descId} class={helpCls}>
|
||||
@@ -367,25 +381,25 @@ const controlWrap = "relative";
|
||||
|
||||
{
|
||||
p.kind === "radio" && (
|
||||
<fieldset class="space-y-2">
|
||||
<fieldset class="wr:space-y-2">
|
||||
{p.label && (
|
||||
<legend class="text-sm font-medium text-foreground">
|
||||
<legend class="wr:text-sm wr:font-medium wr:text-foreground">
|
||||
{p.label}
|
||||
</legend>
|
||||
)}
|
||||
<div class="space-x-3">
|
||||
<div class="wr:space-x-3">
|
||||
{(p.options ?? []).map((opt) => (
|
||||
<label class="inline-flex items-center gap-2">
|
||||
<label class="wr:inline-flex wr:items-center wr:gap-2">
|
||||
<input
|
||||
type="radio"
|
||||
name={p.name}
|
||||
value={opt.value}
|
||||
checked={String(p.value) === opt.value}
|
||||
class="shrink-0 mt-0.5 border-gray-200 rounded-full text-blue-600 focus:ring-blue-500 checked:border-blue-500 disabled:opacity-50 disabled:pointer-events-none dark:bg-neutral-800 dark:border-neutral-700 dark:checked:bg-blue-500 dark:checked:border-blue-500 dark:focus:ring-offset-gray-800"
|
||||
class="wr:shrink-0 wr:mt-0.5 wr:border-gray-200 wr:rounded-full wr:text-blue-600 wr:focus:ring-blue-500 wr:checked:border-blue-500 wr:disabled:opacity-50 wr:disabled:pointer-events-none wr:dark:bg-neutral-800 wr:dark:border-neutral-700 wr:dark:checked:bg-blue-500 wr:dark:checked:border-blue-500 wr:dark:focus:ring-offset-gray-800"
|
||||
disabled={opt.disabled || p.disabled}
|
||||
data-control
|
||||
/>
|
||||
<span class="text-sm text-foreground">
|
||||
<span class="wr:text-sm wr:text-foreground">
|
||||
{opt.label}
|
||||
</span>
|
||||
</label>
|
||||
@@ -397,24 +411,24 @@ const controlWrap = "relative";
|
||||
|
||||
{
|
||||
p.kind === "switch" && (
|
||||
<div class="flex items-center gap-3">
|
||||
<label class="relative inline-block w-11 h-6 cursor-pointer">
|
||||
<div class="wr:flex wr:items-center wr:gap-3">
|
||||
<label class="wr:relative wr:inline-block wr:w-11 wr:h-6 wr:cursor-pointer">
|
||||
<input
|
||||
id={fieldId}
|
||||
name={p.name}
|
||||
type="checkbox"
|
||||
class="sr-only peer"
|
||||
class="wr:sr-only wr:peer"
|
||||
checked={!!p.value}
|
||||
disabled={p.disabled}
|
||||
data-control
|
||||
/>
|
||||
<span class="absolute inset-0 bg-gray-200 rounded-full transition-colors duration-200 ease-in-out peer-checked:bg-blue-600 dark:bg-neutral-700 dark:peer-checked:bg-blue-500 peer-disabled:opacity-50 peer-disabled:pointer-events-none" />
|
||||
<span class="absolute top-1/2 start-0.5 -translate-y-1/2 size-5 bg-white rounded-full shadow-xs transition-transform duration-200 ease-in-out peer-checked:translate-x-full dark:bg-neutral-400 dark:peer-checked:bg-white" />
|
||||
<span class="wr:absolute wr:inset-0 wr:bg-gray-200 wr:rounded-full wr:transition-colors wr:duration-200 wr:ease-in-out wr:peer-checked:bg-blue-600 wr:dark:bg-neutral-700 wr:dark:peer-checked:bg-blue-500 wr:peer-disabled:opacity-50 wr:peer-disabled:pointer-events-none" />
|
||||
<span class="wr:absolute wr:top-1/2 wr:start-0.5 wr:-translate-y-1/2 wr:size-5 wr:bg-white wr:rounded-full wr:shadow-xs wr:transition-transform wr:duration-200 wr:ease-in-out wr:peer-checked:translate-x-full wr:dark:bg-neutral-400 wr:dark:peer-checked:bg-white" />
|
||||
</label>
|
||||
{p.label && (
|
||||
<label
|
||||
for={fieldId}
|
||||
class="text-sm text-gray-500 dark:text-neutral-400"
|
||||
class="wr:text-sm wr:text-gray-500 wr:dark:text-neutral-400"
|
||||
>
|
||||
{p.label}
|
||||
</label>
|
||||
@@ -431,6 +445,5 @@ const controlWrap = "relative";
|
||||
)
|
||||
}
|
||||
|
||||
<!-- Always-present error container (client fills it) -->
|
||||
<p id={errId} class={errCls} hidden>{p.error ?? ""}</p>
|
||||
</div>
|
||||
|
||||
Reference in New Issue
Block a user