Files
tabler/shared/ui/ListGroupItem.astro
T

63 lines
2.2 KiB
Plaintext

---
import type { HTMLTag } from 'astro/types'
// List group item (.list-group-item). With a title, a description or a named
// slot it renders the slot layout: media, content, meta and actions in a row.
type PolymorphicProps = { as?: HTMLTag }
interface Props extends PolymorphicProps {
/** list-group-item-action (hover/focus affordance, typically for a/button items) */
action?: boolean
active?: boolean
disabled?: boolean
/** first line of the content slot (.list-group-item-title) */
title?: string | undefined
/** second line of the content slot (.list-group-item-description) */
description?: string | undefined
/** keeps the actions slot visible in a hoverable list (.show) */
showActions?: boolean
class?: string
/** remaining attributes (href, data-*, …) are forwarded to the element */
[key: string]: unknown
}
const { as: Element = 'div', action, active, disabled, title, description, showActions, class: className, ...rest }: Props = Astro.props
const hasMedia = Astro.slots.has('media')
const hasMeta = Astro.slots.has('meta')
const hasActions = Astro.slots.has('actions')
const hasSlots = Boolean(title || description || hasMedia || hasMeta || hasActions)
---
<Element class:list={['list-group-item', action && 'list-group-item-action', active && 'active', disabled && 'disabled', className]} aria-disabled={disabled ? 'true' : undefined} tabindex={Element === 'a' && disabled ? -1 : undefined} {...rest}>
{
hasSlots ? (
<>
{hasMedia && (
<div class="list-group-item-media">
<slot name="media" />
</div>
)}
<div class="list-group-item-content">
{title && <div class="list-group-item-title">{title}</div>}
{description && <div class="list-group-item-description">{description}</div>}
<slot />
</div>
{hasMeta && (
<div class="list-group-item-meta">
<slot name="meta" />
</div>
)}
{hasActions && (
<div class:list={['list-group-item-actions', showActions && 'show']}>
<slot name="actions" />
</div>
)}
</>
) : (
<slot />
)
}
</Element>