[READ-ONLY] Mirror of https://github.com/flo-bit/ui-kit. 🦊 fox ui, svelte 5 and tailwind 4 flo-bit.dev/ui-kit/
svelte tailwindcss ui-components
0

Configure Feed

Select the types of activity you want to include in your feed.

update docs, add copy code button, some fixes

Florian (Mar 13, 2025, 9:48 PM +0100) 379baf11 4e37e5c8

+349 -82
+1 -1
src/docs/site-components/PublicAlphaAlert.svelte
··· 4 4 let { class: className }: { class?: string } = $props(); 5 5 </script> 6 6 7 - <Alert title="Public alpha" class={cn("mb-8 not-prose", className)} type="warning" variant="default"> 7 + <Alert title="Public alpha" class={cn("mb-8 not-prose w-fit", className)} type="warning" variant="default"> 8 8 <span> 9 9 This is a public alpha release. Expect bugs and breaking changes. 10 10 </span>
+18 -18
src/lib/components/base/alert/alert.svelte
··· 6 6 variants: { 7 7 variant: { 8 8 default: 9 - 'bg-accent-500/10 [&>div:first-of-type]:text-accent-700 [&>svg]:text-accent-600 dark:[&>svg]:text-accent-500 dark:[&>div:first-of-type]:text-accent-500 dark:bg-accent-500/5 text-accent-600 dark:text-accent-400 border-accent-500/20 dark:border-accent-500/10', 9 + 'bg-accent-500/10 [&>div:first-of-type]:text-accent-700 [&>svg]:text-accent-600 dark:[&>svg]:text-accent-500 dark:[&>div:first-of-type]:text-accent-400 dark:bg-accent-500/5 text-accent-600 dark:text-accent-400 border-accent-500/20 dark:border-accent-500/10', 10 10 secondary: 11 11 'bg-base-500/10 [&>div:first-of-type]:text-base-700 [&>svg]:text-base-600 dark:[&>svg]:text-base-400 dark:[&>div:first-of-type]:text-base-300 dark:bg-base-500/5 text-base-600 dark:text-base-400 border-base-500/20 dark:border-base-500/10', 12 - red: 'bg-red-500/10 [&>div:first-of-type]:text-red-700 [&>svg]:text-red-600 dark:[&>svg]:text-red-500 dark:[&>div:first-of-type]:text-red-500 dark:bg-red-500/5 text-red-600 dark:text-red-400 border-red-500/20 dark:border-red-500/10', 12 + red: 'bg-red-500/10 [&>div:first-of-type]:text-red-700 [&>svg]:text-red-600 dark:[&>svg]:text-red-500 dark:[&>div:first-of-type]:text-red-400 dark:bg-red-500/5 text-red-600 dark:text-red-400 border-red-500/20 dark:border-red-500/10', 13 13 orange: 14 - 'bg-orange-500/10 [&>div:first-of-type]:text-orange-700 [&>svg]:text-orange-600 dark:[&>svg]:text-orange-500 dark:[&>div:first-of-type]:text-orange-500 dark:bg-orange-500/5 text-orange-600 dark:text-orange-400 border-orange-500/20 dark:border-orange-500/10', 14 + 'bg-orange-500/10 [&>div:first-of-type]:text-orange-700 [&>svg]:text-orange-600 dark:[&>svg]:text-orange-500 dark:[&>div:first-of-type]:text-orange-400 dark:bg-orange-500/5 text-orange-600 dark:text-orange-400 border-orange-500/20 dark:border-orange-500/10', 15 15 amber: 16 - 'bg-amber-500/10 [&>div:first-of-type]:text-amber-700 [&>svg]:text-amber-600 dark:[&>svg]:text-amber-500 dark:[&>div:first-of-type]:text-amber-500 dark:bg-amber-500/5 text-amber-600 dark:text-amber-400 border-amber-500/20 dark:border-amber-500/10', 16 + 'bg-amber-500/10 [&>div:first-of-type]:text-amber-700 [&>svg]:text-amber-600 dark:[&>svg]:text-amber-500 dark:[&>div:first-of-type]:text-amber-400 dark:bg-amber-500/5 text-amber-600 dark:text-amber-400 border-amber-500/20 dark:border-amber-500/10', 17 17 yellow: 18 - 'bg-yellow-500/10 [&>div:first-of-type]:text-yellow-700 [&>svg]:text-yellow-600 dark:[&>svg]:text-yellow-500 dark:[&>div:first-of-type]:text-yellow-500 dark:bg-yellow-500/5 text-yellow-600 dark:text-yellow-400 border-yellow-500/20 dark:border-yellow-500/10', 19 - lime: 'bg-lime-500/10 [&>div:first-of-type]:text-lime-700 [&>svg]:text-lime-600 dark:[&>svg]:text-lime-500 dark:[&>div:first-of-type]:text-lime-500 dark:bg-lime-500/5 text-lime-600 dark:text-lime-400 border-lime-500/20 dark:border-lime-500/10', 18 + 'bg-yellow-500/10 [&>div:first-of-type]:text-yellow-700 [&>svg]:text-yellow-600 dark:[&>svg]:text-yellow-500 dark:[&>div:first-of-type]:text-yellow-400 dark:bg-yellow-500/5 text-yellow-600 dark:text-yellow-400 border-yellow-500/20 dark:border-yellow-500/10', 19 + lime: 'bg-lime-500/10 [&>div:first-of-type]:text-lime-700 [&>svg]:text-lime-600 dark:[&>svg]:text-lime-500 dark:[&>div:first-of-type]:text-lime-400 dark:bg-lime-500/5 text-lime-600 dark:text-lime-400 border-lime-500/20 dark:border-lime-500/10', 20 20 green: 21 - 'bg-green-500/10 [&>div:first-of-type]:text-green-700 [&>svg]:text-green-600 dark:[&>svg]:text-green-500 dark:[&>div:first-of-type]:text-green-500 dark:bg-green-500/5 text-green-600 dark:text-green-400 border-green-500/20 dark:border-green-500/10', 21 + 'bg-green-500/10 [&>div:first-of-type]:text-green-700 [&>svg]:text-green-600 dark:[&>svg]:text-green-500 dark:[&>div:first-of-type]:text-green-400 dark:bg-green-500/5 text-green-600 dark:text-green-400 border-green-500/20 dark:border-green-500/10', 22 22 emerald: 23 - 'bg-emerald-500/10 [&>div:first-of-type]:text-emerald-700 [&>svg]:text-emerald-600 dark:[&>svg]:text-emerald-500 dark:[&>div:first-of-type]:text-emerald-500 dark:bg-emerald-500/5 text-emerald-600 dark:text-emerald-400 border-emerald-500/20 dark:border-emerald-500/10', 24 - teal: 'bg-teal-500/10 [&>div:first-of-type]:text-teal-700 [&>svg]:text-teal-600 dark:[&>svg]:text-teal-500 dark:[&>div:first-of-type]:text-teal-500 dark:bg-teal-500/5 text-teal-600 dark:text-teal-400 border-teal-500/20 dark:border-teal-500/10', 25 - cyan: 'bg-cyan-500/10 [&>div:first-of-type]:text-cyan-700 [&>svg]:text-cyan-600 dark:[&>svg]:text-cyan-500 dark:[&>div:first-of-type]:text-cyan-500 dark:bg-cyan-500/5 text-cyan-600 dark:text-cyan-400 border-cyan-500/20 dark:border-cyan-500/10', 26 - sky: 'bg-sky-500/10 [&>div:first-of-type]:text-sky-700 [&>svg]:text-sky-600 dark:[&>svg]:text-sky-500 dark:[&>div:first-of-type]:text-sky-500 dark:bg-sky-500/5 text-sky-600 dark:text-sky-400 border-sky-500/20 dark:border-sky-500/10', 27 - blue: 'bg-blue-500/10 [&>div:first-of-type]:text-blue-700 [&>svg]:text-blue-600 dark:[&>svg]:text-blue-500 dark:[&>div:first-of-type]:text-blue-500 dark:bg-blue-500/5 text-blue-600 dark:text-blue-400 border-blue-500/20 dark:border-blue-500/10', 23 + 'bg-emerald-500/10 [&>div:first-of-type]:text-emerald-700 [&>svg]:text-emerald-600 dark:[&>svg]:text-emerald-500 dark:[&>div:first-of-type]:text-emerald-400 dark:bg-emerald-500/5 text-emerald-600 dark:text-emerald-400 border-emerald-500/20 dark:border-emerald-500/10', 24 + teal: 'bg-teal-500/10 [&>div:first-of-type]:text-teal-700 [&>svg]:text-teal-600 dark:[&>svg]:text-teal-500 dark:[&>div:first-of-type]:text-teal-400 dark:bg-teal-500/5 text-teal-600 dark:text-teal-400 border-teal-500/20 dark:border-teal-500/10', 25 + cyan: 'bg-cyan-500/10 [&>div:first-of-type]:text-cyan-700 [&>svg]:text-cyan-600 dark:[&>svg]:text-cyan-500 dark:[&>div:first-of-type]:text-cyan-400 dark:bg-cyan-500/5 text-cyan-600 dark:text-cyan-400 border-cyan-500/20 dark:border-cyan-500/10', 26 + sky: 'bg-sky-500/10 [&>div:first-of-type]:text-sky-700 [&>svg]:text-sky-600 dark:[&>svg]:text-sky-500 dark:[&>div:first-of-type]:text-sky-400 dark:bg-sky-500/5 text-sky-600 dark:text-sky-400 border-sky-500/20 dark:border-sky-500/10', 27 + blue: 'bg-blue-500/10 [&>div:first-of-type]:text-blue-700 [&>svg]:text-blue-600 dark:[&>svg]:text-blue-500 dark:[&>div:first-of-type]:text-blue-400 dark:bg-blue-500/5 text-blue-600 dark:text-blue-400 border-blue-500/20 dark:border-blue-500/10', 28 28 indigo: 29 - 'bg-indigo-500/10 [&>div:first-of-type]:text-indigo-700 [&>svg]:text-indigo-600 dark:[&>svg]:text-indigo-500 dark:[&>div:first-of-type]:text-indigo-500 dark:bg-indigo-500/5 text-indigo-600 dark:text-indigo-400 border-indigo-500/20 dark:border-indigo-500/10', 29 + 'bg-indigo-500/10 [&>div:first-of-type]:text-indigo-700 [&>svg]:text-indigo-600 dark:[&>svg]:text-indigo-500 dark:[&>div:first-of-type]:text-indigo-400 dark:bg-indigo-500/5 text-indigo-600 dark:text-indigo-400 border-indigo-500/20 dark:border-indigo-500/10', 30 30 violet: 31 - 'bg-violet-500/10 [&>div:first-of-type]:text-violet-700 [&>svg]:text-violet-600 dark:[&>svg]:text-violet-500 dark:[&>div:first-of-type]:text-violet-500 dark:bg-violet-500/5 text-violet-600 dark:text-violet-400 border-violet-500/20 dark:border-violet-500/10', 31 + 'bg-violet-500/10 [&>div:first-of-type]:text-violet-700 [&>svg]:text-violet-600 dark:[&>svg]:text-violet-500 dark:[&>div:first-of-type]:text-violet-400 dark:bg-violet-500/5 text-violet-600 dark:text-violet-400 border-violet-500/20 dark:border-violet-500/10', 32 32 purple: 33 - 'bg-purple-500/10 [&>div:first-of-type]:text-purple-700 [&>svg]:text-purple-600 dark:[&>svg]:text-purple-500 dark:[&>div:first-of-type]:text-purple-500 dark:bg-purple-500/5 text-purple-600 dark:text-purple-400 border-purple-500/20 dark:border-purple-500/10', 33 + 'bg-purple-500/10 [&>div:first-of-type]:text-purple-700 [&>svg]:text-purple-600 dark:[&>svg]:text-purple-500 dark:[&>div:first-of-type]:text-purple-400 dark:bg-purple-500/5 text-purple-600 dark:text-purple-400 border-purple-500/20 dark:border-purple-500/10', 34 34 fuchsia: 35 - 'bg-fuchsia-500/10 [&>div:first-of-type]:text-fuchsia-700 [&>svg]:text-fuchsia-600 dark:[&>svg]:text-fuchsia-500 dark:[&>div:first-of-type]:text-fuchsia-500 dark:bg-fuchsia-500/5 text-fuchsia-600 dark:text-fuchsia-400 border-fuchsia-500/20 dark:border-fuchsia-500/10', 36 - pink: 'bg-pink-500/10 [&>div:first-of-type]:text-pink-700 [&>svg]:text-pink-600 dark:[&>svg]:text-pink-500 dark:[&>div:first-of-type]:text-pink-500 dark:bg-pink-500/5 text-pink-600 dark:text-pink-400 border-pink-500/20 dark:border-pink-500/10', 37 - rose: 'bg-rose-500/10 [&>div:first-of-type]:text-rose-700 [&>svg]:text-rose-600 dark:[&>svg]:text-rose-500 dark:[&>div:first-of-type]:text-rose-500 dark:bg-rose-500/5 text-rose-600 dark:text-rose-400 border-rose-500/20 dark:border-rose-500/10' 35 + 'bg-fuchsia-500/10 [&>div:first-of-type]:text-fuchsia-700 [&>svg]:text-fuchsia-600 dark:[&>svg]:text-fuchsia-500 dark:[&>div:first-of-type]:text-fuchsia-400 dark:bg-fuchsia-500/5 text-fuchsia-600 dark:text-fuchsia-400 border-fuchsia-500/20 dark:border-fuchsia-500/10', 36 + pink: 'bg-pink-500/10 [&>div:first-of-type]:text-pink-700 [&>svg]:text-pink-600 dark:[&>svg]:text-pink-500 dark:[&>div:first-of-type]:text-pink-400 dark:bg-pink-500/5 text-pink-600 dark:text-pink-400 border-pink-500/20 dark:border-pink-500/10', 37 + rose: 'bg-rose-500/10 [&>div:first-of-type]:text-rose-700 [&>svg]:text-rose-600 dark:[&>svg]:text-rose-500 dark:[&>div:first-of-type]:text-rose-400 dark:bg-rose-500/5 text-rose-600 dark:text-rose-400 border-rose-500/20 dark:border-rose-500/10' 38 38 } 39 39 }, 40 40 defaultVariants: {
+26
src/lib/components/base/copy-code-button/AddCopyCodeButtons.svelte
··· 1 + <script lang="ts"> 2 + import { afterNavigate } from "$app/navigation"; 3 + import { onMount } from "svelte"; 4 + import CopyCodeButton from "./CopyCodeButton.svelte"; 5 + 6 + onMount(() => { 7 + addButtons(); 8 + }); 9 + 10 + afterNavigate(() => { 11 + addButtons(); 12 + }); 13 + 14 + let codeblocks: HTMLElement[] = $state([]); 15 + 16 + function addButtons() { 17 + codeblocks = Array.from(document.querySelectorAll("pre")); 18 + for (let codeblock of codeblocks) { 19 + codeblock.classList.add("group", "relative"); 20 + } 21 + } 22 + </script> 23 + 24 + {#each codeblocks as codeblock} 25 + <CopyCodeButton codeblock={codeblock} /> 26 + {/each}
+69
src/lib/components/base/copy-code-button/CopyCodeButton.svelte
··· 1 + <script lang="ts"> 2 + import { afterNavigate, onNavigate } from '$app/navigation'; 3 + import { cn } from '$lib'; 4 + import { Portal } from 'bits-ui'; 5 + import { onMount } from 'svelte'; 6 + 7 + let { codeblock } = $props(); 8 + 9 + let copied = $state(false); 10 + 11 + async function clickedCopy() { 12 + let text = codeblock.innerText; 13 + 14 + await navigator.clipboard.writeText(text); 15 + 16 + copied = true; 17 + setTimeout(() => { 18 + copied = false; 19 + }, 2000); 20 + } 21 + </script> 22 + 23 + <Portal to={codeblock}> 24 + {#if !copied} 25 + <button 26 + class={cn( 27 + 'not-prose focus-visible:outline-base-600 dark:focus-visible:outline-base-400 opacity-0 focus-visible:opacity-100 focus-visible:outline-2 focus-visible:outline-offset-2', 28 + 'bg-base-200 inline-flex size-8 items-center justify-center p-1 transition-opacity duration-150 group-hover:opacity-100', 29 + 'dark:bg-base-800 border-base-400 dark:border-base-700 dark:hover:bg-base-700 hover:bg-base-300 absolute top-3 right-3 rounded-2xl border' 30 + )} 31 + onclick={clickedCopy} 32 + > 33 + <svg 34 + xmlns="http://www.w3.org/2000/svg" 35 + fill="none" 36 + viewBox="0 0 24 24" 37 + stroke-width="1.5" 38 + stroke="currentColor" 39 + class="size-4.5" 40 + > 41 + <path 42 + stroke-linecap="round" 43 + stroke-linejoin="round" 44 + d="M8.25 7.5V6.108c0-1.135.845-2.098 1.976-2.192.373-.03.748-.057 1.123-.08M15.75 18H18a2.25 2.25 0 0 0 2.25-2.25V6.108c0-1.135-.845-2.098-1.976-2.192a48.424 48.424 0 0 0-1.123-.08M15.75 18.75v-1.875a3.375 3.375 0 0 0-3.375-3.375h-1.5a1.125 1.125 0 0 1-1.125-1.125v-1.5A3.375 3.375 0 0 0 6.375 7.5H5.25m11.9-3.664A2.251 2.251 0 0 0 15 2.25h-1.5a2.251 2.251 0 0 0-2.15 1.586m5.8 0c.065.21.1.433.1.664v.75h-6V4.5c0-.231.035-.454.1-.664M6.75 7.5H4.875c-.621 0-1.125.504-1.125 1.125v12c0 .621.504 1.125 1.125 1.125h9.75c.621 0 1.125-.504 1.125-1.125V16.5a9 9 0 0 0-9-9Z" 45 + /> 46 + </svg> 47 + 48 + <span class="sr-only">copy code</span> 49 + </button> 50 + {:else} 51 + <div 52 + class={cn( 53 + 'bg-accent-500/10 border-accent-500/20 text-accent-600 dark:text-accent-400 absolute top-3 right-3', 54 + 'inline-flex size-8 items-center justify-center rounded-2xl border p-1 opacity-100 transition-opacity duration-500' 55 + )} 56 + > 57 + <svg 58 + xmlns="http://www.w3.org/2000/svg" 59 + fill="none" 60 + viewBox="0 0 24 24" 61 + stroke-width="1.5" 62 + stroke="currentColor" 63 + class="size-4.5" 64 + > 65 + <path stroke-linecap="round" stroke-linejoin="round" d="m4.5 12.75 6 6 9-13.5" /> 66 + </svg> 67 + </div> 68 + {/if} 69 + </Portal>
+6 -2
src/lib/components/base/prose/Prose.svelte
··· 1 1 <script lang="ts"> 2 2 let { children } = $props(); 3 3 4 + import AddCopyCodeButtons from '$lib/components/base/copy-code-button/AddCopyCodeButtons.svelte'; 5 + 4 6 // this is fucking hacky, todo fix that 5 7 </script> 6 8 7 9 <div 8 - class="prose prose-base prose-a:no-underline prose-a:text-accent-600 dark:prose-a:text-accent-500 dark:hidden w-full" 10 + class="prose prose-base prose-a:no-underline prose-a:text-accent-600 dark:prose-a:text-accent-500 dark:hidden w-full prose-pre:rounded-2xl" 9 11 > 10 12 {@render children?.()} 11 13 </div> 12 14 <div 13 - class="prose prose-base-dark dark:prose-invert prose-a:no-underline prose-a:text-accent-600 dark:prose-a:text-accent-500 hidden dark:block w-full" 15 + class="prose prose-base-dark dark:prose-invert prose-a:no-underline prose-a:text-accent-600 dark:prose-a:text-accent-500 hidden dark:block w-full prose-pre:rounded-2xl" 14 16 > 15 17 {@render children?.()} 16 18 </div> 19 + 20 + <AddCopyCodeButtons /> 17 21 18 22 <style> 19 23 .prose-base {
+19 -28
src/lib/components/base/tooltip/tooltip.svelte
··· 1 1 <script lang="ts"> 2 2 import { Tooltip } from 'bits-ui'; 3 3 import { type Snippet } from 'svelte'; 4 - import { buttonVariants, type ButtonSize, type ButtonVariant } from '../button'; 5 4 import { TooltipContent } from '.'; 6 - import { cn } from '$lib/utils'; 7 5 8 6 type Props = Tooltip.RootProps & { 9 - trigger?: Snippet; 10 - 11 - triggerText?: string; 12 - triggerVariant?: ButtonVariant; 13 - triggerSize?: ButtonSize; 14 - triggerClass?: string; 15 - 16 7 withContext?: boolean; 17 8 18 9 triggerProps?: Tooltip.TriggerProps; 19 - }; 10 + 11 + content?: Snippet; 12 + text?: string; 13 + } & Tooltip.TriggerProps; 20 14 21 15 let { 22 16 open = $bindable(false), 23 - children, 24 - trigger, 25 - triggerText, 26 - triggerVariant = 'primary', 27 - triggerSize = 'default', 28 - triggerClass, 17 + child: myChild, 29 18 30 19 withContext = false, 31 20 32 21 triggerProps = {}, 22 + 23 + content, 24 + text, 33 25 ...restProps 34 26 }: Props = $props(); 35 27 </script> 36 28 37 29 {#snippet root()} 38 30 <Tooltip.Root bind:open {...restProps}> 39 - {#if trigger} 40 - <Tooltip.Trigger {...triggerProps}> 41 - {@render trigger()} 42 - </Tooltip.Trigger> 43 - {:else} 44 - <Tooltip.Trigger 45 - class={cn(buttonVariants({ variant: triggerVariant, size: triggerSize }), triggerClass)} 46 - > 47 - {triggerText} 48 - </Tooltip.Trigger> 49 - {/if} 31 + <Tooltip.Trigger {...triggerProps}> 32 + {#snippet child({ props })} 33 + {@render myChild?.({ props })} 34 + {/snippet} 35 + </Tooltip.Trigger> 36 + 50 37 <Tooltip.Portal> 51 38 <TooltipContent sideOffset={10}> 52 - {@render children?.()} 39 + {#if content} 40 + {@render content()} 41 + {:else} 42 + {text} 43 + {/if} 53 44 </TooltipContent> 54 45 </Tooltip.Portal> 55 46 </Tooltip.Root>
+3
src/routes/components/3d/model-picker/+page.svelte
··· 2 2 import { base } from '$app/paths'; 3 3 import ModalPicker from '$lib/components/3d/model-picker/ModalPicker.svelte'; 4 4 import Button from '$lib/components/base/button/Button.svelte'; 5 + import Subheading from '$lib/components/base/heading/Subheading.svelte'; 5 6 import { toast } from 'svelte-sonner'; 6 7 7 8 let open = $state(false); 8 9 </script> 10 + 11 + <Subheading class="mb-4">Model Picker</Subheading> 9 12 10 13 <ModalPicker 11 14 items={[
+4 -1
src/routes/components/base/accordion/Accordion.md
··· 1 1 <script lang="ts"> 2 2 import { Accordion, AccordionItem } from '$lib/components/base/accordion'; 3 - import Subheading from '$lib/components/base/heading/Subheading.svelte'; 4 3 </script> 5 4 6 5 # Accordion ··· 19 18 ## Usage 20 19 21 20 ```svelte 21 + <script lang="ts"> 22 + import { Accordion, AccordionItem } from 'fox-ui-svelte'; 23 + </script> 24 + 22 25 <Accordion type="single"> 23 26 <AccordionItem value="item-1" title="Is it accessible?"> 24 27 Yes. It adheres to the WAI-ARIA design pattern.
+4 -4
src/routes/components/base/alert/Alert.md
··· 1 1 <script> 2 - import { Subheading } from '$lib/components/base/heading'; 3 - import { Text } from '$lib/components/base/text'; 4 2 import { Alert, AlertDescription, AlertTitle } from '$lib/components/base/alert'; 5 3 </script> 6 4 7 5 # Alert 8 6 9 7 ## Examples 10 - 11 - Default Alert 12 8 13 9 <Alert class="mb-2"> 14 10 <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24" fill="currentColor"> ··· 65 61 ## Usage 66 62 67 63 ```svelte 64 + <script> 65 + import { Alert } from 'fox-ui-svelte'; 66 + </script> 67 + 68 68 <Alert title="Alert Title" type="info"> 69 69 <span>Alert Description</span> 70 70 </Alert>
+20
src/routes/components/base/avatar/Avatar.md
··· 42 42 ## Usage 43 43 44 44 ```svelte 45 + <script> 46 + import { Avatar, AvatarGroup } from 'fox-ui-svelte'; 47 + </script> 48 + 45 49 <Avatar 46 50 src="https://github.com/flo-bit.png" 47 51 alt="flo-bit" 48 52 fallback="FB" 49 53 /> 54 + 55 + <AvatarGroup 56 + users={[ 57 + { 58 + src: 'https://github.com/flo-bit.png', 59 + alt: 'flo-bit', 60 + fallback: 'FB' 61 + }, 62 + { 63 + src: 'https://github.com/rich-harris.png', 64 + alt: 'rich-harris', 65 + fallback: 'RH' 66 + } 67 + ]} 68 + /> 69 + 50 70 ```
+4
src/routes/components/base/badge/Badge.md
··· 84 84 ## Usage 85 85 86 86 ```svelte 87 + <script> 88 + import { Badge } from 'fox-ui-svelte'; 89 + </script> 90 + 87 91 <Badge size="sm" variant="primary"> 88 92 Badge 89 93 </Badge>
+4
src/routes/components/base/box/Box.md
··· 12 12 ## Usage 13 13 14 14 ```svelte 15 + <script> 16 + import { Box } from 'fox-ui-svelte'; 17 + </script> 18 + 15 19 <Box class="text-sm"> 16 20 This is a box, put your stuff here. 17 21 </Box>
+4
src/routes/components/base/button/Button.md
··· 178 178 ## Usage 179 179 180 180 ```svelte 181 + <script> 182 + import { Button } from 'fox-ui-svelte'; 183 + </script> 184 + 181 185 <Button variant="primary" size="sm"> 182 186 Button 183 187 </Button>
+7 -3
src/routes/components/base/cards/Cards.md
··· 52 52 ## Usage 53 53 54 54 ```svelte 55 + <script> 56 + import { ImageCard } from 'fox-ui-svelte'; 57 + </script> 58 + 55 59 <ImageCard 56 - src={nature1} 60 + src={'/image.jpg'} 57 61 alt="" 58 - title="Best places to visit" 59 - description="Hello World!" 62 + title="Card title" 63 + description="Card description" 60 64 href="#" 61 65 /> 62 66 ```
+4
src/routes/components/base/chat-bubble/ChatBubble.md
··· 41 41 ## Usage 42 42 43 43 ```svelte 44 + <script> 45 + import { ChatBubble } from 'fox-ui-svelte'; 46 + </script> 47 + 44 48 <ChatBubble side="right" variant="secondary"> 45 49 <p>Hello there</p> 46 50 </ChatBubble>
+7
src/routes/components/base/checkbox/Checkbox.md
··· 40 40 ## Usage 41 41 42 42 ```svelte 43 + <script> 44 + import { Checkbox } from 'fox-ui-svelte'; 45 + 46 + let checked = $state(false); 47 + </script> 48 + 43 49 <Checkbox 44 50 sizeVariant="sm" 45 51 variant="primary" 52 + bind:checked 46 53 /> 47 54 ``` 48 55
+8
src/routes/components/base/head/Head.md
··· 1 1 # Head 2 2 3 + Sets title, description, open graph image, url and emoji favicon. 4 + 5 + It's recommended to add this to your root layout. 6 + 3 7 ## Usage 4 8 5 9 ```svelte 10 + <script> 11 + import { Head } from 'fox-ui-svelte'; 12 + </script> 13 + 6 14 <Head 7 15 title="Website Title" 8 16 description="Website Description"
+14 -2
src/routes/components/base/image/Image.md
··· 13 13 14 14 <ImageContainer src={cute} alt="Such a cute animal" containerClasses="not-prose max-w-64" /> 15 15 16 - Overlay theme color 16 + Overlay theme color: 17 17 18 18 <ImageContainer src={cute2} alt="Another cute animal" useThemeColor={true} containerClasses="max-w-44 not-prose" /> 19 19 20 - Show normal image on hover 20 + Show normal image on hover: 21 + 21 22 <ImageContainer 22 23 src={cute2} 23 24 alt="Another cute animal" ··· 29 30 ## Usage 30 31 31 32 ```svelte 33 + <script> 34 + import { ImageContainer } from 'fox-ui-svelte'; 35 + </script> 36 + 32 37 <ImageContainer 33 38 src="/image.jpg" 34 39 alt="Alt tag" 40 + /> 41 + 42 + <ImageContainer 43 + src="/image.jpg" 44 + alt="Alt tag" 45 + useThemeColor 46 + showNormalOnHover 35 47 /> 36 48 ``` 37 49
+7 -1
src/routes/components/base/input/Input.md
··· 27 27 ## Usage 28 28 29 29 ```svelte 30 + <script> 31 + import { Input } from 'fox-ui-svelte'; 32 + 33 + let value = $state(''); 34 + </script> 35 + 30 36 <Input 31 37 sizeVariant="sm" 32 - placeholder="Enter text here (small)" 38 + placeholder="Enter text here" 33 39 bind:value={value} 34 40 /> 35 41 ```
+10
src/routes/components/base/modal/Modal.md
··· 46 46 47 47 ```svelte 48 48 <script> 49 + import { Modal, Button } from 'fox-ui-svelte'; 50 + 49 51 let open = $state(false); 52 + 53 + function yesClicked() { 54 + console.log('yes'); 55 + } 56 + 57 + function noClicked() { 58 + console.log('no'); 59 + } 50 60 </script> 51 61 52 62 <Modal bind:open title="This is the default modal" />
+2
src/routes/components/base/number-input/NumberInput.md
··· 13 13 14 14 ```svelte 15 15 <script> 16 + import { NumberInput } from 'fox-ui-svelte'; 17 + 16 18 let value = $state(0); 17 19 </script> 18 20
+4
src/routes/components/base/prose/Prose.md
··· 18 18 ## Usage 19 19 20 20 ```svelte 21 + <script> 22 + import Prose from 'fox-ui-svelte'; 23 + </script> 24 + 21 25 <Prose> 22 26 <h1>Prose</h1> 23 27
+6 -1
src/routes/components/base/scroll-area/ScrollArea.md
··· 47 47 ## Usage 48 48 49 49 ```svelte 50 + <script> 51 + import { ScrollArea } from 'fox-ui-svelte'; 52 + </script> 53 + 50 54 <ScrollArea class="h-52 w-96"> 51 55 <div> 52 56 Your content here 53 57 </div> 54 - </ScrollArea> 58 + </ScrollArea> 59 + ```
+2
src/routes/components/base/slider/Slider.md
··· 15 15 16 16 ```svelte 17 17 <script> 18 + import { Slider } from 'fox-ui-svelte'; 19 + 18 20 let value = $state(50); 19 21 </script> 20 22
+13 -3
src/routes/components/base/sonner/Sonner.md
··· 41 41 42 42 ## Usage 43 43 44 + In your root layout: 45 + 44 46 ```svelte 45 47 <script> 46 - import { Toaster, Button, toast } from 'fox-ui-kit'; 48 + import { Toaster } from 'fox-ui-svelte'; 49 + </script> 50 + 51 + <Toaster /> 52 + ``` 53 + 54 + In your page: 55 + 56 + ```svelte 57 + <script> 58 + import { Button, toast } from 'fox-ui-svelte'; 47 59 48 60 function handleClick() { 49 61 toast('Hello there', { description: 'General Kenobi!' }); 50 62 } 51 63 </script> 52 - 53 - <Toaster /> 54 64 55 65 <Button onclick={handleClick}> 56 66 Default
+8 -1
src/routes/components/base/switch/Switch.md
··· 19 19 <Switch disabled /> 20 20 </div> 21 21 22 - <Text class="mt-4 mb-2">With Label</Text> 22 + With Label 23 + 23 24 <div class="flex items-center space-x-2"> 24 25 <Switch id="terms-switch" aria-labelledby="terms-switch-label" /> 25 26 <Label ··· 34 35 ## Usage 35 36 36 37 ```svelte 38 + <script> 39 + import { Switch } from 'fox-ui-svelte'; 40 + 41 + let checked = $state(false); 42 + </script> 43 + 37 44 <Switch bind:checked /> 38 45 ```
+12
src/routes/components/base/textarea/Textarea.md
··· 23 23 <Textarea placeholder="Enter text here (default)" variant="secondary" /> 24 24 <Textarea placeholder="Enter text here (large)" variant="secondary" sizeVariant="lg" /> 25 25 </div> 26 + 27 + ## Usage 28 + 29 + ```svelte 30 + <script> 31 + import { Textarea } from 'fox-ui-svelte'; 32 + 33 + let value = $state(''); 34 + </script> 35 + 36 + <Textarea placeholder="Enter text here" bind:value /> 37 + ```
+23 -14
src/routes/components/base/tooltip/Tooltip.md
··· 2 2 import { Subheading } from '$lib/components/base/heading'; 3 3 import { Tooltip } from '$lib/components/base/tooltip'; 4 4 import { Text } from '$lib/components/base/text'; 5 + import { Button } from '$lib/components/base/button'; 6 + import { toast } from 'svelte-sonner'; 7 + 8 + function handleClick() { 9 + toast.error('Don\'t click, just hover!') 10 + } 5 11 </script> 6 12 7 13 # Tooltip 8 14 9 15 ## Example 10 16 11 - Primary 12 - 13 17 <div class="flex w-full flex-col items-start gap-2 py-12"> 14 - <Tooltip triggerText="Hover me" triggerVariant="primary" withContext>Hello there!</Tooltip> 18 + <Tooltip text="Hello there!" withContext> 19 + {#snippet child({ props })} 20 + <Button {...props} onclick={handleClick}>Hover me</Button> 21 + {/snippet} 22 + </Tooltip> 15 23 </div> 16 24 17 - Secondary 25 + ## Usage 18 26 19 - <div class="flex w-full flex-col items-start gap-2 py-12"> 20 - <Tooltip triggerText="Hover me" triggerVariant="secondary" withContext>Hello there!</Tooltip> 21 - </div> 27 + ```svelte 28 + <script> 29 + import { Tooltip, Button } from 'fox-ui-svelte'; 22 30 23 - ## Usage 31 + function handleClick() { 32 + console.log('clicked') 33 + } 34 + </script> 24 35 25 - ```svelte 26 - <Tooltip 27 - triggerText="Hover me" 28 - triggerVariant="primary" 29 - withContext> 30 - Hello there! 36 + <Tooltip text="Hello there!" withContext> 37 + {#snippet child({ props })} 38 + <Button {...props} onclick={handleClick}>Hover me</Button> 39 + {/snippet} 31 40 </Tooltip> 32 41 ``` 33 42
+40 -3
src/routes/docs/philosophy/Philosophy.md
··· 15 15 16 16 ## Two colors 17 17 18 - Still all apps looking the same is kinda boring, so there are some easy and quick ways to customize all components. 18 + Still all apps looking the same is kinda boring, so there are is one easy and quick way to customize all components. 19 19 20 - The main idea is having two colors: 20 + The main idea is having two colors (in all tailwind shades from 50 up to 950): 21 21 22 22 - base color (usually one of the 5 tailwind gray tones) 23 23 - accent color (usually one of the not-gray tailwind colors) 24 24 25 - You can try it out by setting the current theme colors in the navbar for this documentation site. 25 + You can try it out by setting the current theme colors in the navbar for this documentation site. 26 + 27 + ## Lots of components 28 + 29 + While currently only the base components are visible, there are lots of components in the pipeline. 30 + The aim is to have a component library that has lots of components that are useful for building webapps/websites/games, all in a consistent style/theme. 31 + 32 + See here for a few examples of work in progress components (some may be partially broken): 33 + 34 + 35 + ### graphs 36 + 37 + - [ring chart](/ui-kit/components/graphs/ring-chart/) 38 + - [heatmap](/ui-kit/components/graphs/heatmap/) 39 + - [line chart](/ui-kit/components/graphs/line-graph/) 40 + 41 + ### extras 42 + 43 + - [color picker](/ui-kit/components/extras/color-picker/) 44 + - [excalidraw](/ui-kit/components/extras/excalidraw/) 45 + - [quote](/ui-kit/components/extras/quote/) 46 + - [phone](/ui-kit/components/extras/phone/) 47 + - [timer](/ui-kit/components/extras/timer/) 48 + 49 + ### social 50 + 51 + - [github-corner](/ui-kit/components/social/github-corner/) 52 + - [star rating](/ui-kit/components/social/star-rating/) 53 + - [social media post](/ui-kit/components/social/post/) 54 + 55 + ### 3d 56 + 57 + - [depth 3d](/ui-kit/components/3d/depth-3d/) 58 + - [model-picker](/ui-kit/components/3d/model-picker/) 59 + - [voxel-art](/ui-kit/components/3d/voxel-art/) 60 + 61 + 62 + If you have any suggestions for components, please open an issue on [github](https://github.com/flo-bit/ui-kit/issues).