91 lines
4.1 KiB
Plaintext
91 lines
4.1 KiB
Plaintext
component Tabs {
|
|
props {
|
|
size: string = "default"
|
|
color: string = "primary"
|
|
label: string = "Tabs"
|
|
items: unknown[] = []
|
|
active: string = ""
|
|
orientation: string = "horizontal"
|
|
class: string = ""
|
|
}
|
|
|
|
state activeValue = active || (items[0] ? (items[0].value || items[0].id || "0") : "")
|
|
|
|
view {
|
|
<section
|
|
data-ui-component="Tabs"
|
|
class='w-full {class}'
|
|
class:flex='orientation === "vertical"'
|
|
class:items-start='orientation === "vertical"'
|
|
class:gap-6='orientation === "vertical"'
|
|
>
|
|
<div
|
|
role="tablist"
|
|
aria-label='{label}'
|
|
aria-orientation='{orientation}'
|
|
class="flex min-w-0 gap-1 overflow-x-auto rounded-xl border border-[var(--wire-color-border)] bg-[var(--wire-color-surface-soft)] p-1"
|
|
class:flex-col='orientation === "vertical"'
|
|
class:w-56='orientation === "vertical"'
|
|
class:shrink-0='orientation === "vertical"'
|
|
>
|
|
{#each items as item, index}
|
|
<button
|
|
type="button"
|
|
role="tab"
|
|
id='tab-{item.value || item.id || index}'
|
|
aria-selected='{activeValue === (item.value || item.id || String(index))}'
|
|
aria-controls='panel-{item.value || item.id || index}'
|
|
tabindex='{activeValue === (item.value || item.id || String(index)) ? "0" : "-1"}'
|
|
disabled='{item.disabled || false}'
|
|
class="inline-flex min-w-max flex-1 items-center justify-center gap-2 rounded-lg px-4 py-2.5 text-sm font-semibold outline-none transition disabled:cursor-not-allowed disabled:opacity-50"
|
|
class:bg-[var(--wire-color-surface-raised)]='activeValue === (item.value || item.id || String(index))'
|
|
class:text-[var(--wire-color-primary)]='activeValue === (item.value || item.id || String(index))'
|
|
class:shadow-sm='activeValue === (item.value || item.id || String(index))'
|
|
class:text-[var(--wire-color-text-muted)]='activeValue !== (item.value || item.id || String(index))'
|
|
class:hover:text-[var(--wire-color-text)]='activeValue !== (item.value || item.id || String(index))'
|
|
class:justify-start='orientation === "vertical"'
|
|
class:px-3='size === "sm"'
|
|
class:py-2='size === "sm"'
|
|
class:px-5='size === "lg"'
|
|
class:py-3='size === "lg"'
|
|
@click='activeValue = item.value || item.id || String(index); event.currentTarget.dispatchEvent(new CustomEvent("change", { bubbles: true, detail: { item: item, index: index, value: activeValue } })); event.currentTarget.dispatchEvent(new CustomEvent("select", { bubbles: true, detail: { item: item, index: index, value: activeValue } }))'
|
|
>
|
|
{#if item.icon}
|
|
<span class='{item.icon + " size-4"}' aria-hidden="true"></span>
|
|
{/if}
|
|
<span>{item.label || item.title}</span>
|
|
{#if item.badge}
|
|
<span class="rounded-full bg-[var(--wire-color-primary-soft)] px-2 py-0.5 text-xs text-[var(--wire-color-primary)]">{item.badge}</span>
|
|
{/if}
|
|
</button>
|
|
{/each}
|
|
</div>
|
|
|
|
<div class="min-w-0 flex-1 pt-4" class:pt-0='orientation === "vertical"'>
|
|
{#each items as item, index}
|
|
<div
|
|
role="tabpanel"
|
|
id='panel-{item.value || item.id || index}'
|
|
aria-labelledby='tab-{item.value || item.id || index}'
|
|
tabindex="0"
|
|
data-show='activeValue === (item.value || item.id || String(index))'
|
|
class="rounded-xl outline-none focus-visible:ring-2 focus-visible:ring-[var(--wire-color-focus)]"
|
|
>
|
|
{#if item.title && item.title !== item.label}
|
|
<h3 class="text-lg font-bold text-[var(--wire-color-text)]">{item.title}</h3>
|
|
{/if}
|
|
{#if item.description}
|
|
<p class="mt-2 leading-7 text-[var(--wire-color-text-muted)]">{item.description}</p>
|
|
{/if}
|
|
{#if item.content}
|
|
<div class="mt-4 text-[var(--wire-color-text)]">{item.content}</div>
|
|
{/if}
|
|
</div>
|
|
{/each}
|
|
|
|
<slot></slot>
|
|
</div>
|
|
</section>
|
|
}
|
|
}
|