Getting ready to clean up the package and release 0.2.0

This commit is contained in:
Ronan Berder
2025-06-16 17:58:01 +08:00
parent f51a03da79
commit 17a18c1871
34 changed files with 789 additions and 707 deletions
+11 -10
View File
@@ -59,6 +59,7 @@
<link rel="stylesheet" href="/assets/styles.css">
{# JS #}
<script src="/assets/js/dropdown-menu.js" defer></script>
<script src="/assets/js/popover.js" defer></script>
<script src="/assets/js/select.js" defer></script>
<script src="/assets/js/sidebar.js" defer></script>
<script src="/assets/js/tabs.js" defer></script>
@@ -71,17 +72,17 @@
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/highlight.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/django.min.js"></script>
<script>
const applyHighlighting = () => { if (window.hljs) {
hljs.highlightAll();
document.querySelectorAll('code.highlight').forEach((block) => {
hljs.highlightElement(block);
});
}};
const highlight = () => {
if (!window.hljs) return;
document
.querySelectorAll('code:not([data-highlighted])')
.forEach(el => hljs.highlightElement(el));
};
if (!window._hljsInitialized) {
window._hljsInitialized = true;
document.addEventListener('DOMContentLoaded', applyHighlighting);
document.addEventListener('htmx:afterSwap', applyHighlighting);
if (!window._hljsInit) {
window._hljsInit = true;
document.addEventListener('DOMContentLoaded', highlight);
document.addEventListener('htmx:afterSwap', highlight);
}
</script>
{% if head %}{{ head | safe }}{% endif %}
+1 -2
View File
@@ -20,8 +20,7 @@
{{ tabs(
tabsets=tabsets,
default_tab_index=(2 if default_code else 1),
register_on=["alpine:init", "htmx:afterSwap"]
default_tab_index=(2 if default_code else 1)
) }}
</div>
{% endmacro %}
@@ -11,7 +11,7 @@
<div class="flex flex-wrap items-start gap-4">
{% set options_frameworks = ["Next.js", "SvelteKit", "Nuxt.js", "Remix", "Astro"] %}
{% call select(
content_attrs={"class": "w-48"},
popover_attrs={"class": "w-48"},
listbox_attrs={"data-empty": "No framework found."},
is_combobox=true
) %}
@@ -56,7 +56,7 @@
}
] %}
{% call select(
content_attrs={"class": "w-72"},
popover_attrs={"class": "w-72"},
listbox_attrs={"data-empty": "No timezone found."},
is_combobox=true
) %}
@@ -17,10 +17,9 @@
id="demo-dialog-edit-profile",
title="Edit profile",
description="Make changes to your profile here. Click save when you're done.",
main_attrs={"x-ref": "myDialog"},
trigger="Edit Profile",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
dialog_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
footer=footer
) %}
<form class="form grid gap-4">
@@ -36,17 +35,16 @@
{% endcall %}
{% set footer %}
<button class="btn-outline" @click="open = false">Close</button>
<button class="btn-outline" onclick="this.closest('dialog').close()">Close</button>
{% endset %}
{% call dialog(
id="dialog-example",
title="Scrollable Content",
description="This is a dialog with scrollable content.",
main_attrs={"x-ref": "myDialog"},
trigger="Scrollable Content",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
content_body_attrs={"class": "overflow-y-auto scrollbar"},
dialog_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
body_attrs={"class": "overflow-y-auto scrollbar"},
footer=footer
) %}
<div class="space-y-4 text-sm">
@@ -62,15 +60,6 @@
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
</div>
{% endcall %}
<button
x-init
@click="$dispatch('dialog:open', { id: 'dialog-example' })"
type="button"
class="btn-outline"
>
Trigger dialog:open
</button>
</div>
</div>
</section>
@@ -13,68 +13,66 @@
id="dropdown-menu-default",
trigger="Open",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "min-w-56"}
popover_attrs={"class": "min-w-56"}
) %}
<div role="group" aria-labelledby="account-options">
<span id="account-options" role="heading">My Account</span>
<button type="button" role="menuitem">
<div role="presentation" id="account-options">My Account</div>
<div role="menuitem">
Profile
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Billing
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Settings
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Keyboard shortcuts
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘K</span>
</button>
</div>
</div>
<hr role="separator">
<button type="button" role="menuitem">GitHub</button>
<button type="button" role="menuitem">Support</button>
<button type="button" role="menuitem" disabled>API</button>
<div role="menuitem">GitHub</div>
<div role="menuitem">Support</div>
<div role="menuitem" disabled>API</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
Logout
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
</div>
{% endcall %}
{% call dropdown_menu(
id="dropdown-menu-checkboxes",
trigger="Checkboxes",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "min-w-56"},
register_on=["alpine:init", "htmx:afterSwap"]
popover_attrs={"class": "min-w-56"}
) %}
<div role="group" aria-labelledby="account-options">
<span id="account-options" role="heading">Account Options</span>
<button type="button" role="menuitem">
<div role="presentation" id="account-options">Account Options</div>
<div role="menuitem">
{% lucide "user" %}
Profile
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
{% lucide "credit-card" %}
Billing
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
{% lucide "settings" %}
Settings
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
</div>
</div>
<hr role="separator">
<div role="group" aria-labelledby="appearance-options">
<span id="appearance-options" role="heading">Appearance</span>
<button
type="button"
<div role="presentation" id="appearance-options">Appearance</div>
<div
role="menuitemcheckbox"
aria-checked="true"
class="group"
@@ -89,9 +87,8 @@
} %}
Status Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button
type="button"
</div>
<div
role="menuitemcheckbox"
aria-checked="false"
class="group"
@@ -107,9 +104,8 @@
} %}
Activity Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button
type="button"
</div>
<div
role="menuitemcheckbox"
aria-checked="false"
class="group"
@@ -124,14 +120,14 @@
} %}
Panel
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
</div>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
{% lucide "log-out" %}
Logout
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
</div>
{% endcall %}
{% set profile_menu %}
@@ -143,41 +139,39 @@
</div>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
{% lucide "star" %}
Upgrade to Pro
</button>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
{% lucide "user" %}
Account
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
{% lucide "credit-card" %}
Billing
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
{% lucide "bell" %}
Notifications
</button>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
{% lucide "log-out" %}
Signout
</button>
</div>
{% endset %}
{% call dropdown_menu(
trigger="Radio Group",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "min-w-56"},
register_on=["alpine:init", "htmx:afterSwap"]
popover_attrs={"class": "min-w-56"}
) %}
<div role="group" aria-labelledby="position-options" x-data="{ checked: 'bottom' }">
<span id="position-options" role="heading">Panel Position</span>
<hr role="separator">
<button
type="button"
<div
role="menuitemradio"
aria-checked="false"
class="group"
@@ -193,9 +187,8 @@
</div>
Status Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button
type="button"
</div>
<div
role="menuitemradio"
aria-checked="false"
class="group"
@@ -211,9 +204,8 @@
</div>
Activity Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button
type="button"
</div>
<div
role="menuitemradio"
aria-checked="false"
class="group"
@@ -229,7 +221,7 @@
</div>
Panel
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
</div>
</div>
{% endcall %}
@@ -256,7 +248,7 @@
id="dropdown-checkboxes",
trigger=trigger,
trigger_attrs={"class": "btn-icon-ghost rounded-full size-8"},
content_attrs={"data-align": "end"}
popover_attrs={"data-align": "end"}
) %}
{{ profile_menu | safe }}
{% endcall %}
@@ -268,21 +260,21 @@
id="dropdown-checkboxes",
trigger=trigger,
trigger_attrs={"class": "btn-icon-ghost"},
content_attrs={"class": "min-w-32"}
popover_attrs={"class": "min-w-32"}
) %}
<button type="button" role="menuitem">
<div role="menuitem">
{% lucide "pencil" %}
Edit
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
{% lucide "share" %}
Share
</button>
</div>
<hr role="separator">
<button type="button" role="menuitem" class="text-destructive hover:bg-destructive/10 dark:hover:bg-destructive/20 focus:bg-destructive/10 dark:focus:bg-destructive/20 focus:text-destructive [&_svg]:!text-destructive">
<div role="menuitem" class="text-destructive hover:bg-destructive/10 dark:hover:bg-destructive/20 focus:bg-destructive/10 dark:focus:bg-destructive/20 focus:text-destructive [&_svg]:!text-destructive">
{% lucide "trash-2" %}
Delete
</button>
</div>
{% endcall %}
</div>
</div>
@@ -38,7 +38,7 @@
items: [
{ type: "item", label: "Apple", value: "apple" },
{ type: "item", label: "Banana", value: "banana" },
{ type: "item", label: "Blueberry Blueberry Blueberry Blueberry Blueberry", value: "blueberry" }
{ type: "item", label: "Blueberry", value: "blueberry" }
]
},
{
+1 -1
View File
@@ -29,7 +29,7 @@
"
}
) %}
<div class="grid gap-4 p-4">
<div class="grid gap-4">
<header class="grid gap-1.5">
<h2 class="font-semibold">I hope you like Basecoat...</h2>
<p class="text-muted-foreground text-sm">My name is <a href="https://ronanberder.com" target="_blank">Ronan</a> and I made this (and <a class="underline underline-offset-4" href="https://pagescms.org" target="_target">other things</a>). If you find it useful, please consider sponsoring me on GitHub or following me on X.</p>
+151 -74
View File
@@ -5,6 +5,7 @@
:root, :host {
--font-sans: ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji",
"Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji";
--font-serif: ui-serif, Georgia, Cambria, "Times New Roman", Times, serif;
--font-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono",
"Courier New", monospace;
--color-amber-50: oklch(98.7% 0.022 95.277);
@@ -63,6 +64,13 @@
--radius-md: calc(var(--radius) - 2px);
--radius-lg: var(--radius);
--radius-xl: calc(var(--radius) + 4px);
--shadow-2xs: 0 1px rgb(0 0 0 / 0.05);
--shadow-xs: 0 1px 2px 0 rgb(0 0 0 / 0.05);
--shadow-sm: 0 1px 3px 0 rgb(0 0 0 / 0.1), 0 1px 2px -1px rgb(0 0 0 / 0.1);
--shadow-md: 0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1);
--shadow-lg: 0 10px 15px -3px rgb(0 0 0 / 0.1), 0 4px 6px -4px rgb(0 0 0 / 0.1);
--shadow-xl: 0 20px 25px -5px rgb(0 0 0 / 0.1), 0 8px 10px -6px rgb(0 0 0 / 0.1);
--shadow-2xl: 0 25px 50px -12px rgb(0 0 0 / 0.25);
--ease-in-out: cubic-bezier(0.4, 0, 0.2, 1);
--animate-spin: spin 1s linear infinite;
--animate-pulse: pulse 2s cubic-bezier(0.4, 0, 0.6, 1) infinite;
@@ -245,6 +253,9 @@
}
}
@layer utilities {
.\@container {
container-type: inline-size;
}
.pointer-events-none {
pointer-events: none;
}
@@ -280,6 +291,9 @@
.top-0 {
top: calc(var(--spacing) * 0);
}
.top-1 {
top: calc(var(--spacing) * 1);
}
.top-1\/2 {
top: calc(1/2 * 100%);
}
@@ -289,9 +303,15 @@
.top-22 {
top: calc(var(--spacing) * 22);
}
.right-2 {
right: calc(var(--spacing) * 2);
}
.right-2\.5 {
right: calc(var(--spacing) * 2.5);
}
.left-1 {
left: calc(var(--spacing) * 1);
}
.left-1\/2 {
left: calc(1/2 * 100%);
}
@@ -355,6 +375,9 @@
.mb-12 {
margin-bottom: calc(var(--spacing) * 12);
}
.-ml-1 {
margin-left: calc(var(--spacing) * -1);
}
.-ml-1\.5 {
margin-left: calc(var(--spacing) * -1.5);
}
@@ -376,9 +399,6 @@
.hidden {
display: none;
}
.inline {
display: inline;
}
.inline-block {
display: inline-block;
}
@@ -402,6 +422,10 @@
width: calc(var(--spacing) * 2.5);
height: calc(var(--spacing) * 2.5);
}
.size-3 {
width: calc(var(--spacing) * 3);
height: calc(var(--spacing) * 3);
}
.size-3\.5 {
width: calc(var(--spacing) * 3.5);
height: calc(var(--spacing) * 3.5);
@@ -466,9 +490,15 @@
.min-h-\[350px\] {
min-height: 350px;
}
.w-1 {
width: calc(var(--spacing) * 1);
}
.w-1\/2 {
width: calc(1/2 * 100%);
}
.w-2 {
width: calc(var(--spacing) * 2);
}
.w-2\/3 {
width: calc(2/3 * 100%);
}
@@ -550,21 +580,42 @@
.flex-1 {
flex: 1;
}
.flex-shrink {
flex-shrink: 1;
}
.shrink-0 {
flex-shrink: 0;
}
.border-collapse {
border-collapse: collapse;
}
.-translate-x-1 {
--tw-translate-x: calc(var(--spacing) * -1);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
.-translate-x-1\/2 {
--tw-translate-x: calc(calc(1/2 * 100%) * -1);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
.-translate-y-1 {
--tw-translate-y: calc(var(--spacing) * -1);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
.-translate-y-1\/2 {
--tw-translate-y: calc(calc(1/2 * 100%) * -1);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
.translate-y-0 {
--tw-translate-y: calc(var(--spacing) * 0);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
.translate-y-0\.5 {
--tw-translate-y: calc(var(--spacing) * 0.5);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
.transform {
transform: var(--tw-rotate-x,) var(--tw-rotate-y,) var(--tw-rotate-z,) var(--tw-skew-x,) var(--tw-skew-y,);
}
.animate-pulse {
animation: var(--animate-pulse);
}
@@ -574,6 +625,9 @@
.cursor-pointer {
cursor: pointer;
}
.resize {
resize: both;
}
.scroll-m-20 {
scroll-margin: calc(var(--spacing) * 20);
}
@@ -619,6 +673,9 @@
.justify-start {
justify-content: flex-start;
}
.gap-0 {
gap: calc(var(--spacing) * 0);
}
.gap-0\.5 {
gap: calc(var(--spacing) * 0.5);
}
@@ -674,6 +731,9 @@
margin-block-end: calc(calc(var(--spacing) * 6) * calc(1 - var(--tw-space-y-reverse)));
}
}
.gap-x-1 {
column-gap: calc(var(--spacing) * 1);
}
.gap-x-1\.5 {
column-gap: calc(var(--spacing) * 1.5);
}
@@ -763,6 +823,9 @@
.border-amber-50 {
border-color: var(--color-amber-50);
}
.border-border {
border-color: var(--color-border);
}
.border-border\/50 {
border-color: var(--color-border);
@supports (color: color-mix(in lab, red, red)) {
@@ -799,6 +862,9 @@
.bg-sidebar-primary {
background-color: var(--color-sidebar-primary);
}
.mask-repeat {
mask-repeat: repeat;
}
.object-cover {
object-fit: cover;
}
@@ -841,6 +907,9 @@
.px-\[0\.3rem\] {
padding-inline: 0.3rem;
}
.py-1 {
padding-block: calc(var(--spacing) * 1);
}
.py-1\.5 {
padding-block: calc(var(--spacing) * 1.5);
}
@@ -2534,7 +2603,10 @@
}
@layer components {
.dropdown-menu {
[popover].popover {
position: relative;
display: inline-flex;
padding: calc(var(--spacing) * 1);
[data-popover] {
padding: calc(var(--spacing) * 1);
min-width: anchor-size(width);
[role='menuitem'], [role='menuitemcheckbox'], [role='menuitemradio'] {
@@ -2606,7 +2678,7 @@
color: var(--color-accent-foreground);
}
}
[role='menu'] [role='heading'] {
[role='menu'] [role="presentation"] {
display: flex;
padding-inline: calc(var(--spacing) * 2);
padding-block: calc(var(--spacing) * 1.5);
@@ -2762,15 +2834,15 @@
}
}
@layer components {
[popover].popover {
[data-popover] {
visibility: visible;
position: absolute;
inset: auto;
z-index: 50;
width: max-content;
--tw-scale-x: 95%;
--tw-scale-y: 95%;
--tw-scale-z: 95%;
min-width: 100%;
--tw-scale-x: 100%;
--tw-scale-y: 100%;
--tw-scale-z: 100%;
scale: var(--tw-scale-x) var(--tw-scale-y);
overflow-x: hidden;
overflow-y: auto;
@@ -2778,106 +2850,85 @@
border-style: var(--tw-border-style);
border-width: 1px;
background-color: var(--color-popover);
padding: calc(var(--spacing) * 4);
color: var(--color-popover-foreground);
opacity: 0%;
opacity: 100%;
--tw-shadow: 0 4px 6px -1px var(--tw-shadow-color, rgb(0 0 0 / 0.1)), 0 2px 4px -2px var(--tw-shadow-color, rgb(0 0 0 / 0.1));
box-shadow: var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow);
transition-property: all;
transition-timing-function: var(--tw-ease, var(--default-transition-timing-function));
transition-duration: var(--tw-duration, var(--default-transition-duration));
transition-behavior: allow-discrete;
&:not([data-side]), &[data-side='bottom'] {
--tw-translate-y: calc(var(--spacing) * -2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='top'] {
--tw-translate-y: calc(var(--spacing) * 2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='left'] {
--tw-translate-x: calc(var(--spacing) * 2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='right'] {
--tw-translate-x: calc(var(--spacing) * -2);
translate: var(--tw-translate-x) var(--tw-translate-y);
&[aria-hidden='true'] {
visibility: hidden;
--tw-scale-x: 95%;
--tw-scale-y: 95%;
--tw-scale-z: 95%;
scale: var(--tw-scale-x) var(--tw-scale-y);
opacity: 0%;
&:not([data-side]), &[data-side='bottom'] {
--tw-translate-y: calc(var(--spacing) * -2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='top'] {
--tw-translate-y: calc(var(--spacing) * 2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='left'] {
--tw-translate-x: calc(var(--spacing) * 2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='right'] {
--tw-translate-x: calc(var(--spacing) * -2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
}
&:not([data-side]), &[data-side='bottom'] {
top: anchor(bottom);
top: 100%;
margin-top: calc(var(--spacing) * 1);
}
&[data-side='top'] {
bottom: anchor(top);
bottom: 100%;
margin-bottom: calc(var(--spacing) * 1);
}
&[data-side='left'] {
right: anchor(left);
right: 100%;
margin-right: calc(var(--spacing) * 1);
}
&[data-side='right'] {
left: anchor(right);
left: 100%;
margin-left: calc(var(--spacing) * 1);
}
&:not([data-side]), &[data-side='bottom'], &[data-side='top'] {
&:not([data-align]), &[data-align='start'] {
left: anchor(left);
left: calc(var(--spacing) * 0);
}
&[data-align='end'] {
right: anchor(right);
right: calc(var(--spacing) * 0);
}
&[data-align='center'] {
left: anchor(center);
left: calc(1/2 * 100%);
--tw-translate-x: calc(calc(1/2 * 100%) * -1);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
}
&[data-side='left'], &[data-side='right'] {
&:not([data-align]), &[data-align='start'] {
top: anchor(top);
top: calc(var(--spacing) * 0);
}
&[data-align='end'] {
bottom: anchor(bottom);
bottom: calc(var(--spacing) * 0);
}
&[data-align='center'] {
top: anchor(center);
top: calc(1/2 * 100%);
--tw-translate-y: calc(calc(1/2 * 100%) * -1);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
}
&:is(:popover-open) {
--tw-translate-x: calc(var(--spacing) * 0);
translate: var(--tw-translate-x) var(--tw-translate-y);
--tw-translate-y: calc(var(--spacing) * 0);
translate: var(--tw-translate-x) var(--tw-translate-y);
--tw-scale-x: 100%;
--tw-scale-y: 100%;
--tw-scale-z: 100%;
scale: var(--tw-scale-x) var(--tw-scale-y);
opacity: 100%;
@starting-style {
--tw-scale-x: 95%;
--tw-scale-y: 95%;
--tw-scale-z: 95%;
scale: var(--tw-scale-x) var(--tw-scale-y);
opacity: 0%;
&:not([data-side]), &[data-side='bottom'] {
--tw-translate-y: calc(var(--spacing) * -2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='top'] {
--tw-translate-y: calc(var(--spacing) * 2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='left'] {
--tw-translate-x: calc(var(--spacing) * 2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
&[data-side='right'] {
--tw-translate-x: calc(var(--spacing) * -2);
translate: var(--tw-translate-x) var(--tw-translate-y);
}
}
}
.popover {
position: relative;
display: inline-flex;
[data-popover] {
padding: calc(var(--spacing) * 4);
}
}
}
@@ -3159,8 +3210,9 @@
}
}
*:not(select).select {
[popover].popover {
min-width: anchor-size(width);
position: relative;
display: inline-flex;
[data-popover] {
padding: calc(var(--spacing) * 1);
[role='option'] {
position: relative;
@@ -3218,7 +3270,7 @@
background-repeat: no-repeat;
}
}
[role='listbox'] [role='heading'] {
[role='listbox'] [role="presentation"] {
display: flex;
padding-inline: calc(var(--spacing) * 2);
padding-block: calc(var(--spacing) * 1.5);
@@ -4886,6 +4938,26 @@ code.hljs {
inherits: false;
initial-value: 0;
}
@property --tw-rotate-x {
syntax: "*";
inherits: false;
}
@property --tw-rotate-y {
syntax: "*";
inherits: false;
}
@property --tw-rotate-z {
syntax: "*";
inherits: false;
}
@property --tw-skew-x {
syntax: "*";
inherits: false;
}
@property --tw-skew-y {
syntax: "*";
inherits: false;
}
@property --tw-space-y-reverse {
syntax: "*";
inherits: false;
@@ -5100,6 +5172,11 @@ code.hljs {
--tw-translate-x: 0;
--tw-translate-y: 0;
--tw-translate-z: 0;
--tw-rotate-x: initial;
--tw-rotate-y: initial;
--tw-rotate-z: initial;
--tw-skew-x: initial;
--tw-skew-y: initial;
--tw-space-y-reverse: 0;
--tw-space-x-reverse: 0;
--tw-border-style: solid;
+1 -2
View File
@@ -29,8 +29,7 @@ toc:
{% call dropdown_menu(
id="demo-breadcrumb-menu",
trigger=trigger,
trigger_attrs={"class": "flex size-9 items-center justify-center h-4 w-4 hover:text-foreground cursor-pointer"},
register_on=["alpine:init", "htmx:afterSwap"]
trigger_attrs={"class": "flex size-9 items-center justify-center h-4 w-4 hover:text-foreground cursor-pointer"}
) %}
<nav role="menu">
<button type="button" role="menuitem" onclick="console.log('Documentation')">Documentation</button>
+7 -15
View File
@@ -36,8 +36,7 @@ toc:
trigger_attrs={"class": "w-[200px]"},
listbox_attrs={"data-empty": "No framework found."},
is_combobox=true,
search_placeholder="Search framework...",
register_on=["alpine:init", "htmx:afterSwap"]
search_placeholder="Search framework..."
) %}
{% for framework in options_frameworks %}
<div role="option" data-value="{{ framework }}">{{ framework }}</div>
@@ -54,15 +53,10 @@ toc:
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1: Include the JavaScript files</a></h4>
<section class="prose">
<p>Include the <a href="https://github.com/hunvreus/basecoat/blob/main/src/js/select.js" target="_blank"><code>select.js</code></a> file. It is recommended to also include the <a href="https://github.com/oddbird/css-anchor-positioning" target="_blank">CSS anchor positioning polyfill</a> to support older browsers. Add this to the <code>&lt;head&gt;</code> of your page:</p>
<p>You can either <a href="/installation/#install-cdn-all">include the JavaScript file for all the components</a>, or just the one for this component by adding this to the <code>&lt;head&gt;</code> of your page:</p>
</section>
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/select.min.js" defer></script>
<script type="module">
if (!("anchorName" in document.documentElement.style)) {
import("https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/css-anchor-positioning.min.js");
}
</script>{% endset %}
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ pkg.version }}/dist/js/select.min.js" defer></script>{% endset %}
{{ code_block(code_script | prettyHtml, "html") }}
<div class="flex flex-wrap gap-2 my-6">
@@ -211,16 +205,15 @@ toc:
{% set code %}
{% call select(
trigger_attrs={"class": "w-[200px]"},
content_attrs={"class": "w-72"},
popover_attrs={"class": "w-72"},
listbox_attrs={"data-empty": "No timezone found."},
is_combobox=true,
search_placeholder="Search timezone...",
register_on=["alpine:init", "htmx:afterSwap"]
search_placeholder="Search timezone..."
) %}
<div class="max-h-64 overflow-y-auto scrollbar">
{% for group in options_timezones %}
<div role="group" aria-labelledby="demo-combobox-timezones-group-{{ loop.index0 }}">
<span id="demo-combobox-timezones-group-{{ loop.index0 }}" role="heading">{{ group.label }}</span>
<div role="presentation" id="demo-combobox-timezones-group-{{ loop.index0 }}">{{ group.label }}</div>
{% for timezone in group.timezones %}
<div role="option" data-value="{{ timezone.value}}">
{{ timezone.label }}
@@ -247,8 +240,7 @@ toc:
listbox_attrs={"data-empty": "No framework found."},
is_combobox=true,
search_placeholder="Search framework...",
register_on=["alpine:init", "htmx:afterSwap"],
content_attrs={"data-side": "top"}
popover_attrs={"data-side": "top"}
) %}
{% for framework in options_frameworks %}
<div role="option" data-value="{{ framework }}">{{ framework }}</div>
+6 -8
View File
@@ -32,13 +32,13 @@ toc:
description="Make changes to your profile here. Click save when you're done.",
trigger="Edit Profile",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
dialog_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
footer=footer
) %}
<form class="form grid gap-4">
<div class="grid gap-3">
<label for="demo-dialog-edit-profile-name">Name</label>
<input type="text" value="Pedro Duarte" id="demo-dialog-edit-profile-name" x-ref="focusOnOpen" />
<input type="text" value="Pedro Duarte" id="demo-dialog-edit-profile-name" autofocus/>
</div>
<div class="grid gap-3">
<label for="demo-dialog-edit-profile-username">Username</label>
@@ -126,7 +126,7 @@ toc:
description="Make changes to your profile here. Click save when you're done.",
trigger="Edit Profile",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
dialog_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
footer=footer
) %}
<form class="form grid gap-4">
@@ -154,13 +154,11 @@ toc:
id="dialog-example",
title="Scrollable Content",
description="This is a dialog with scrollable content.",
main_attrs={"x-ref": "myDialog"},
trigger="Scrollable Content",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
content_body_attrs={"class": "overflow-y-auto scrollbar"},
footer=footer,
register_on=["alpine:init", "htmx:afterSwap"]
dialog_attrs={"class": "w-full sm:max-w-[425px] max-h-[612px]"},
dialog_attrs={"class": "overflow-y-auto scrollbar"},
footer=footer
) %}
<div class="space-y-4 text-sm">
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.</p>
+60 -73
View File
@@ -38,39 +38,39 @@ toc:
popover_attrs={"class": "min-w-56"}
) %}
<div role="group" aria-labelledby="account-options">
<span id="account-options" role="heading">My Account</span>
<button type="button" role="menuitem">
<div role="presentation" id="account-options">My Account</div>
<div role="menuitem">
Profile
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Billing
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Settings
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Keyboard shortcuts
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘K</span>
</button>
</div>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
GitHub
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Support
</button>
<button type="button" role="menuitem" disabled>
</div>
<div role="menuitem" disabled>
API
</button>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
Logout
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
</div>
{% endcall %}
{% endset %}
@@ -83,15 +83,10 @@ toc:
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1: Include the JavaScript files</a></h4>
<section class="prose">
<p>Include the <a href="https://github.com/hunvreus/basecoat/blob/main/src/js/dropdown-menu.js" target="_blank"><code>dropdown-menu.js</code></a> file. It is recommended to also include the <a href="https://github.com/oddbird/css-anchor-positioning" target="_blank">CSS anchor positioning polyfill</a> to support older browsers. Add this to the <code>&lt;head&gt;</code> of your page:</p>
<p>You can either <a href="/installation/#install-cdn-all">include the JavaScript file for all the components</a>, or just the one for this component by adding this to the <code>&lt;head&gt;</code> of your page:</p>
</section>
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/dropdown-menu.min.js" defer></script>
<script type="module">
if (!("anchorName" in document.documentElement.style)) {
import("https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/css-anchor-positioning.min.js");
}
</script>{% endset %}
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ pkg.version }}/dist/js/dropdown-menu.min.js" defer></script>{% endset %}
{{ code_block(code_script | prettyHtml, "html") }}
<div class="flex flex-wrap gap-2 my-6">
@@ -185,43 +180,42 @@ toc:
id="dropdown-menu",
trigger="Open",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "min-w-56"},
register_on=["alpine:init", "htmx:afterSwap"]
popover_attrs={"class": "min-w-56"}
) %}
<div role="group" aria-labelledby="account-options">
<span id="account-options" role="heading">My Account</span>
<button type="button" role="menuitem">
<div role="presentation" id="account-options">My Account</div>
<div role="menuitem">
Profile
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Billing
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Settings
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Keyboard shortcuts
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘K</span>
</button>
</div>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
GitHub
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
Support
</button>
<button type="button" role="menuitem" disabled>
</div>
<div role="menuitem" disabled>
API
</button>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
Logout
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
</div>
{% endcall %}{% endraw %}{% endset%}
{{ code_block(raw_code, "jinja") }}
@@ -233,32 +227,30 @@ toc:
id="dropdown-menu-checkboxes",
trigger="Open",
trigger_attrs={"class": "btn-outline"},
content_attrs={"class": "min-w-56"},
register_on=["alpine:init", "htmx:afterSwap"]
popover_attrs={"class": "min-w-56"}
) %}
<div role="group" aria-labelledby="account-options">
<span id="account-options" role="heading">Account Options</span>
<button type="button" role="menuitem">
<div role="presentation" id="account-options">Account Options</div>
<div role="menuitem">
{% lucide "user" %}
Profile
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
{% lucide "credit-card" %}
Billing
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button type="button" role="menuitem">
</div>
<div role="menuitem">
{% lucide "settings" %}
Settings
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
</div>
</div>
<hr role="separator">
<div role="group" aria-labelledby="appearance-options">
<span id="appearance-options" role="heading">Appearance</span>
<button
type="button"
<div role="presentation" id="appearance-options">Appearance</div>
<div
role="menuitemcheckbox"
aria-checked="true"
class="group"
@@ -273,9 +265,8 @@ toc:
} %}
Status Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button
type="button"
</div>
<div
role="menuitemcheckbox"
aria-checked="false"
class="group"
@@ -291,9 +282,8 @@ toc:
} %}
Activity Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button
type="button"
</div>
<div
role="menuitemcheckbox"
aria-checked="false"
class="group"
@@ -308,14 +298,14 @@ toc:
} %}
Panel
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
</div>
</div>
<hr role="separator">
<button type="button" role="menuitem">
<div role="menuitem">
{% lucide "log-out" %}
Logout
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
</div>
{% endcall %}{% endset %}
{{ code_preview("dropdown-menu-checkboxes", code | prettyHtml) }}
@@ -330,8 +320,7 @@ toc:
<div role="group" aria-labelledby="position-options" x-data="{ checked: 'bottom' }">
<span id="position-options" role="heading">Panel Position</span>
<hr role="separator">
<button
type="button"
<div
role="menuitemradio"
aria-checked="false"
class="group"
@@ -347,9 +336,8 @@ toc:
</div>
Status Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⇧⌘P</span>
</button>
<button
type="button"
</div>
<div
role="menuitemradio"
aria-checked="false"
class="group"
@@ -365,9 +353,8 @@ toc:
</div>
Activity Bar
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘B</span>
</button>
<button
type="button"
</div>
<div
role="menuitemradio"
aria-checked="false"
class="group"
@@ -383,7 +370,7 @@ toc:
</div>
Panel
<span class="text-muted-foreground ml-auto text-xs tracking-widest">⌘S</span>
</button>
</div>
</div>
{% endcall %}{% endset %}
{{ code_preview("dropdown-menu", code | prettyHtml) }}
+3 -7
View File
@@ -63,17 +63,13 @@ toc:
<h3 id="usage-html-js"><a href="#usage-html-js">HTML + JavaScript</a></h3>
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1 (Optional): Include the JavaScript file</a></h4>
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1: Include the JavaScript file</a></h4>
<section class="prose">
<p>It is recommended to include the <a href="https://github.com/oddbird/css-anchor-positioning" target="_blank">CSS anchor positioning polyfill</a> to support older browsers. Add this to the <code>&lt;head&gt;</code> of your page:</p>
<p>You can either <a href="/installation/#install-cdn-all">include the JavaScript file for all the components</a>, or just the one for this component by adding this to the <code>&lt;head&gt;</code> of your page:</p>
</section>
{% set code_script %}<script type="module">
if (!("anchorName" in document.documentElement.style)) {
import("https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/css-anchor-positioning.min.js");
}
</script>{% endset %}
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ pkg.version }}/dist/js/popover.min.js" defer></script>{% endset %}
{{ code_block(code_script | prettyHtml, "html") }}
<div class="flex flex-wrap gap-2 my-6">
+5 -13
View File
@@ -85,15 +85,10 @@ toc:
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1: Include the JavaScript files</a></h4>
<section class="prose">
<p>Include the <a href="https://github.com/hunvreus/basecoat/blob/main/src/js/select.js" target="_blank"><code>select.js</code></a> file. It is recommended to also include the <a href="https://github.com/oddbird/css-anchor-positioning" target="_blank">CSS anchor positioning polyfill</a> to support older browsers. Add this to the <code>&lt;head&gt;</code> of your page:</p>
<p>You can either <a href="/installation/#install-cdn-all">include the JavaScript file for all the components</a>, or just the one for this component by adding this to the <code>&lt;head&gt;</code> of your page:</p>
</section>
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/select.min.js" defer></script>
<script type="module">
if (!("anchorName" in document.documentElement.style)) {
import("https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/css-anchor-positioning.min.js");
}
</script>{% endset %}
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ pkg.version }}/dist/js/select.min.js" defer></script>{% endset %}
{{ code_block(code_script | prettyHtml, "html") }}
<div class="flex flex-wrap gap-2 my-6">
@@ -205,8 +200,7 @@ toc:
{% set code %}
{% call select(
listbox_attrs={"class": "scrollbar overflow-y-auto max-h-64"},
register_on=["alpine:init", "htmx:afterSwap"]
listbox_attrs={"class": "scrollbar overflow-y-auto max-h-64"}
) %}
{% for i in range(0, 99) %}
<div role="option" data-value="item-{{ i }}">Item {{ i }}</div>
@@ -220,8 +214,7 @@ toc:
{% set code %}
{% call select(
trigger_attrs={"disabled": "disabled"},
register_on=["alpine:init", "htmx:afterSwap"]
trigger_attrs={"disabled": "disabled"}
) %}
<div role="option" data-value="disabled">Disabled</div>
{% endcall %}
@@ -233,8 +226,7 @@ toc:
{% set code %}
{% call select(
trigger_attrs={'class': 'w-[180px]'},
register_on=["alpine:init", "htmx:afterSwap"]
trigger_attrs={'class': 'w-[180px]'}
) %}
<div type="button" role="option" data-value="bar">
<span class="flex items-center gap-2">
+2 -2
View File
@@ -29,10 +29,10 @@ toc:
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1: Include the JavaScript files</a></h4>
<section class="prose">
<p>Include the <a href="https://github.com/hunvreus/basecoat/blob/main/src/js/sidebar.js" target="_blank"><code>sidebar.js</code></a> file. Add this to the <code>&lt;head&gt;</code> of your page:</p>
<p>You can either <a href="/installation/#install-cdn-all">include the JavaScript file for all the components</a>, or just the one for this component by adding this to the <code>&lt;head&gt;</code> of your page:</p>
</section>
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/sidebar.min.js" defer></script>{% endset %}
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ pkg.version }}/dist/js/select.min.js" defer></script>{% endset %}
{{ code_block(code_script | prettyHtml, "html") }}
<div class="flex flex-wrap gap-2 my-6">
+4 -6
View File
@@ -71,8 +71,7 @@ toc:
id='demo-tabs-with-panels',
tabsets=tabsets_demo,
main_attrs={ "class": "w-full" },
tablist_attrs={ "class": "w-full" },
register_on=["alpine:init", "htmx:afterSwap"]
tablist_attrs={ "class": "w-full" }
) }}
{% endset %}
@@ -83,10 +82,10 @@ toc:
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1: Include the JavaScript files</a></h4>
<section class="prose">
<p>Include the <a href="https://github.com/hunvreus/basecoat/blob/main/src/js/tabs.js" target="_blank"><code>tabs.js</code></a> file. Add this to the <code>&lt;head&gt;</code> of your page:</p>
<p>You can either <a href="/installation/#install-cdn-all">include the JavaScript file for all the components</a>, or just the one for this component by adding this to the <code>&lt;head&gt;</code> of your page:</p>
</section>
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/tabs.min.js" defer></script>{% endset %}
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ pkg.version }}/dist/js/select.min.js" defer></script>{% endset %}
{{ code_block(code_script | prettyHtml, "html") }}
<div class="flex flex-wrap gap-2 my-6">
@@ -209,7 +208,6 @@ toc:
id='demo-tabs-with-panels',
tabsets=tabsets_demo,
main_attrs={ "class": "w-full" },
tablist_attrs={ "class": "w-full" },
register_on=["alpine:init", "htmx:afterSwap"]
tablist_attrs={ "class": "w-full" }
) }}{% endraw %}{% endset%}
{{ code_block(raw_code, "jinja") }}
+2 -2
View File
@@ -64,10 +64,10 @@ toc:
<h4 id="usage-html-js-1"><a href="#usage-html-js-1">Step 1: Include the JavaScript file</a></h4>
<section class="prose">
<p>Include the <a href="https://github.com/hunvreus/basecoat/blob/main/src/js/toast.js" target="_blank"><code>toast.js</code></a> file. Add this to the <code>&lt;head&gt;</code> of your page:</p>
<p>You can either <a href="/installation/#install-cdn-all">include the JavaScript file for all the components</a>, or just the one for this component by adding this to the <code>&lt;head&gt;</code> of your page:</p>
</section>
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/toast.min.js" defer></script>{% endset %}
{% set code_script %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ pkg.version }}/dist/js/select.min.js" defer></script>{% endset %}
{{ code_block(code_script | prettyHtml, "html") }}
<div class="flex flex-wrap gap-2 my-6">
+2 -2
View File
@@ -53,7 +53,7 @@ layout: layouts/layout.njk
{% call select(
is_combobox=true,
content_attrs={"data-align": "end"}
popover_attrs={"data-align": "end"}
) %}
<div role="option" data-value="viewer">Viewer</div>
<div role="option" data-value="developer">Developer</div>
@@ -70,7 +70,7 @@ layout: layouts/layout.njk
{% call select(
is_combobox=true,
content_attrs={"data-align": "end"}
popover_attrs={"data-align": "end"}
) %}
<div role="option" data-value="viewer">Viewer</div>
<div role="option" data-value="developer">Developer</div>
+12 -34
View File
@@ -3,8 +3,6 @@ layout: layouts/page.njk
title: Installation
description: How to install and use Basecoat in your app.
toc:
- label: Quickstart
id: install-quickstart
- label: Install using the CDN
id: install-cdn
- label: Installing using NPM
@@ -33,39 +31,26 @@ toc:
{% from "macros/code_block.njk" import code_block %}
{% from "tabs.njk" import tabs %}
<h2 id="install-quickstart"><a href="#install-quickstart">Quickstart</a></h2>
<h2 id="install-cdn"><a href="#install-cdn">Install using the CDN</a></h2>
<h3 id="install-cdn-all"><a href="#install-cdn-all">Install all components</a></h3>
<section class="prose">
<p>The fastest way to get up and running is to load the CSS and all of the components' JavaScript using the CDN. Add the following to the <code>&lt;head&gt;</code> of your HTML file:</p>
<p>Add the following to the <code>&lt;head&gt;</code> of your HTML file:</p>
</section>
{% set code %}<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/cdn.min.css">
<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/all.min.js" defer></script>
<script type="module">
if (!("anchorName" in document.documentElement.style)) {
import("https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/css-anchor-positioning.min.js");
}
</script>{% endset %}
<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/all.min.js" defer></script>{% endset %}
{{ code_block(code, "html") }}
<section class="prose">
<p>If you're not using all of the components requiring JavaScript (<a href="#install-js">Dropdown Menu</a>, <a href="#install-js">Select</a>, <a href="#install-js">Sidebar</a>, <a href="#install-js">Tabs</a> and <a href="#install-js">Toast</a>), follow the instructions below to only include the JavaScript files you actually need.</p>
</section>
<h2 id="install-cdn"><a href="#install-cdn">Install using the CDN</a></h2>
<h3 id="install-cdn-all"><a href="#install-cdn-all">Install specific components</a></h3>
<section class="prose">
<p>The easiest way to use Basecoat is use the CDN. First, add the CSS to the <code>&lt;head&gt;</code> of your HTML file:</p>
<p>While the JavaScript file for all components is small (around 3kB gzipped), you can cherry-pick the components you need as instructed in the component's page (<a href="/components/dropdown-menu">Dropdown Menu</a>, <a href="/components/popover">Popover</a>, <a href="/components/select">Select</a>, <a href="/components/sidebar">Sidebar</a>, <a href="/components/tabs">Tabs</a> and <a href="/components/toast">Toast</a>). For example, to add the <a href="/components/dropdown-menu">Dropdown Menu</a> component, add the following to the <code>&lt;head&gt;</code> of your HTML file:</p>
</section>
{% set code %}<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/cdn.min.css">{% endset %}
{{ code_block(code, "html") }}
<section class="prose">
<p>Depending on the components you want to use, you may also need to add JavaScript files as instructed on the component's page. For example, for the <a href="/components/tabs">Tabs</a> component, you would add the following:</p>
</section>
{% set code %}<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/tabs.min.js"></script>{% endset %}
{% set code %}<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/cdn.min.css">
<script src="https://cdn.jsdelivr.net/npm/basecoat-css@{{ site.version }}/dist/js/dropdown-menu.min.js" defer></script>{% endset %}
{{ code_block(code, "html") }}
<h2 id="install-npm"><a href="#install-npm">Install using NPM</a></h2>
@@ -122,20 +107,13 @@ toc:
<h2 id="install-js"><a href="#install-js">Components with JavaScript</a></h2>
<div class="prose">
<p><b>Some components may require JavaScript code to work.</b></p>
<p><b>A handful of components require JavaScript code to work.</b>, specifically <a href="/components/dropdown-menu">Dropdown Menu</a>, <a href="/components/popover">Popover</a>, <a href="/components/select">Select</a>, <a href="/components/sidebar">Sidebar</a>, <a href="/components/tabs">Tabs</a> and <a href="/components/toast">Toast</a></p>
<p>If a component requires JavaScript, the documentation page will provide instructions. There are 2 options to add the JavaScript code to your project:</p>
<ul>
<li><b>CDN</b>: you add the <code>&lt;script&gt;</code> tag provided on the component's page to the <code>&lt;head&gt;</code> of your HTML file.</li>
<li><b>Local file</b>: you download the script as a separate file and include it in your project (<a href="#install-cli">or let the CLI do it for you</a>). Make sure keep the <code>defer</code> attribute on the <code>&lt;script&gt;</code> tag when doing so.</p>
</ul>
<p>A few things to keep in mind:</p>
<ul>
<li>Most components (e.g. <a href="/components/button">Button</a>, <a href="/components/card">Card</a>, <a href="/components/input">Input</a>, etc) do not require any JavaScript at all to work.</li>
<li>Some of the JavaScript is optional. For example the <a href="/components/dropdown-menu">Dropdown Menu component</a> suggest to add the <a href="https://github.com/oddbird/css-anchor-positioning" target="_blank">CSS anchor positioning polyfill</a> to support older browser, as well as a <code>dropdown-menu.js</code> to improve accessiblity (WAI-ARIA) and usability (keyboard navigation).</li>
<li>Only a handful of components require JavaScript to work (e.g. <a href="/components/sidebar">Sidebar</a>, <a href="/components/toast">Toast</a>, ...).</li>
<li><b>CDN</b>: you either <a href="#install-cdn-all">add the code for all of the components</a> to the <code>&lt;head&gt;</code> of your HTML file, or just the file for the component you want to use as instructed on the component's page.</li>
<li><b>Local file</b>: you download the script as a separate file and include it in your project (<a href="#install-cli">or let the CLI do it for you</a>). Once again, you have the choice to include the fiel for all components at once (<a><code>all.min.js</code> or <code>all.js</code>).</p>
</ul>
</div>
+71
View File
@@ -0,0 +1,71 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Anchor Positioning Test (Top, End)</title>
<script type="module">
if (!("anchorName" in document.documentElement.style)) {
console.log("Loading CSS anchor positioning polyfill...");
import("https://unpkg.com/@oddbird/css-anchor-positioning");
}
</script>
<style>
body {
font-family: sans-serif;
display: grid;
place-items: center;
height: 100vh;
margin: 0;
background: #222;
color: #eee;
}
button {
padding: 0.5em 1em;
font-size: 1rem;
border-radius: 6px;
border: 1px solid #888;
background: #444;
color: #eee;
cursor: pointer;
}
[popover] {
border: 1px solid #888;
border-radius: 6px;
background: #333;
color: #eee;
padding: 1em;
margin: 0;
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.5);
}
/* The core anchor positioning logic */
#my-popover {
position: absolute;
inset: auto; /* Required to override default popover centering */
bottom: anchor(top); /* Position bottom of popover to top of anchor */
right: anchor(right); /* Align right edge of popover with right edge of anchor */
margin-bottom: 8px; /* A little space between popover and button */
}
</style>
</head>
<body>
<button
popovertarget="my-popover"
id="my-anchor-button"
style="anchor-name: --my-anchor;">
Click Me
</button>
<div
popover
id="my-popover"
style="position-anchor: --my-anchor;">
I should be anchored above the button, aligned to the right.
</div>
</body>
</html>