DaisyUI 5 Masterclass Reference
Production-grade reference for Funday. Zero setup, zero bloat, 100% truth.
<element class="COMPONENT [STYLE] [COLOR] [SIZE] [MODIFIER] [BEHAVIOR] [PLACEMENT]">
<child class="PART">content</child>
</element>
Slot Examples Required? COMPONENT btn, card, modal, input, dropdown, drawer, tabs, accordion, avatar, badge, alert, navbar, menu, tab, progress, loading, tooltip, swap, divider, stat, kbd, join, mask, indicator, radial-progress, countdown, diff, chat, carousel, collapse, fieldset, label, range, rating, select, textarea, toggle, checkbox, radio, file-input, filter, calendar, validator, breadcrumbs, dock, link, pagination, steps, hero, footer, stack, toast, table, timeline, hover-3d, hover-gallery, text-rotate, mockup-browser, mockup-code, mockup-phone, mockup-window, theme-controller, fab, glass, aura✅ YES STYLE btn-outline, btn-dash, btn-soft, btn-ghost, btn-link / card-border, card-dash / alert-outline, alert-dash, alert-soft / input-ghost, select-ghost / tabs-box, tabs-border, tabs-lift / badge-outline, badge-dash, badge-soft, badge-ghostNo COLOR primary, secondary, accent, neutral, info, success, warning, error, base-100, base-200, base-300No SIZE xs, sm, md, lg, xl (prefixed: btn-, badge-, input-, select-, tab-, menu-, avatar-, kbd-, aura-, collapse-, divider-, stat-, loading-, progress-, radial-progress-, tooltip-, join-, indicator-, countdown-, diff-, carousel-, mockup-)No MODIFIER btn-wide, btn-block, btn-circle, btn-square / card-side, image-full / modal-top, modal-bottom, modal-middle, modal-start, modal-end / drawer-end / tabs-top, tabs-bottom / menu-horizontal / alert-vertical, alert-horizontal / collapse-arrow, collapse-plus / avatar-online, avatar-offline, avatar-placeholder / mask-squircle, mask-hexagon, mask-triangle / join-*No BEHAVIOR btn-active, btn-disabled / tab-active, tab-disabled / menu-active / collapse-open, collapse-close / modal-open / drawer-open / swap-on, swap-off / checkbox-checked, radio-checked / toggle-on, toggle-off / input-checkedState only PLACEMENT modal-top, modal-middle, modal-bottom, modal-start, modal-end / drawer-end / tooltip-top, tooltip-bottom, tooltip-left, tooltip-rightComponent-specific
Color System — Only These Exist
Semantic Background Foreground Use For primarybg-primarytext-primary-contentMain CTA secondarybg-secondarytext-secondary-contentSecondary brand accentbg-accenttext-accent-contentHighlights neutralbg-neutraltext-neutral-contentSubdued UI base-100bg-base-100text-base-contentPage background base-200bg-base-200text-base-contentElevated surface base-300bg-base-300text-base-contentMore elevation infobg-infotext-info-contentInfo messages successbg-successtext-success-contentSuccess states warningbg-warningtext-warning-contentCaution errorbg-errortext-error-contentErrors, destructive
All work with every Tailwind utility: bg-, text-, border-, ring-, shadow-, fill-, stroke-, divide-, placeholder-, ring-offset-, from-, via-, to-, accent-, caret-, decoration-
<!-- ✅ Theme-adaptive -->
< button class = "btn btn-primary" >Primary</ button >
< div class = "bg-base-200 text-base-content/60" >Muted text on elevated surface</ div >
<!-- ❌ Never: hardcoded colors break dark mode -->
< div class = "bg-blue-500 text-gray-800" >Broken on dark theme</ div >
<!-- Styles -->
< button class = "btn" >Default solid</ button >
< button class = "btn btn-outline" >Outline</ button >
< button class = "btn btn-dash" >Dashed</ button >
< button class = "btn btn-soft" >Soft tint</ button >
< button class = "btn btn-ghost" >Ghost (hover only)</ button >
< button class = "btn btn-link" >Link look</ button >
<!-- Colors -->
< button class = "btn btn-primary" >Primary</ button >
< button class = "btn btn-secondary" >Secondary</ button >
< button class = "btn btn-accent" >Accent</ button >
< button class = "btn btn-neutral" >Neutral</ button >
< button class = "btn btn-success" >Success</ button >
< button class = "btn btn-warning" >Warning</ button >
< button class = "btn btn-error" >Error</ button >
< button class = "btn btn-info" >Info</ button >
<!-- Sizes -->
< button class = "btn btn-xs" >XS</ button >
< button class = "btn btn-sm" >SM</ button >
< button class = "btn btn-md" >MD (default)</ button >
< button class = "btn btn-lg" >LG</ button >
< button class = "btn btn-xl" >XL</ button >
<!-- Shapes -->
< button class = "btn btn-wide" >Wide</ button >
< button class = "btn btn-block" >Full width</ button >
< button class = "btn btn-circle" >Circle</ button >
< button class = "btn btn-square" >Square</ button >
<!-- States -->
< button class = "btn btn-active" >Active</ button >
< button class = "btn btn-disabled" >Disabled</ button >
<!-- Responsive (v5+) -->
< button class = "btn btn-sm lg:btn-lg" >Responsive size</ button >
Card
< div class = "card bg-base-100 shadow-xl" >
< figure >< img src = "..." alt = "..." /></ figure >
< div class = "card-body" >
< h2 class = "card-title" >Title</ h2 >
< p >Description</ p >
< div class = "card-actions justify-end" >
< button class = "btn btn-primary" >Action</ button >
</ div >
</ div >
</ div >
<!-- Variants -->
< div class = "card card-border" >Border</ div >
< div class = "card card-dash" >Dashed</ div >
< div class = "card card-side" >Horizontal</ div >
< div class = "card image-full" >Full image</ div >
<!-- Sizes: card-xs, card-sm, card-md, card-lg, card-xl -->
Modal (Native <dialog>)
< button onclick = " my_modal . showModal ()" class = "btn" >Open</ button >
< dialog id = "my_modal" class = "modal" >
< div class = "modal-box" >
< h3 class = "text-lg font-bold" >Title</ h3 >
< p class = "py-4" >Content</ p >
< div class = "modal-action" >
< form method = "dialog" >< button class = "btn" >Close</ button ></ form >
</ div >
</ div >
< form method = "dialog" class = "modal-backdrop" >< button >Close</ button ></ form >
</ dialog >
<!-- Placements: modal-top, modal-middle (default), modal-bottom, modal-start, modal-end -->
Tabs (Radio-Based, No JS)
< div class = "tabs tabs-lift" >
< input type = "radio" name = "tabs" class = "tab" aria-label = "Tab 1" checked />
< div class = "tab-content bg-base-100 border-base-300 p-6" >Content 1</ div >
< input type = "radio" name = "tabs" class = "tab" aria-label = "Tab 2" />
< div class = "tab-content bg-base-100 border-base-300 p-6" >Content 2</ div >
< input type = "radio" name = "tabs" class = "tab" aria-label = "Tab 3" disabled />
< div class = "tab-content bg-base-100 border-base-300 p-6" >Disabled</ div >
</ div >
<!-- Styles: tabs-box, tabs-border, tabs-lift (default) -->
<!-- Placement: tabs-top (default), tabs-bottom -->
Drawer — FUNDAY CRITICAL FIX
<!-- ⚠️ BROKEN: DaisyUI default grid collapses to 0px on lg: -->
< div class = "drawer lg:drawer-open" >
< input id = "drawer" type = "checkbox" class = "drawer-toggle" />
< div class = "drawer-content" >Main</ div >
< div class = "drawer-side" >< label for = "drawer" class = "drawer-overlay" ></ label >Sidebar</ div >
</ div >
<!-- ✅ FIX 1: CSS Override (add to app.css) -->
.drawer.lg\:drawer-open {
grid-template-columns: max-content auto !important;
}
<!-- ✅ FIX 2: Flexbox Sidebar (RECOMMENDED - no grid fragility) -->
< div class = "flex min-h-screen" >
< aside class = "w-64 bg-base-200 lg:w-64 hidden lg:block" >Sidebar</ aside >
< main class = "flex-1" >Main content</ main >
</ div >
<!-- Mobile drawer (works correctly) -->
< div class = "drawer" >
< input id = "mobile-drawer" type = "checkbox" class = "drawer-toggle" />
< div class = "drawer-content" >
< nav class = "navbar bg-base-300" >
< label for = "mobile-drawer" class = "btn btn-square btn-ghost lg:hidden" >☰</ label >
< div class = "px-4" >Title</ div >
</ nav >
< main class = "p-4" >Content</ main >
</ div >
< div class = "drawer-side" >
< label for = "mobile-drawer" class = "drawer-overlay" ></ label >
< ul class = "menu min-h-full w-80 bg-base-200 p-4" >
< li >< a >Item 1</ a ></ li >
< li >< a >Item 2</ a ></ li >
</ ul >
</ div >
</ div >
Badge
<!-- Styles: badge, badge-outline, badge-dash, badge-soft, badge-ghost -->
<!-- Colors: badge-primary, badge-secondary, badge-accent, badge-neutral, badge-success, badge-warning, badge-error, badge-info -->
<!-- Sizes: badge-xs, badge-sm, badge-md, badge-lg, badge-xl -->
< span class = "badge badge-primary badge-lg" >Primary Large</ span >
Alert
< div role = "alert" class = "alert" >Default</ div >
< div role = "alert" class = "alert alert-outline" >Outline</ div >
< div role = "alert" class = "alert alert-dash" >Dashed</ div >
< div role = "alert" class = "alert alert-soft" >Soft</ div >
< div role = "alert" class = "alert alert-info" >Info</ div >
< div role = "alert" class = "alert alert-success" >Success</ div >
< div role = "alert" class = "alert alert-warning" >Warning</ div >
< div role = "alert" class = "alert alert-error" >Error</ div >
< div role = "alert" class = "alert alert-vertical" >Stacked</ div >
< div role = "alert" class = "alert alert-horizontal sm:alert-horizontal" >Responsive horizontal</ div >
Input / Select / Textarea
< input type = "text" class = "input input-bordered w-full max-w-xs" placeholder = "Text" />
< input type = "text" class = "input input-ghost w-full max-w-xs" placeholder = "Ghost" />
< input type = "text" class = "input input-primary w-full max-w-xs" placeholder = "Primary" />
< input type = "text" class = "input input-error w-full max-w-xs" placeholder = "Error" />
< input type = "text" class = "input input-xs w-full max-w-xs" placeholder = "XS" />
< input type = "text" class = "input input-sm w-full max-w-xs" placeholder = "SM" />
< input type = "text" class = "input input-md w-full max-w-xs" placeholder = "MD" />
< input type = "text" class = "input input-lg w-full max-w-xs" placeholder = "LG" />
< input type = "text" class = "input input-xl w-full max-w-xs" placeholder = "XL" />
< input type = "text" class = "input" disabled placeholder = "Disabled" />
< select class = "select select-bordered w-full max-w-xs" >
< option value = "" >Select...</ option >
< option value = "1" >Option 1</ option >
</ select >
< select class = "select select-ghost w-full max-wxs" >...</ select >
< select class = "select select-primary w-full max-w-xs" >...</ select >
< textarea class = "textarea textarea-bordered h-24 w-full max-w-xs" placeholder = "Textarea" ></ textarea >
< textarea class = "textarea textarea-ghost h-24 w-full max-w-xs" ></ textarea >
< textarea class = "textarea textarea-primary h-24 w-full max-w-xs" ></ textarea >
Loading / Progress / Radial Progress
< span class = "loading loading-spinner loading-lg" ></ span >
< span class = "loading loading-dots loading-lg" ></ span >
< span class = "loading loading-ring loading-lg" ></ span >
< span class = "loading loading-ball loading-lg" ></ span >
< span class = "loading loading-bar loading-lg" ></ span >
< span class = "loading loading-infinity loading-lg" ></ span >
< span class = "loading loading-spinner text-primary" ></ span >
< progress class = "progress progress-primary w-full" value = "50" max = "100" ></ progress >
< progress class = "progress progress-secondary w-full" value = "30" max = "100" ></ progress >
< div class = "radial-progress" style = "--value: 50; --size: 80px;" ></ div >
< div class = "radial-progress radial-progress-primary" style = "--value: 75; --size: 100px;" ></ div >
Navbar
< nav class = "navbar bg-base-300" >
< div class = "navbar-start" >
< div class = "dropdown" >
< label tabindex = "0" class = "btn btn-ghost btn-circle" >☰</ label >
< ul class = "menu menu-sm dropdown-content mt-3 z-[1] p-2 shadow bg-base-100 rounded-box w-52" >
< li >< a >Item 1</ a ></ li >
< li >< a >Item 2</ a ></ li >
</ ul >
</ div >
< a class = "btn btn-ghost text-xl" >Funday</ a >
</ div >
< div class = "navbar-center" >
< ul class = "menu menu-horizontal px-1" >
< li >< a >Games</ a ></ li >
< li >< a >Leaderboard</ a ></ li >
< li >< a >Profile</ a ></ li >
</ ul >
</ div >
< div class = "navbar-end" >
< button class = "btn btn-primary" >Play</ button >
</ div >
</ nav >
Dock (Mobile Bottom Nav — Funday Play Shell)
< div class = "dock" >
< label for = "dock-game" class = "dock-item" >
< input type = "radio" name = "dock" id = "dock-game" class = "dock-toggle" checked />
< svg class = "dock-icon" >< use href = "#icon-game" ></ use ></ svg >
< span class = "dock-label" >Game</ span >
</ label >
< label for = "dock-chat" class = "dock-item" >
< input type = "radio" name = "dock" id = "dock-chat" class = "dock-toggle" />
< svg class = "dock-icon" >< use href = "#icon-chat" ></ use ></ svg >
< span class = "dock-label" >Chat</ span >
</ label >
< label for = "dock-profile" class = "dock-item" >
< input type = "radio" name = "dock" id = "dock-profile" class = "dock-toggle" />
< svg class = "dock-icon" >< use href = "#icon-profile" ></ use ></ svg >
< span class = "dock-label" >Profile</ span >
</ label >
</ div >
Theme Config (Funday Default)
/* src/app.css */
@import "tailwindcss" ;
@plugin "daisyui" {
themes: light --default, dark --prefersdark;
}
/* Custom Funday theme (OKLCH) */
@plugin "daisyui/theme" {
name: "funday";
default: true;
prefersdark: false;
color-scheme : light;
--color-base-100: oklch(98% 0 .02 240);
--color-base-200: oklch(95% 0 .03 240);
--color-base-300: oklch(92% 0 .04 240);
--color-base-content: oklch(20% 0 .05 240);
--color-primary: oklch(55% 0 .3 240);
--color-primary-content: oklch(98% 0 .01 240);
--color-secondary: oklch(70% 0 .25 200);
--color-secondary-content: oklch(98% 0 .01 200);
--color-accent: oklch(65% 0 .25 160);
--color-accent-content: oklch(98% 0 .01 160);
--color-neutral: oklch(50% 0 .05 240);
--color-neutral-content: oklch(98% 0 .01 240);
--color-info: oklch(70% 0 .2 220);
--color-info-content: oklch(98% 0 .01 220);
--color-success: oklch(65% 0 .25 140);
--color-success-content: oklch(98% 0 .01 140);
--color-warning: oklch(80% 0 .25 80);
--color-warning-content: oklch(20% 0 .05 80);
--color-error: oklch(65% 0 .3 30);
--color-error-content: oklch(98% 0 .01 30);
--radius-selector: 1rem;
--radius-field: 0.25rem;
--radius-box: 0.5rem;
--size-selector: 0.25rem;
--size-field: 0.25rem;
--border: 1px;
--depth: 1;
--noise: 0;
}
Theme switching:
< div data-theme = "dark" >Dark section</ div >
< div data-theme = "cupcake" >Cupcake section</ div >
< input type = "radio" name = "theme" class = "theme-controller" value = "light" />
< input type = "radio" name = "theme" class = "theme-controller" value = "dark" />
< input type = "radio" name = "theme" class = "theme-controller" value = "cupcake" />
Join
< div class = "join" >
< input type = "text" class = "join-item" placeholder = "Username" />
< button class = "btn join-item" >@</ button >
</ div >
< div class = "join join-vertical" >...</ div > <!-- stacked -->
< div class = "join" >...</ div > <!-- horizontal (default) -->
< div class = "join" >
< input class = "join-item join-item-start" /> <!-- rounded left/top -->
< input class = "join-item join-item-end" /> <!-- rounded right/bottom -->
</ div >
FUNDAY AESTHETIC CONSTRAINT — PURE SOLID BEAUTY
✅ DO ❌ DON’T bg-base-100, bg-primary, bg-secondary (100% opaque)backdrop-blur, glass, bg-base-100/50shadow-sm, shadow, shadow-lg, shadow-xl, shadow-2xlOpacity-based depth ring-1 ring-base-content/10 for subtle bordersTranslucent overlays rounded-box, rounded-field, rounded-selector (theme tokens)Hardcoded rounded-lg, rounded-xl
Mantra: Solid, high-performance, sharply readable. Elevate with clarity, not blur.
Svelte 5 Integration
< script >
let drawerOpen = $ state ( false );
let activeTab = $ state ( 'tab1' );
let accordionOpen = $ state ( false );
let isOpen = $ state ( false );
let dropdownOpen = $ state ( false );
let userTheme = $ state ( 'light' );
</ script >
<!-- Drawer -->
< div class = "drawer" >
< input type = "checkbox" class = "drawer-toggle" bind : checked ={drawerOpen} />
< div class = "drawer-content" >Main</ div >
< div class = "drawer-side" >Sidebar</ div >
</ div >
<!-- Modal -->
< dialog bind : open ={isOpen} class = "modal" >
< div class = "modal-box" >Content</ div >
< form method = "dialog" class = "modal-backdrop" ></ form >
</ dialog >
<!-- Tabs -->
< div class = "tabs tabs-lift" >
< input type = "radio" name = "tabs" class = "tab" bind : group ={activeTab} value = "tab1" />
< div class = "tab-content" >Tab 1</ div >
< input type = "radio" name = "tabs" class = "tab" bind : group ={activeTab} value = "tab2" />
< div class = "tab-content" >Tab 2</ div >
</ div >
<!-- Native events -->
< button onclick ={handleClick} class = "btn btn-primary" >Click</ button >
< input oninput ={handleInput} class = "input" />
<!-- ARIA from runes -->
< button aria-expanded ={dropdownOpen} class = "btn" >Menu</ button >
< div role = "alert" class = "alert alert-success" >Saved!</ div >
<!-- Dynamic theme -->
< div data-theme ={userTheme}>...</ div >
Common Pitfalls
❌ Mistake ✅ Fix dark:bg-gray-800 for themingbg-base-200 — auto-adaptstext-gray-800 on bg-base-100text-base-contentrounded-lg on cardsrounded-box (theme token)Custom CSS for btn hover btn-ghost, btn-outline, btn-softNesting component classes Each component is self-contained @apply for everythingOnly for new custom variants Forgetting data-theme for previews Add data-theme="x" on container v4 syntax daisyui: { themes: [] } v5: @plugin "daisyui" { themes: } Drawer grid = 0px width Flexbox sidebar OR CSS override <button aria-label="X">X</button>Remove aria-label if visible text exists
Size Scale
Size Multiplier Height Use xs×6 24px Dense UIs, badges sm×8 32px Compact forms md×10 40px Default lg×12 48px Prominent CTAs xl×14 56px Hero actions
Component CSS Variables (Inline Override)
< div class = "alert [--alert-color:blue]" >Custom blue alert</ div >
< button class = "btn [--btn-color:oklch(50%_0.2_200)]" >Custom color</ button >
< div class = "radial-progress" style = "--value: 75; --size: 120px; --thickness: 8px;" ></ div >
Component Key Variables Alert —alert-color Badge —badge-color, —size Button —btn-color, —btn-fg, —btn-shadow, —btn-p, —size Card —card-p, —card-fs, —cardtitle-fs Modal —modal-tl, —modal-tr, —modal-bl, —modal-br Radial Progress —value, —size, —thickness Tab —tabs-height, —tab-p, —tab-bg, —tab-border-color Toast —toast-x, —toast-y Tooltip —tt-bg, —tt-off, —tt-tailw Glass —glass-blur, —glass-opacity, —glass-reflect-* Join —join-ss, —join-se, —join-es, —join-ee
Verification Checklist (Pre-Ship)
Source: daisyUI 5 llms.txt + Funday production patterns. Triple-checked against live funday.gg codebase.