├── LICENSE ├── README.md ├── biome.json └── packages └── frameworks ├── react ├── .gitignore ├── README.md ├── index.html ├── package-lock.json ├── package.json ├── postcss.config.js ├── public │ └── vite.svg ├── src │ ├── App.tsx │ ├── components │ │ └── ui │ │ │ ├── accordion.tsx │ │ │ ├── alert-dialog.tsx │ │ │ ├── alert.tsx │ │ │ ├── avatar.tsx │ │ │ ├── badge.tsx │ │ │ ├── button.tsx │ │ │ ├── checkbox.tsx │ │ │ ├── dialog.tsx │ │ │ ├── input.tsx │ │ │ └── label.tsx │ ├── examples │ │ ├── accordion.example.tsx │ │ ├── alert-dialog.example.tsx │ │ ├── alert.example.tsx │ │ ├── avatar.example.tsx │ │ ├── badge.example.tsx │ │ ├── button.example.tsx │ │ ├── checkbox.example.tsx │ │ ├── dialog.example.tsx │ │ ├── input.example.tsx │ │ └── label.example.tsx │ ├── index.css │ ├── lib │ │ └── utils.ts │ ├── main.tsx │ └── vite-env.d.ts ├── tailwind.config.js ├── tsconfig.json └── vite.config.ts ├── solid ├── .gitignore ├── README.md ├── index.html ├── package-lock.json ├── package.json ├── postcss.config.js ├── src │ ├── App.tsx │ ├── components │ │ └── ui │ │ │ ├── accordion.tsx │ │ │ ├── alert-dialog.tsx │ │ │ ├── alert.tsx │ │ │ ├── avatar.tsx │ │ │ ├── badge.tsx │ │ │ ├── breadcrumb.tsx │ │ │ ├── button.tsx │ │ │ ├── card.tsx │ │ │ ├── carousel.tsx │ │ │ ├── checkbox.tsx │ │ │ ├── clipboard.tsx │ │ │ ├── collapsible.tsx │ │ │ ├── dialog.tsx │ │ │ ├── dropdown-menu.tsx │ │ │ ├── hover-card.tsx │ │ │ ├── input.tsx │ │ │ ├── label.tsx │ │ │ ├── radio-group.tsx │ │ │ ├── select.tsx │ │ │ ├── sheet.tsx │ │ │ ├── skeleton.tsx │ │ │ ├── slider.tsx │ │ │ ├── table.tsx │ │ │ ├── tabs.tsx │ │ │ └── tooltip.tsx │ ├── examples │ │ ├── accordion.example.tsx │ │ ├── alert-dialog.example.tsx │ │ ├── alert.example.tsx │ │ ├── avatar.example.tsx │ │ ├── badge.example.tsx │ │ ├── breadcrumb.example.tsx │ │ ├── button.example.tsx │ │ ├── card.example.tsx │ │ ├── checkbox.example.tsx │ │ ├── clipboard.example.tsx │ │ ├── collapsible.example.tsx │ │ ├── dialog.example.tsx │ │ ├── dropdown-menu.example.tsx │ │ ├── hover-card.example.tsx │ │ ├── input.example.tsx │ │ ├── label.example.tsx │ │ ├── radio-group.example.tsx │ │ ├── select.example.tsx │ │ ├── sheet.example.tsx │ │ ├── skeleton.example.tsx │ │ ├── slider.example.tsx │ │ ├── table.example.tsx │ │ ├── tabs.example.tsx │ │ └── tooltip.example.tsx │ ├── index.css │ ├── index.tsx │ ├── lib │ │ └── utils.ts │ └── logo.svg ├── tailwind.config.js ├── tsconfig.json └── vite.config.ts └── vue ├── .gitignore ├── .vscode └── extensions.json ├── README.md ├── index.html ├── package-lock.json ├── package.json ├── postcss.config.js ├── public └── vite.svg ├── src ├── App.vue ├── components │ └── ui │ │ └── Accordion.vue ├── main.js └── style.css ├── tailwind.config.js └── vite.config.js /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2024 Alex Whitmore 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## SolidJS UI Library 2 | 3 | A beautiful and accessible UI component library based on shadcn-ui and built with SolidJS, ArkUI, and Tailwind. 4 | 5 | Screenshot 2024-02-26 at 6 29 37 PM 6 | 7 | > [!WARNING] 8 | > This is an early-stage component library and is subject to significant changes. Please use with caution! 9 | 10 | ## Documentation 11 | 12 | The documentation is a WIP and will be updated here when ready. 13 | 14 | ## Progress 15 | 16 | | Component | Solid | React | Vue | 17 | |---------------- |:-----:|:-----:|:---:| 18 | | Accordion | ✅ | ✅ | | 19 | | Alert | ✅ | ✅ | | 20 | | Alert Dialog | ✅ | ✅ | | 21 | | Aspect Ratio | | | | 22 | | Avatar | ✅ | ✅ | | 23 | | Badge | ✅ | ✅ | | 24 | | Breadcrumb | ✅ | | | 25 | | Button | ✅ | ✅ | | 26 | | Calendar | | | | 27 | | Card | ✅ | | | 28 | | Carousel | | | | 29 | | Checkbox | ✅ | | | 30 | | Collapsible | ✅ | | | 31 | | Combobox | | | | 32 | | Command | | | | 33 | | Context Menu | | | | 34 | | Data Table | | | | 35 | | Date Picker | | | | 36 | | Dialog | ✅ | ✅ | | 37 | | Drawer | | | | 38 | | Dropdown Menu | ✅ | | | 39 | | Form | | | | 40 | | Hover Card | ✅ | | | 41 | | Input | ✅ | ✅ | | 42 | | Input OTP | | | | 43 | | Label | ✅ | ✅ | | 44 | | Menubar | | | | 45 | | Navigation Menu | | | | 46 | | Pagination | | | | 47 | | Popover | | | | 48 | | Progress | | | | 49 | | Radio Group | ✅ | | | 50 | | Resizable | | | | 51 | | Scroll Area | | | | 52 | | Select | ✅ | | | 53 | | Separator | | | | 54 | | Sheet | ✅ | | | 55 | | Skeleton | ✅ | | | 56 | | Slider | | | | 57 | | Sonner | | | | 58 | | Switch | | | | 59 | | Table | ✅ | | | 60 | | Tabs | ✅ | | | 61 | | Text Area | | | | 62 | | Toast | | | | 63 | | Toggle | | | | 64 | | Toggle Group | | | | 65 | | Tooltip | ✅ | | | 66 | 67 | | Additional Components | Solid | React | Vue | 68 | |------------------------ |:-----:|:-----:|:---:| 69 | | Clipboard | ✅ | | | 70 | 71 | 72 | ## Contributing 73 | 74 | If this project sounds like something you'd like to help out with, feel free to reach out on [Twitter](https://twitter.com/theAlexWhitmore)! 75 | 76 | ## License 77 | 78 | Licensed under the [MIT license](https://github.com/alexwhitmore/solidjs-ui/tree/main?tab=MIT-1-ov-file#readme) 79 | -------------------------------------------------------------------------------- /biome.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://biomejs.dev/schemas/1.5.3/schema.json", 3 | "organizeImports": { 4 | "enabled": true 5 | }, 6 | "javascript": { 7 | "formatter": { 8 | "enabled": true, 9 | "indentStyle": "space", 10 | "indentWidth": 2, 11 | "lineWidth": 100, 12 | "quoteStyle": "single", 13 | "semicolons": "asNeeded", 14 | "trailingComma": "all" 15 | } 16 | }, 17 | "json": { 18 | "formatter": { 19 | "enabled": true, 20 | "indentStyle": "space", 21 | "indentWidth": 2 22 | } 23 | }, 24 | "linter": { 25 | "enabled": true, 26 | "rules": { 27 | "recommended": true, 28 | "suspicious": { 29 | "noArrayIndexKey": "off" 30 | } 31 | } 32 | } 33 | } -------------------------------------------------------------------------------- /packages/frameworks/react/.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | -------------------------------------------------------------------------------- /packages/frameworks/react/README.md: -------------------------------------------------------------------------------- 1 | # React + TypeScript + Vite 2 | 3 | This template provides a minimal setup to get React working in Vite with HMR and some ESLint rules. 4 | 5 | Currently, two official plugins are available: 6 | 7 | - [@vitejs/plugin-react](https://github.com/vitejs/vite-plugin-react/blob/main/packages/plugin-react/README.md) uses [Babel](https://babeljs.io/) for Fast Refresh 8 | - [@vitejs/plugin-react-swc](https://github.com/vitejs/vite-plugin-react-swc) uses [SWC](https://swc.rs/) for Fast Refresh 9 | 10 | ## Expanding the ESLint configuration 11 | 12 | If you are developing a production application, we recommend updating the configuration to enable type aware lint rules: 13 | 14 | - Configure the top-level `parserOptions` property like this: 15 | 16 | ```js 17 | export default { 18 | // other rules... 19 | parserOptions: { 20 | ecmaVersion: 'latest', 21 | sourceType: 'module', 22 | project: ['./tsconfig.json', './tsconfig.node.json'], 23 | tsconfigRootDir: __dirname, 24 | }, 25 | } 26 | ``` 27 | 28 | - Replace `plugin:@typescript-eslint/recommended` to `plugin:@typescript-eslint/recommended-type-checked` or `plugin:@typescript-eslint/strict-type-checked` 29 | - Optionally add `plugin:@typescript-eslint/stylistic-type-checked` 30 | - Install [eslint-plugin-react](https://github.com/jsx-eslint/eslint-plugin-react) and add `plugin:react/recommended` & `plugin:react/jsx-runtime` to the `extends` list 31 | -------------------------------------------------------------------------------- /packages/frameworks/react/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Vite + React + TS 8 | 9 | 10 |
11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /packages/frameworks/react/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react", 3 | "private": true, 4 | "version": "0.0.0", 5 | "scripts": { 6 | "dev": "vite", 7 | "build": "tsc && vite build", 8 | "lint": "eslint . --ext ts,tsx --report-unused-disable-directives --max-warnings 0", 9 | "preview": "vite preview" 10 | }, 11 | "dependencies": { 12 | "@ark-ui/react": "^2.2.3", 13 | "class-variance-authority": "^0.7.0", 14 | "clsx": "^2.1.0", 15 | "lucide-react": "^0.344.0", 16 | "react": "^18.2.0", 17 | "react-dom": "^18.2.0", 18 | "tailwind-merge": "^2.2.1", 19 | "tailwindcss-animate": "^1.0.7" 20 | }, 21 | "devDependencies": { 22 | "@types/react": "^18.2.56", 23 | "@types/react-dom": "^18.2.19", 24 | "@typescript-eslint/eslint-plugin": "^7.0.2", 25 | "@typescript-eslint/parser": "^7.0.2", 26 | "@vitejs/plugin-react": "^4.2.1", 27 | "autoprefixer": "^10.4.18", 28 | "eslint": "^8.56.0", 29 | "eslint-plugin-react-hooks": "^4.6.0", 30 | "eslint-plugin-react-refresh": "^0.4.5", 31 | "install": "^0.13.0", 32 | "npm": "^10.5.0", 33 | "postcss": "^8.4.35", 34 | "tailwindcss": "^3.4.1", 35 | "typescript": "^5.2.2", 36 | "vite": "^5.1.4" 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /packages/frameworks/react/postcss.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | plugins: { 3 | tailwindcss: {}, 4 | autoprefixer: {}, 5 | }, 6 | }; 7 | -------------------------------------------------------------------------------- /packages/frameworks/react/public/vite.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/App.tsx: -------------------------------------------------------------------------------- 1 | import Example from './examples/avatar.example' 2 | import { TreeView } from '@ark-ui/react' 3 | import { ChevronDown } from 'lucide-react' 4 | 5 | function App() { 6 | // return 7 | return ( 8 |
9 | 10 | Introduction 11 | 12 | 13 | 14 | 15 | 16 | 17 | 2.0 18 | 19 | 20 | 24 | 2.2 25 | 26 | 30 | 2.2 31 | 32 | 33 | 34 | 35 | 36 |
37 | ) 38 | } 39 | 40 | export default App 41 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/components/ui/accordion.tsx: -------------------------------------------------------------------------------- 1 | import type { CSSProperties } from 'react' 2 | import React, { useRef, useEffect, useState } from 'react' 3 | import { 4 | Accordion as ArkAccordion, 5 | type AccordionItemProps, 6 | type AccordionItemTriggerProps, 7 | type AccordionItemContentProps, 8 | } from '@ark-ui/react' 9 | import { ChevronDown } from 'lucide-react' 10 | import { cn } from '../../lib/utils' 11 | 12 | const Accordion = ArkAccordion.Root 13 | 14 | const AccordionItem = React.forwardRef< 15 | React.ElementRef, 16 | AccordionItemProps 17 | >((props, ref) => { 18 | const { className, ...restProps } = props 19 | return 20 | }) 21 | AccordionItem.displayName = 'AccordionItem' 22 | 23 | const AccordionTrigger = React.forwardRef< 24 | React.ElementRef, 25 | AccordionItemTriggerProps 26 | >(({ className, children, ...props }, ref) => ( 27 |
28 | svg]:rotate-180', 32 | className, 33 | )} 34 | {...props} 35 | > 36 | {children} 37 | 38 | 39 |
40 | )) 41 | AccordionTrigger.displayName = 'AccordionTrigger' 42 | 43 | const AccordionContent: React.FC = ({ id, className, children }) => { 44 | const [rect, setRect] = useState<{ height: number; width: number }>({ 45 | height: 0, 46 | width: 0, 47 | }) 48 | const contentRef = useRef(null) 49 | 50 | useEffect(() => { 51 | const handler = (entries: ResizeObserverEntry[]) => { 52 | const { height } = entries[0].contentRect 53 | const adjustedHeight = height + 16 54 | setRect((prevRect) => ({ ...prevRect, height: adjustedHeight })) 55 | } 56 | 57 | const resizeObserver = new ResizeObserver(handler) 58 | 59 | if (contentRef.current) { 60 | resizeObserver.observe(contentRef.current) 61 | } 62 | return () => { 63 | resizeObserver.disconnect() 64 | } 65 | }, []) 66 | 67 | const style: CSSProperties = { 68 | '--accordion-content-height': `${rect.height}px`, 69 | } as React.CSSProperties 70 | 71 | return ( 72 | 80 |
81 | {children} 82 |
83 |
84 | ) 85 | } 86 | AccordionContent.displayName = 'AccordionContent' 87 | 88 | export { Accordion, AccordionItem, AccordionTrigger, AccordionContent } 89 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/components/ui/alert-dialog.tsx: -------------------------------------------------------------------------------- 1 | import * as React from 'react' 2 | import { 3 | Dialog as ArkDialog, 4 | type DialogBackdropProps, 5 | type DialogContentProps, 6 | type DialogTitleProps, 7 | type DialogDescriptionProps, 8 | type DialogCloseTriggerProps, 9 | } from '@ark-ui/react' 10 | 11 | import { cn } from '../../lib/utils' 12 | import { buttonVariants } from './button' 13 | 14 | const AlertDialog = ArkDialog.Root 15 | const AlertDialogTrigger = ArkDialog.Trigger 16 | 17 | const AlertDialogOverlay = React.forwardRef< 18 | React.ElementRef, 19 | React.ComponentPropsWithoutRef 20 | >(({ className, ...props }, ref) => ( 21 | 29 | )) 30 | AlertDialogOverlay.displayName = ArkDialog.Backdrop.displayName 31 | 32 | const AlertDialogContent = React.forwardRef< 33 | React.ElementRef, 34 | React.ComponentPropsWithoutRef 35 | >(({ className, ...props }, ref) => ( 36 |
37 | 38 | 46 |
47 | )) 48 | AlertDialogContent.displayName = ArkDialog.Content.displayName 49 | 50 | const AlertDialogHeader = ({ className, ...props }: React.HTMLAttributes) => ( 51 |
52 | ) 53 | AlertDialogHeader.displayName = 'AlertDialogHeader' 54 | 55 | const AlertDialogFooter = ({ className, ...props }: React.HTMLAttributes) => ( 56 |
60 | ) 61 | AlertDialogFooter.displayName = 'AlertDialogFooter' 62 | 63 | const AlertDialogTitle = React.forwardRef< 64 | React.ElementRef, 65 | React.ComponentPropsWithoutRef 66 | >(({ className, ...props }, ref) => ( 67 | 68 | )) 69 | AlertDialogTitle.displayName = ArkDialog.Title.displayName 70 | 71 | const AlertDialogDescription = React.forwardRef< 72 | React.ElementRef, 73 | React.ComponentPropsWithoutRef 74 | >(({ className, ...props }, ref) => ( 75 | 80 | )) 81 | AlertDialogDescription.displayName = ArkDialog.Description.displayName 82 | 83 | const AlertDialogAction = React.forwardRef< 84 | HTMLButtonElement, 85 | React.ButtonHTMLAttributes 86 | >(({ className, ...props }, ref) => ( 87 | 20 | 21 | 22 | 23 | Are you absolutely sure? 24 | 25 | This action cannot be undone. This will permanently delete your account and remove 26 | your data from our servers. 27 | 28 | 29 | 30 | Cancel 31 | Continue 32 | 33 | 34 | 35 |
36 | ) 37 | } 38 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/alert.example.tsx: -------------------------------------------------------------------------------- 1 | import { Terminal } from 'lucide-react' 2 | import { Alert, AlertDescription, AlertTitle } from '../components/ui/alert' 3 | 4 | export default function Example() { 5 | return ( 6 |
7 | 8 | 9 | Heads up! 10 | You can add components to your app using the cli. 11 | 12 |
13 | ) 14 | } 15 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/avatar.example.tsx: -------------------------------------------------------------------------------- 1 | import { Avatar, AvatarFallback, AvatarImage } from '../components/ui/avatar' 2 | 3 | export default function Example() { 4 | return ( 5 |
6 | 7 | AW 8 | 9 | 10 |
11 | ) 12 | } 13 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/badge.example.tsx: -------------------------------------------------------------------------------- 1 | import { Badge } from '../components/ui/badge' 2 | 3 | export default function Example() { 4 | return ( 5 |
6 | Badge 7 |
8 | ) 9 | } 10 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/button.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from '../components/ui/button' 2 | 3 | export default function Example() { 4 | return ( 5 |
6 | 7 |
8 | ) 9 | } 10 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/checkbox.example.tsx: -------------------------------------------------------------------------------- 1 | import { Checkbox } from '../components/ui/checkbox' 2 | 3 | export default function Example() { 4 | return ( 5 |
6 |
7 | 8 | 14 |
15 |
16 | ) 17 | } 18 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/dialog.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from '../components/ui/button' 2 | import { 3 | Dialog, 4 | DialogContent, 5 | DialogDescription, 6 | DialogFooter, 7 | DialogHeader, 8 | DialogTitle, 9 | DialogTrigger, 10 | } from '../components/ui/dialog' 11 | import { Input } from '../components/ui/input' 12 | import { Label } from '../components/ui/label' 13 | 14 | export default function Example() { 15 | return ( 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 | Edit profile 24 | 25 | Make changes to your profile here. Click save when you're done. 26 | 27 | 28 |
29 |
30 | 33 | 34 |
35 |
36 | 39 | 40 |
41 |
42 | 43 | 44 | 45 |
46 |
47 |
48 | ) 49 | } 50 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/input.example.tsx: -------------------------------------------------------------------------------- 1 | import { Input } from '../components/ui/input' 2 | 3 | export default function Example() { 4 | return ( 5 |
6 | 7 |
8 | ) 9 | } 10 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/examples/label.example.tsx: -------------------------------------------------------------------------------- 1 | import { Checkbox } from '../components/ui/checkbox' 2 | import { Label } from '../components/ui/label' 3 | 4 | export default function Example() { 5 | return ( 6 |
7 |
8 | 9 | 10 |
11 |
12 | ) 13 | } 14 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/index.css: -------------------------------------------------------------------------------- 1 | @tailwind base; 2 | @tailwind components; 3 | @tailwind utilities; 4 | 5 | @layer base { 6 | /* :root { 7 | --background: 0 0% 100%; 8 | --foreground: 240 10% 3.9%; 9 | --card: 0 0% 100%; 10 | --card-foreground: 240 10% 3.9%; 11 | --popover: 0 0% 100%; 12 | --popover-foreground: 240 10% 3.9%; 13 | --primary: 240 5.9% 10%; 14 | --primary-foreground: 0 0% 98%; 15 | --secondary: 240 4.8% 95.9%; 16 | --secondary-foreground: 240 5.9% 10%; 17 | --muted: 240 4.8% 95.9%; 18 | --muted-foreground: 240 3.8% 46.1%; 19 | --accent: 240 4.8% 95.9%; 20 | --accent-foreground: 240 5.9% 10%; 21 | --destructive: 0 84.2% 60.2%; 22 | --destructive-foreground: 0 0% 98%; 23 | --border: 240 5.9% 90%; 24 | --input: 240 5.9% 90%; 25 | --ring: 240 5.9% 10%; 26 | --radius: 0.5rem; 27 | } */ 28 | 29 | :root { 30 | --background: 240 10% 3.9%; 31 | --foreground: 0 0% 98%; 32 | --card: 240 10% 3.9%; 33 | --card-foreground: 0 0% 98%; 34 | --popover: 240 10% 3.9%; 35 | --popover-foreground: 0 0% 98%; 36 | --primary: 0 0% 98%; 37 | --primary-foreground: 240 5.9% 10%; 38 | --secondary: 240 3.7% 15.9%; 39 | --secondary-foreground: 0 0% 98%; 40 | --muted: 240 3.7% 15.9%; 41 | --muted-foreground: 240 5% 64.9%; 42 | --accent: 240 3.7% 15.9%; 43 | --accent-foreground: 0 0% 98%; 44 | --destructive: 0 62.8% 30.6%; 45 | --destructive-foreground: 0 0% 98%; 46 | --border: 240 3.7% 15.9%; 47 | --input: 240 3.7% 15.9%; 48 | --ring: 240 4.9% 83.9%; 49 | --radius: 0.5rem; 50 | } 51 | } 52 | 53 | .checkbox-outline:has(+ :focus-visible) { 54 | @apply ring-2 ring-ring ring-offset-2 outline-none; 55 | } 56 | 57 | .example-center { 58 | @apply flex justify-center items-center h-screen 59 | } 60 | 61 | @layer base { 62 | * { 63 | @apply border-border; 64 | } 65 | body { 66 | @apply bg-background text-foreground; 67 | font-feature-settings: 68 | 'rlig' 1, 69 | 'calt' 1; 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/lib/utils.ts: -------------------------------------------------------------------------------- 1 | import { ClassValue, clsx } from 'clsx' 2 | import { twMerge } from 'tailwind-merge' 3 | 4 | export function cn(...inputs: ClassValue[]) { 5 | return twMerge(clsx(inputs)) 6 | } 7 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/main.tsx: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import ReactDOM from 'react-dom/client' 3 | import App from './App.tsx' 4 | import './index.css' 5 | 6 | ReactDOM.createRoot(document.getElementById('root')!).render( 7 | 8 | 9 | , 10 | ) 11 | -------------------------------------------------------------------------------- /packages/frameworks/react/src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /packages/frameworks/react/tailwind.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | content: ["./index.html", "./src/**/*.{js,ts,jsx,tsx}"], 3 | darkMode: ["class"], 4 | theme: { 5 | extend: { 6 | colors: { 7 | border: "hsl(var(--border))", 8 | input: "hsl(var(--input))", 9 | ring: "hsl(var(--ring))", 10 | background: "hsl(var(--background))", 11 | foreground: "hsl(var(--foreground))", 12 | primary: { 13 | DEFAULT: "hsl(var(--primary))", 14 | foreground: "hsl(var(--primary-foreground))", 15 | }, 16 | secondary: { 17 | DEFAULT: "hsl(var(--secondary))", 18 | foreground: "hsl(var(--secondary-foreground))", 19 | }, 20 | destructive: { 21 | DEFAULT: "hsl(var(--destructive))", 22 | foreground: "hsl(var(--destructive-foreground))", 23 | }, 24 | muted: { 25 | DEFAULT: "hsl(var(--muted))", 26 | foreground: "hsl(var(--muted-foreground))", 27 | }, 28 | accent: { 29 | DEFAULT: "hsl(var(--accent))", 30 | foreground: "hsl(var(--accent-foreground))", 31 | }, 32 | popover: { 33 | DEFAULT: "hsl(var(--popover))", 34 | foreground: "hsl(var(--popover-foreground))", 35 | }, 36 | card: { 37 | DEFAULT: "hsl(var(--card))", 38 | foreground: "hsl(var(--card-foreground))", 39 | }, 40 | }, 41 | borderRadius: { 42 | lg: "var(--radius)", 43 | md: "calc(var(--radius) - 2px)", 44 | sm: "calc(var(--radius) - 4px)", 45 | }, 46 | keyframes: { 47 | "accordion-down": { 48 | from: { height: 0 }, 49 | to: { height: "var(--accordion-content-height)" }, 50 | }, 51 | "accordion-up": { 52 | from: { height: "var(--accordion-content-height)" }, 53 | to: { height: 0 }, 54 | }, 55 | }, 56 | animation: { 57 | "accordion-down": "accordion-down 0.2s ease-out", 58 | "accordion-up": "accordion-up 0.2s ease-out", 59 | }, 60 | }, 61 | }, 62 | plugins: [require("tailwindcss-animate")], 63 | }; 64 | -------------------------------------------------------------------------------- /packages/frameworks/react/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "strict": true, 4 | "target": "ESNext", 5 | "module": "ESNext", 6 | "moduleResolution": "node", 7 | "allowSyntheticDefaultImports": true, 8 | "esModuleInterop": true, 9 | "jsx": "react-jsx", 10 | "types": ["vite/client"], 11 | "noEmit": true, 12 | "isolatedModules": true, 13 | "baseUrl": ".", 14 | "paths": { 15 | "~/*": ["./src/*"] 16 | } 17 | }, 18 | "include": ["src/**/*"] 19 | } 20 | -------------------------------------------------------------------------------- /packages/frameworks/react/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vite' 2 | import react from '@vitejs/plugin-react' 3 | 4 | // https://vitejs.dev/config/ 5 | export default defineConfig({ 6 | plugins: [react()], 7 | }) 8 | -------------------------------------------------------------------------------- /packages/frameworks/solid/.gitignore: -------------------------------------------------------------------------------- 1 | dist 2 | .solid 3 | .output 4 | .vercel 5 | .netlify 6 | 7 | # Environment 8 | .env 9 | .env*.local 10 | 11 | # dependencies 12 | /node_modules 13 | 14 | # IDEs and editors 15 | /.idea 16 | .project 17 | .classpath 18 | *.launch 19 | .settings/ 20 | 21 | # Temp 22 | gitignore 23 | 24 | # System Files 25 | .DS_Store 26 | Thumbs.db 27 | -------------------------------------------------------------------------------- /packages/frameworks/solid/README.md: -------------------------------------------------------------------------------- 1 | ## Project Structure 2 | 3 | ``` 4 | src/ 5 | ├── components 6 | │ ├── ui 7 | ├── examples 8 | └── lib 9 | ``` 10 | 11 | | Path | Description | 12 | | ---------------------- | -------------------------------------------------------------------------- | 13 | | `src` | The root directory for the SolidJS project, containing all source code. | 14 | | `src/components/ui` | Contains all reusable UI components for the project. | 15 | | `src/examples` | Contains real-world usage examples demonstrating how to integrate and use the UI components in various scenarios. | 16 | | `src/lib` | Contains utility functions and helpers that assist with component creation and updates. | -------------------------------------------------------------------------------- /packages/frameworks/solid/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Solid App 9 | 10 | 11 | 12 |
13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /packages/frameworks/solid/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vite-template-solid", 3 | "version": "0.0.0", 4 | "description": "", 5 | "scripts": { 6 | "start": "vite", 7 | "dev": "vite", 8 | "build": "vite build", 9 | "serve": "vite preview" 10 | }, 11 | "license": "MIT", 12 | "devDependencies": { 13 | "autoprefixer": "^10.4.18", 14 | "postcss": "^8.4.35", 15 | "solid-devtools": "^0.29.2", 16 | "tailwindcss": "^3.4.1", 17 | "typescript": "^5.3.3", 18 | "vite": "^5.0.11", 19 | "vite-plugin-solid": "^2.8.2", 20 | "vite-tsconfig-paths": "^4.3.2" 21 | }, 22 | "dependencies": { 23 | "@ark-ui/solid": "^2.2.0", 24 | "class-variance-authority": "^0.7.0", 25 | "clsx": "^2.1.0", 26 | "embla-carousel-solid": "^8.1.3", 27 | "lucide-solid": "^0.344.0", 28 | "solid-js": "^1.8.11", 29 | "tailwind-merge": "^2.2.1", 30 | "tailwindcss-animate": "^1.0.7" 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /packages/frameworks/solid/postcss.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | plugins: { 3 | tailwindcss: {}, 4 | autoprefixer: {}, 5 | }, 6 | } 7 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/App.tsx: -------------------------------------------------------------------------------- 1 | import type { Component } from 'solid-js'; 2 | import { Slider } from "~/components/ui/slider" 3 | 4 | const App: Component = () => { 5 | return ( 6 |
7 | console.log("Slider value:", value)} 13 | /> 14 |
15 | ); 16 | }; 17 | 18 | export default App; 19 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/accordion.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | Accordion as ArkAccordion, 3 | type AccordionItemProps, 4 | type AccordionItemTriggerProps, 5 | type AccordionItemContentProps, 6 | } from '@ark-ui/solid' 7 | import { splitProps } from 'solid-js' 8 | import { cn } from '../../lib/utils' 9 | import { ChevronDown } from 'lucide-solid' 10 | import { createSignal, onMount } from 'solid-js' 11 | 12 | export interface AccordionContentProps extends AccordionItemContentProps { 13 | id: string 14 | } 15 | 16 | const Accordion = ArkAccordion.Root 17 | 18 | const AccordionItem = (props: AccordionItemProps) => { 19 | const [, rest] = splitProps(props, ['class']) 20 | return 21 | } 22 | 23 | const AccordionTrigger = (props: AccordionItemTriggerProps) => ( 24 |
25 | svg]:rotate-180', 28 | props.class, 29 | )} 30 | > 31 | {props.children} 32 | 33 | 34 |
35 | ) 36 | 37 | const AccordionContent = (props: AccordionContentProps) => { 38 | const [rect, setRect] = createSignal({ height: 0, width: 0 }) 39 | 40 | let resizeObserver: ResizeObserver 41 | 42 | /** 43 | * 16 accounts for the padding pixels below the AccordianItem which is 44 | * required for the dropdown animation to function correctly. 45 | * 46 | * TODO: If someone overrides the padding, I need to dynamically pull in 47 | * that value for the `adjustedHeight` 48 | */ 49 | const handler = (entries: ResizeObserverEntry[]) => { 50 | const { height, width } = entries[0].contentRect 51 | const adjustedHeight = height + 16 52 | setRect({ height: adjustedHeight, width }) 53 | } 54 | onMount(() => { 55 | const targetDiv = document.getElementById(props.id) 56 | if (targetDiv) { 57 | resizeObserver = new ResizeObserver(handler) 58 | resizeObserver.observe(targetDiv) 59 | } 60 | 61 | return () => { 62 | if (resizeObserver) resizeObserver.disconnect() 63 | } 64 | }) 65 | 66 | return ( 67 | 74 |
75 | {props.children} 76 |
77 |
78 | ) 79 | } 80 | 81 | export { Accordion, AccordionItem, AccordionTrigger, AccordionContent } 82 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/alert-dialog.tsx: -------------------------------------------------------------------------------- 1 | import type { Component, ComponentProps } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { Portal } from "solid-js/web"; 4 | import { 5 | Dialog as ArkDialog, 6 | type DialogBackdropProps, 7 | type DialogContentProps, 8 | type DialogTitleProps, 9 | type DialogDescriptionProps, 10 | type DialogCloseTriggerProps, 11 | } from "@ark-ui/solid"; 12 | import { cn } from "../../lib/utils"; 13 | import { buttonVariants } from "../../components/ui/button"; 14 | 15 | const AlertDialog = ArkDialog.Root; 16 | const AlertDialogTrigger = ArkDialog.Trigger; 17 | const AlertDialogPosition = ArkDialog.Positioner; 18 | const AlertDialogClose = ArkDialog.CloseTrigger; 19 | 20 | const AlertDialogOverlay: Component = (props) => { 21 | const [, rest] = splitProps(props, ["class"]); 22 | return ( 23 | 30 | ); 31 | }; 32 | 33 | const AlertDialogContent: Component = (props) => { 34 | const [, rest] = splitProps(props, ["class"]); 35 | return ( 36 | 37 | 38 | 45 | 46 | ); 47 | }; 48 | 49 | const AlertDialogHeader: Component> = (props) => { 50 | const [, rest] = splitProps(props, ["class"]); 51 | return ( 52 |
59 | ); 60 | }; 61 | 62 | const AlertDialogFooter: Component> = (props) => { 63 | const [, rest] = splitProps(props, ["class"]); 64 | return ( 65 |
72 | ); 73 | }; 74 | 75 | const AlertDialogTitle: Component = (props) => { 76 | const [, rest] = splitProps(props, ["class"]); 77 | return ( 78 | 82 | ); 83 | }; 84 | 85 | const AlertDialogDescription: Component = (props) => { 86 | const [, rest] = splitProps(props, ["class"]); 87 | return ( 88 | 92 | ); 93 | }; 94 | 95 | const AlertDialogAction: Component> = (props) => { 96 | const [, rest] = splitProps(props, ["class"]); 97 | return ( 98 | 221 | ) 222 | } 223 | 224 | const CarouselNext: Component = (rawProps) => { 225 | const props = mergeProps({ variant: "outline", size: "icon" }, rawProps) 226 | const [local, others] = splitProps(props, ["class", "variant", "size"]) 227 | const { orientation, scrollNext, canScrollNext } = useCarousel() 228 | 229 | return ( 230 | 261 | ) 262 | } 263 | 264 | export { Carousel, CarouselContent, CarouselItem, CarouselPrevious, CarouselNext } -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/checkbox.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | Checkbox as ArkCheckbox, 3 | type CheckboxRootProps as ArkCheckboxProps, 4 | } from "@ark-ui/solid"; 5 | import type { Component } from "solid-js"; 6 | import { splitProps, Show } from "solid-js"; 7 | import { Check } from "lucide-solid"; 8 | import { cn } from "../../lib/utils"; 9 | 10 | export const Checkbox: Component = (props) => { 11 | const [, rest] = splitProps(props, ["class"]); 12 | return ( 13 | 17 | {(state) => ( 18 |
19 | 24 | 25 | 26 | 27 | 28 |
29 | )} 30 |
31 | ); 32 | }; 33 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/clipboard.tsx: -------------------------------------------------------------------------------- 1 | import { Clipboard as ArkClipboard } from '@ark-ui/solid'; 2 | import type { JSX } from 'solid-js'; 3 | 4 | const Clipboard = ArkClipboard.Root; 5 | const ClipboardControl = ArkClipboard.Control; 6 | const ClipboardIndicator = ArkClipboard.Indicator; 7 | const ClipboardTrigger = ArkClipboard.Trigger; 8 | 9 | const ClipboardCopied = (props: { copied: JSX.Element; children: JSX.Element }) => { 10 | return ( 11 | 12 | {props.children} 13 | 14 | ); 15 | }; 16 | 17 | export { 18 | Clipboard, 19 | ClipboardControl, 20 | ClipboardIndicator, 21 | ClipboardTrigger, 22 | ClipboardCopied 23 | }; 24 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/collapsible.tsx: -------------------------------------------------------------------------------- 1 | // Reference: https://ark-ui.com/react/docs/components/collapsible 2 | 3 | import { Collapsible as ArkCollapsible } from '@ark-ui/solid' 4 | 5 | const Collapsible = ArkCollapsible.Root 6 | const CollapsibleTrigger = ArkCollapsible.Trigger 7 | const CollapsibleContent = ArkCollapsible.Content 8 | 9 | export { 10 | Collapsible, 11 | CollapsibleTrigger, 12 | CollapsibleContent 13 | } -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/dialog.tsx: -------------------------------------------------------------------------------- 1 | import { splitProps } from 'solid-js' 2 | import type { Component, ComponentProps } from 'solid-js' 3 | import { Portal } from 'solid-js/web' 4 | import { 5 | Dialog as ArkDialog, 6 | type DialogBackdropProps, 7 | type DialogContentProps, 8 | type DialogTitleProps, 9 | type DialogDescriptionProps, 10 | } from '@ark-ui/solid' 11 | import { X } from 'lucide-solid' 12 | import { cn } from '../../lib/utils' 13 | 14 | const Dialog = ArkDialog.Root 15 | const DialogTrigger = ArkDialog.Trigger 16 | const DialogPosition = ArkDialog.Positioner 17 | const DialogClose = ArkDialog.CloseTrigger 18 | 19 | const DialogOverlay: Component = (props) => { 20 | const [, rest] = splitProps(props, ['class']) 21 | return ( 22 | 29 | ) 30 | } 31 | 32 | const DialogContent: Component = (props) => { 33 | const [, rest] = splitProps(props, ['class', 'children']) 34 | return ( 35 | 36 | 37 | 38 | 45 | {props.children} 46 | 47 | 48 | Close 49 | 50 | 51 | 52 | 53 | ) 54 | } 55 | 56 | const DialogHeader: Component> = (props) => { 57 | const [, rest] = splitProps(props, ['class']) 58 | return ( 59 |
60 | ) 61 | } 62 | 63 | const DialogFooter: Component> = (props) => { 64 | const [, rest] = splitProps(props, ['class']) 65 | return ( 66 |
70 | ) 71 | } 72 | 73 | const DialogTitle: Component = (props) => { 74 | const [, rest] = splitProps(props, ['class']) 75 | return ( 76 | 80 | ) 81 | } 82 | 83 | const DialogDescription: Component = (props) => { 84 | const [, rest] = splitProps(props, ['class']) 85 | return ( 86 | 87 | ) 88 | } 89 | 90 | export { 91 | Dialog, 92 | DialogTrigger, 93 | DialogPosition, 94 | DialogClose, 95 | DialogOverlay, 96 | DialogContent, 97 | DialogHeader, 98 | DialogFooter, 99 | DialogTitle, 100 | DialogDescription, 101 | } 102 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/dropdown-menu.tsx: -------------------------------------------------------------------------------- 1 | import type { Component, ComponentProps } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { Menu } from "@ark-ui/solid"; 4 | import type { 5 | MenuContentProps, 6 | MenuItemProps, 7 | MenuItemGroupLabelProps, 8 | MenuTriggerItemProps, 9 | } from "@ark-ui/solid"; 10 | import { ChevronRight } from "lucide-solid"; 11 | import { cn } from "../../lib/utils"; 12 | 13 | const DropdownMenu = Menu.Root; 14 | const DropdownMenuTrigger = Menu.Trigger; 15 | const DropdownPosition = Menu.Positioner; 16 | const DropdownMenuSeparator = Menu.Separator; 17 | const DropdownMenuGroup = Menu.ItemGroup; 18 | 19 | const DropdownMenuContent: Component = (props) => { 20 | const [, rest] = splitProps(props, ["class"]); 21 | return ( 22 | 29 | ); 30 | }; 31 | 32 | const DropdownMenuItem: Component = (props) => { 33 | const [, rest] = splitProps(props, ["class"]); 34 | return ( 35 | 42 | ); 43 | }; 44 | 45 | const DropdownMenuLabel: Component = (props) => { 46 | const [, rest] = splitProps(props, ["class"]); 47 | return ( 48 | 52 | ); 53 | }; 54 | 55 | const DropdownMenuSubContent: Component = (props) => { 56 | const [, rest] = splitProps(props, ["class"]); 57 | return ( 58 | 65 | ); 66 | }; 67 | 68 | const DropdownMenuSubTrigger: Component = (props) => { 69 | const [, rest] = splitProps(props, ["class"]); 70 | return ( 71 | 78 | {props.children} 79 | 80 | 81 | ); 82 | }; 83 | 84 | const DropdownMenuShortcut: Component> = (props) => { 85 | const [, rest] = splitProps(props, ["class"]); 86 | return ( 87 | 91 | ); 92 | }; 93 | 94 | export { 95 | DropdownMenu, 96 | DropdownMenuTrigger, 97 | DropdownMenuSubTrigger, 98 | DropdownPosition, 99 | DropdownMenuContent, 100 | DropdownMenuItem, 101 | DropdownMenuSeparator, 102 | DropdownMenuGroup, 103 | DropdownMenuLabel, 104 | DropdownMenuSubContent, 105 | DropdownMenuShortcut, 106 | }; 107 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/hover-card.tsx: -------------------------------------------------------------------------------- 1 | import type { Component } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { Portal } from "solid-js/web"; 4 | import type { HoverCardContentProps } from "@ark-ui/solid"; 5 | import { HoverCard as ArkHoverCard } from "@ark-ui/solid"; 6 | import { cn } from "../../lib/utils"; 7 | 8 | const HoverCard = ArkHoverCard.Root; 9 | const HoverCardTrigger = ArkHoverCard.Trigger; 10 | 11 | const HoverCardContent: Component = (props) => { 12 | const [, rest] = splitProps(props, ["class"]); 13 | return ( 14 | 15 | 16 | 23 | {props.children} 24 | 25 | 26 | 27 | 28 | 29 | 30 | ); 31 | }; 32 | 33 | export { HoverCard, HoverCardTrigger, HoverCardContent }; 34 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/input.tsx: -------------------------------------------------------------------------------- 1 | import type { Component, ComponentProps } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { ark } from "@ark-ui/solid"; 4 | import { cn } from "../../lib/utils"; 5 | 6 | const Input: Component> = (props) => { 7 | const [, rest] = splitProps(props, ["type", "class"]); 8 | return ( 9 | 16 | ); 17 | }; 18 | 19 | export { Input }; 20 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/label.tsx: -------------------------------------------------------------------------------- 1 | import type { Component, ComponentProps } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { ark } from "@ark-ui/solid"; 4 | import { cva } from "class-variance-authority"; 5 | import { cn } from "../../lib/utils"; 6 | 7 | const labelVariants = cva( 8 | "text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70", 9 | ); 10 | 11 | const Label: Component> = (props) => { 12 | const [, rest] = splitProps(props, ["class"]); 13 | return ( 14 | 15 | {props.children} 16 | 17 | ); 18 | }; 19 | 20 | export { Label, labelVariants }; 21 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/radio-group.tsx: -------------------------------------------------------------------------------- 1 | import type { Component } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import type { RadioGroupRootProps, RadioGroupItemProps } from "@ark-ui/solid"; 4 | import { RadioGroup as ArkRadioGroup } from "@ark-ui/solid"; 5 | import { Circle } from "lucide-solid"; 6 | import { cn } from "../../lib/utils"; 7 | 8 | const RadioGroup: Component = (props) => { 9 | const [, rest] = splitProps(props, ["class"]); 10 | return ; 11 | }; 12 | 13 | /** 14 | * 15 | * TODO: Figure out why vertical alignment in ArkRadioGroup.Indicator 16 | * doesn't work. As a temporary workaround I've offset its position 17 | * with mt-[3px] 18 | */ 19 | 20 | const RadioGroupItem: Component = (props) => { 21 | const [, rest] = splitProps(props, ["class"]); 22 | return ( 23 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | ); 37 | }; 38 | 39 | export { RadioGroup, RadioGroupItem }; 40 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/select.tsx: -------------------------------------------------------------------------------- 1 | import type { Component } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { 4 | Select as ArkSelect, 5 | type SelectTriggerProps, 6 | type SelectContentProps, 7 | type SelectItemProps, 8 | type SelectItemGroupLabelProps, 9 | type SelectItemGroupProps, 10 | } from "@ark-ui/solid"; 11 | import { Check, ChevronDown } from "lucide-solid"; 12 | import { cn } from "../../lib/utils"; 13 | 14 | const Select = ArkSelect.Root; 15 | const SelectValue = ArkSelect.ValueText; 16 | const SelectControl = ArkSelect.Control; 17 | const SelectIndicator = ArkSelect.Indicator; 18 | const SelectItemText = ArkSelect.ItemText; 19 | 20 | const SelectItemGroup: Component = (props) => { 21 | const [, rest] = splitProps(props, ["class"]); 22 | return ; 23 | }; 24 | 25 | const SelectItemGroupLabel: Component = (props) => { 26 | const [, rest] = splitProps(props, ["class"]); 27 | return ( 28 | 32 | ); 33 | }; 34 | 35 | const SelectTrigger: Component = (props) => { 36 | const [, rest] = splitProps(props, ["class", "children"]); 37 | return ( 38 | span]:line-clamp-1 w-[180px]", 41 | props.class, 42 | )} 43 | {...rest} 44 | > 45 | {props.children} 46 | 47 | 48 | ); 49 | }; 50 | 51 | const SelectContent: Component = (props) => { 52 | const [, rest] = splitProps(props, ["class"]); 53 | return ( 54 | 61 | ); 62 | }; 63 | 64 | const SelectItem: Component = (props) => { 65 | const [, rest] = splitProps(props, ["class", "children"]); 66 | return ( 67 | 74 | <> 75 | 76 | 77 | 78 | 79 | 80 | {props.children} 81 | 82 | 83 | ); 84 | }; 85 | 86 | export { 87 | Select, 88 | SelectValue, 89 | SelectTrigger, 90 | SelectContent, 91 | SelectItem, 92 | SelectControl, 93 | SelectIndicator, 94 | SelectItemText, 95 | SelectItemGroup, 96 | SelectItemGroupLabel, 97 | }; 98 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/sheet.tsx: -------------------------------------------------------------------------------- 1 | import type { Component, ComponentProps } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { Portal } from "solid-js/web"; 4 | import type { 5 | DialogBackdropProps, 6 | DialogContentProps, 7 | DialogTitleProps, 8 | DialogDescriptionProps, 9 | } from "@ark-ui/solid"; 10 | import { Dialog as ArkDrawer } from "@ark-ui/solid"; 11 | import { cva } from "class-variance-authority"; 12 | import { X } from "lucide-solid"; 13 | import { cn } from "../../lib/utils"; 14 | 15 | const sheetVariants = cva( 16 | "fixed z-50 gap-4 bg-background p-6 shadow-lg transition ease-in-out data-[state=open]:animate-in data-[state=closed]:animate-out data-[state=closed]:duration-300 data-[state=open]:duration-500", 17 | { 18 | variants: { 19 | side: { 20 | top: "inset-x-0 top-0 border-b data-[state=closed]:slide-out-to-top data-[state=open]:slide-in-from-top", 21 | bottom: 22 | "inset-x-0 bottom-0 border-t data-[state=closed]:slide-out-to-bottom data-[state=open]:slide-in-from-bottom", 23 | left: "inset-y-0 left-0 h-full w-3/4 border-r data-[state=closed]:slide-out-to-left data-[state=open]:slide-in-from-left sm:max-w-sm", 24 | right: 25 | "inset-y-0 right-0 h-full w-3/4 border-l data-[state=closed]:slide-out-to-right data-[state=open]:slide-in-from-right sm:max-w-sm", 26 | }, 27 | }, 28 | defaultVariants: { 29 | side: "right", 30 | }, 31 | }, 32 | ); 33 | 34 | const Sheet = ArkDrawer.Root; 35 | const SheetTrigger = ArkDrawer.Trigger; 36 | const SheetClose = ArkDrawer.CloseTrigger; 37 | const SheetPortal = Portal; 38 | 39 | const SheetOverlay: Component = (props) => { 40 | const [, rest] = splitProps(props, ["class"]); 41 | return ( 42 | 48 | ); 49 | }; 50 | 51 | const SheetContent: Component< 52 | DialogContentProps & { side?: "top" | "right" | "bottom" | "left" } 53 | > = (props) => { 54 | const [, rest] = splitProps(props, ["class"]); 55 | 56 | return ( 57 | 58 | 62 | {props.children} 63 | 64 | 65 | Close 66 | 67 | 68 | 69 | ); 70 | }; 71 | 72 | const SheetHeader: Component> = (props) => { 73 | const [, rest] = splitProps(props, ["class"]); 74 | return ( 75 |
82 | ); 83 | }; 84 | 85 | const SheetFooter: Component> = (props) => { 86 | const [, rest] = splitProps(props, ["class"]); 87 | return ( 88 |
95 | ); 96 | }; 97 | 98 | const SheetTitle: Component = (props) => { 99 | const [, rest] = splitProps(props, ["class"]); 100 | return ( 101 | 105 | ); 106 | }; 107 | 108 | const SheetDescription: Component = (props) => { 109 | const [, rest] = splitProps(props, ["class"]); 110 | return ( 111 | 115 | ); 116 | }; 117 | 118 | export { 119 | Sheet, 120 | SheetTrigger, 121 | SheetClose, 122 | SheetPortal, 123 | SheetContent, 124 | SheetHeader, 125 | SheetFooter, 126 | SheetTitle, 127 | SheetDescription, 128 | SheetOverlay, 129 | }; 130 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/skeleton.tsx: -------------------------------------------------------------------------------- 1 | import type { Component, ComponentProps } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { cn } from "../../lib/utils"; 4 | 5 | const Skeleton: Component> = (props) => { 6 | const [, rest] = splitProps(props, ["class"]); 7 | return ( 8 |
12 | ); 13 | }; 14 | 15 | export { Skeleton }; 16 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/slider.tsx: -------------------------------------------------------------------------------- 1 | import { splitProps } from "solid-js"; 2 | import { Slider as ArkSlider } from "@ark-ui/solid"; 3 | import type { SliderRootProps } from "@ark-ui/solid"; 4 | import { cn } from "~/lib/utils"; 5 | 6 | const Slider = (props: SliderRootProps) => { 7 | const [local, rest] = splitProps(props, ["class"]); 8 | 9 | return ( 10 | 14 | 15 | 16 | 17 | 18 | 22 | 23 | 24 | ); 25 | }; 26 | 27 | export { Slider }; 28 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/table.tsx: -------------------------------------------------------------------------------- 1 | import type { Component, ComponentProps } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import { cn } from "../../lib/utils"; 4 | 5 | const Table: Component> = (props) => { 6 | const [, rest] = splitProps(props, ["class"]); 7 | return ( 8 |
9 | 13 | 14 | ); 15 | }; 16 | 17 | const TableHeader: Component> = (props) => { 18 | const [, rest] = splitProps(props, ["class"]); 19 | return ; 20 | }; 21 | 22 | const TableBody: Component> = (props) => { 23 | const [, rest] = splitProps(props, ["class"]); 24 | return ( 25 | 26 | ); 27 | }; 28 | 29 | const TableFooter: Component> = (props) => { 30 | const [, rest] = splitProps(props, ["class"]); 31 | return ( 32 | 36 | ); 37 | }; 38 | 39 | const TableRow: Component> = (props) => { 40 | const [, rest] = splitProps(props, ["class"]); 41 | return ( 42 | 49 | ); 50 | }; 51 | 52 | const TableHead: Component> = (props) => { 53 | const [, rest] = splitProps(props, ["class"]); 54 | return ( 55 |
62 | ); 63 | }; 64 | 65 | const TableCell: Component> = (props) => { 66 | const [, rest] = splitProps(props, ["class"]); 67 | return ( 68 | 72 | ); 73 | }; 74 | 75 | const TableCaption: Component> = (props) => { 76 | const [, rest] = splitProps(props, ["class"]); 77 | return ( 78 |
82 | ); 83 | }; 84 | 85 | export { 86 | Table, 87 | TableHeader, 88 | TableBody, 89 | TableFooter, 90 | TableRow, 91 | TableHead, 92 | TableCell, 93 | TableCaption, 94 | }; 95 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/tabs.tsx: -------------------------------------------------------------------------------- 1 | import type { Component } from "solid-js"; 2 | import { splitProps } from "solid-js"; 3 | import type { 4 | TabListProps, 5 | TabTriggerProps, 6 | TabContentProps, 7 | TabIndicatorProps, 8 | } from "@ark-ui/solid"; 9 | import { Tabs as ArkTabs } from "@ark-ui/solid"; 10 | import { cn } from "../../lib/utils"; 11 | 12 | const Tabs = ArkTabs.Root; 13 | 14 | const TabsList: Component = (props) => { 15 | const [, rest] = splitProps(props, ["class"]); 16 | return ( 17 | 24 | ); 25 | }; 26 | 27 | const TabsTrigger: Component = (props) => { 28 | const [, rest] = splitProps(props, ["class"]); 29 | return ( 30 | 37 | ); 38 | }; 39 | 40 | const TabsContent: Component = (props) => { 41 | const [, rest] = splitProps(props, ["class"]); 42 | return ( 43 | 50 | ); 51 | }; 52 | 53 | const TabsIndicator: Component = (props) => { 54 | const [, rest] = splitProps(props, ["class"]); 55 | return ( 56 | 63 | ); 64 | }; 65 | 66 | export { Tabs, TabsList, TabsTrigger, TabsIndicator, TabsContent }; 67 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/components/ui/tooltip.tsx: -------------------------------------------------------------------------------- 1 | import { splitProps, type Component } from "solid-js"; 2 | import { Portal } from "solid-js/web"; 3 | import { Tooltip as ArkTooltip, type TooltipContentProps } from "@ark-ui/solid"; 4 | import { cn } from "../../lib/utils"; 5 | 6 | const Tooltip = ArkTooltip.Root; 7 | const TooltipTrigger = ArkTooltip.Trigger; 8 | 9 | const TooltipContent: Component = (props) => { 10 | const [, rest] = splitProps(props, ["class"]); 11 | return ( 12 | 13 | 14 | 21 | 22 | 23 | ); 24 | }; 25 | 26 | export { Tooltip, TooltipTrigger, TooltipContent }; 27 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/accordion.example.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | Accordion, 3 | AccordionContent, 4 | AccordionItem, 5 | AccordionTrigger, 6 | } from "../components/ui/accordion"; 7 | 8 | export default function Example() { 9 | return ( 10 |
11 | 12 | 13 | Is it accessible? 14 | 15 | Yes. It adheres to the WAI-ARIA design pattern. 16 | 17 | 18 | 19 | Is it styled? 20 | 21 | Yes. It comes with default styles that matches the other components' 22 | aesthetic. 23 | 24 | 25 | 26 | Is it animated? 27 | 28 | Yes. It's animated by default, but you can disable it if you prefer. 29 | 30 | 31 | 32 |
33 | ); 34 | } 35 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/alert-dialog.example.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | AlertDialog, 3 | AlertDialogHeader, 4 | AlertDialogContent, 5 | AlertDialogDescription, 6 | AlertDialogTitle, 7 | AlertDialogTrigger, 8 | AlertDialogFooter, 9 | AlertDialogCancel, 10 | AlertDialogAction, 11 | } from "../components/ui/alert-dialog"; 12 | import { Button } from "../components/ui/button"; 13 | 14 | export default function Example() { 15 | return ( 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 | Are you absolutely sure? 24 | 25 | This action cannot be undone. This will permanently delete your 26 | account and remove your data from our servers. 27 | 28 | 29 | 30 | Cancel 31 | Continue 32 | 33 | 34 | 35 |
36 | ); 37 | } 38 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/alert.example.tsx: -------------------------------------------------------------------------------- 1 | import { Alert, AlertTitle, AlertDescription } from "../components/ui/alert"; 2 | import { Terminal } from "lucide-solid"; 3 | 4 | export default function Example() { 5 | return ( 6 |
7 | 8 | 9 | Heads up! 10 | 11 | You can add components to your app using the cli. 12 | 13 | 14 |
15 | ); 16 | } 17 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/avatar.example.tsx: -------------------------------------------------------------------------------- 1 | import { Avatar, AvatarFallback, AvatarImage } from "../components/ui/avatar"; 2 | 3 | export default function Example() { 4 | return ( 5 | 6 | AW 7 | 11 | 12 | ); 13 | } 14 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/badge.example.tsx: -------------------------------------------------------------------------------- 1 | import { Badge } from "../components/ui/badge"; 2 | 3 | export default function Example() { 4 | return ( 5 |
6 | Badge 7 |
8 | ); 9 | } 10 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/breadcrumb.example.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | Breadcrumb, 3 | BreadcrumbEllipsis, 4 | BreadcrumbItem, 5 | BreadcrumbLink, 6 | BreadcrumbList, 7 | BreadcrumbPage, 8 | BreadcrumbSeparator, 9 | } from "../components/ui/breadcrumb"; 10 | import { 11 | DropdownMenu, 12 | DropdownMenuTrigger, 13 | DropdownPosition, 14 | DropdownMenuContent, 15 | DropdownMenuItem, 16 | } from "../components/ui/dropdown-menu"; 17 | 18 | export default function Example() { 19 | return ( 20 | 21 | 22 | 23 | Home 24 | 25 | 26 | 27 | 28 | 29 | 30 | Toggle menu 31 | 32 | 33 | 34 | Documentation 35 | Themes 36 | GitHub 37 | 38 | 39 | 40 | 41 | 42 | 43 | Components 44 | 45 | 46 | 47 | Breadcrumb 48 | 49 | 50 | 51 | ); 52 | }; -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/button.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from "../components/ui/button"; 2 | 3 | export default function Example() { 4 | return ( 5 |
6 | 7 |
8 | ); 9 | } 10 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/card.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from "../components/ui/button"; 2 | import { 3 | Card, 4 | CardContent, 5 | CardDescription, 6 | CardFooter, 7 | CardHeader, 8 | CardTitle, 9 | } from "../components/ui/card"; 10 | import { Input } from "../components/ui/input"; 11 | import { Label } from "../components/ui/label"; 12 | 13 | export default function Example() { 14 | return ( 15 |
16 | 17 | 18 | Create project 19 | 20 | Deploy your new project in one-click. 21 | 22 | 23 | 24 |
25 |
26 |
27 | 28 | 29 |
30 |
31 | 32 | 33 |
34 |
35 |
36 |
37 | 38 | 39 | 40 | 41 |
42 |
43 | ); 44 | } 45 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/checkbox.example.tsx: -------------------------------------------------------------------------------- 1 | import { Checkbox } from "../components/ui/checkbox"; 2 | 3 | export default function Example() { 4 | return ( 5 |
6 |
7 | 8 | 14 |
15 |
16 | ); 17 | } 18 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/clipboard.example.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | Clipboard, 3 | ClipboardControl, 4 | ClipboardTrigger, 5 | ClipboardCopied 6 | } from '~/components/ui/clipboard' 7 | import { Label } from '~/components/ui/label' 8 | import { Input } from '~/components/ui/input' 9 | import { Button } from '~/components/ui/button'; 10 | 11 | import { CheckIcon, ClipboardCopy } from 'lucide-solid' 12 | 13 | export default function Example() { 14 | const clipboardValue = 'https://ark-ui.com' 15 | return ( 16 | 17 | 18 | 19 |
20 | 21 | 22 | 27 | 28 |
29 |
30 |
31 | ) 32 | } -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/collapsible.example.tsx: -------------------------------------------------------------------------------- 1 | import { createSignal } from 'solid-js'; 2 | import { Button } from "~/components/ui/button" 3 | import { 4 | Collapsible, 5 | CollapsibleContent, 6 | CollapsibleTrigger, 7 | } from "~/components/ui/collapsible" 8 | 9 | export default function Example() { 10 | const [isOpen, setIsOpen] = createSignal(false) 11 | return ( 12 |
13 | 18 |
19 |

20 | @peduarte starred 3 repositories 21 |

22 | 23 | 27 | 28 |
29 |
30 | @radix-ui/primitives 31 |
32 | 33 |
34 | @radix-ui/colors 35 |
36 |
37 | @stitches/react 38 |
39 |
40 |
41 |
42 | ); 43 | }; -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/dialog.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from "../components/ui/button"; 2 | import { 3 | Dialog, 4 | DialogContent, 5 | DialogDescription, 6 | DialogFooter, 7 | DialogHeader, 8 | DialogTitle, 9 | DialogTrigger, 10 | } from "../components/ui/dialog"; 11 | import { Input } from "../components/ui/input"; 12 | import { Label } from "../components/ui/label"; 13 | 14 | export default function Example() { 15 | return ( 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 | Edit profile 24 | 25 | Make changes to your profile here. Click save when you're done. 26 | 27 | 28 |
29 |
30 | 33 | 34 |
35 |
36 | 39 | 40 |
41 |
42 | 43 | 44 | 45 |
46 |
47 |
48 | ); 49 | } 50 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/dropdown-menu.example.tsx: -------------------------------------------------------------------------------- 1 | import { Portal } from "solid-js/web"; 2 | import { Button } from "../components/ui/button"; 3 | import { 4 | Cloud, 5 | CreditCard, 6 | Github, 7 | Keyboard, 8 | LifeBuoy, 9 | LogOut, 10 | Mail, 11 | MessageSquare, 12 | Plus, 13 | PlusCircle, 14 | Settings, 15 | User, 16 | UserPlus, 17 | Users, 18 | } from "lucide-solid"; 19 | import { 20 | DropdownMenu, 21 | DropdownMenuTrigger, 22 | DropdownPosition, 23 | DropdownMenuContent, 24 | DropdownMenuItem, 25 | DropdownMenuSeparator, 26 | DropdownMenuLabel, 27 | DropdownMenuSubTrigger, 28 | DropdownMenuSubContent, 29 | DropdownMenuShortcut, 30 | } from "../components/ui/dropdown-menu"; 31 | 32 | export default function Example() { 33 | return ( 34 | 35 | 36 | 37 | 38 | 39 | 40 | My Account 41 | 42 | 43 | 44 | Profile 45 | ⇧⌘P 46 | 47 | 48 | 49 | Billing 50 | ⌘B 51 | 52 | 53 | 54 | Settings 55 | ⌘S 56 | 57 | 58 | 59 | Keyboard response 60 | ⌘K 61 | 62 | 63 | 64 | 65 | Team 66 | 67 | 68 | 69 | 70 | 71 | Invite users 72 | 73 | 74 | 75 | 76 | 77 | 78 | Email 79 | 80 | 81 | 82 | Message 83 | 84 | 85 | 86 | 87 | More... 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | New team 97 | ⌘+T 98 | 99 | 100 | 101 | 102 | GitHub 103 | 104 | 105 | 106 | Support 107 | 108 | 109 | 110 | API 111 | 112 | 113 | 114 | 115 | Log out 116 | 117 | 118 | 119 | 120 | ); 121 | } 122 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/hover-card.example.tsx: -------------------------------------------------------------------------------- 1 | import { CalendarDays } from "lucide-solid"; 2 | 3 | import { Avatar, AvatarFallback, AvatarImage } from "../components/ui/avatar"; 4 | import { Button } from "../components/ui/button"; 5 | import { 6 | HoverCard, 7 | HoverCardContent, 8 | HoverCardTrigger, 9 | } from "../components/ui/hover-card"; 10 | 11 | export default function Example() { 12 | return ( 13 |
14 | 15 | 16 | 17 | 18 | 19 |
20 | 21 | AW 22 | 23 | 24 |
25 |

@nextjs

26 |

27 | The React Framework – created and maintained by @vercel. 28 |

29 |
30 | {" "} 31 | 32 | Joined December 2021 33 | 34 |
35 |
36 |
37 |
38 |
39 |
40 | ); 41 | } 42 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/input.example.tsx: -------------------------------------------------------------------------------- 1 | import { Checkbox } from "../components/ui/checkbox"; 2 | import { Label } from "../components/ui/label"; 3 | 4 | export function Example() { 5 | return ( 6 |
7 |
8 | 9 | 10 |
11 |
12 | ); 13 | } 14 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/label.example.tsx: -------------------------------------------------------------------------------- 1 | import { Checkbox } from "../components/ui/checkbox"; 2 | 3 | export default function Example() { 4 | return ( 5 |
6 |
7 | 8 | 14 |
15 |
16 | ); 17 | } 18 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/radio-group.example.tsx: -------------------------------------------------------------------------------- 1 | import { RadioGroup, RadioGroupItem } from "../components/ui/radio-group"; 2 | import { Label } from "../components/ui/label"; 3 | 4 | export default function Example() { 5 | return ( 6 |
7 | 8 |
9 | 10 | 11 |
12 |
13 | 14 | 15 |
16 |
17 | 18 | 21 |
22 |
23 |
24 | ); 25 | } 26 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/select.example.tsx: -------------------------------------------------------------------------------- 1 | import { 2 | Select, 3 | SelectTrigger, 4 | SelectControl, 5 | SelectValue, 6 | SelectItem, 7 | SelectItemText, 8 | SelectContent, 9 | SelectItemGroup, 10 | SelectItemGroupLabel, 11 | } from "../components/ui/select"; 12 | 13 | export default function Example() { 14 | const items = ["Apple", "Banana", "Blueberry", "Grapes", "Pineapple"]; 15 | return ( 16 |
17 | 34 |
35 | ); 36 | } 37 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/sheet.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from "../components/ui/button"; 2 | import { Input } from "../components/ui/input"; 3 | import { Label } from "../components/ui/label"; 4 | import { 5 | Sheet, 6 | SheetClose, 7 | SheetContent, 8 | SheetDescription, 9 | SheetFooter, 10 | SheetHeader, 11 | SheetTitle, 12 | SheetTrigger, 13 | } from "../components/ui/sheet"; 14 | 15 | export default function Example() { 16 | return ( 17 | 18 | 19 | 20 | 21 | 22 | 23 | Edit profile 24 | 25 | Make changes to your profile here. Click save when you're done. 26 | 27 | 28 |
29 |
30 | 33 | 34 |
35 |
36 | 39 | 40 |
41 |
42 | 43 | 44 | 45 | 46 | 47 |
48 |
49 | ); 50 | } 51 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/skeleton.example.tsx: -------------------------------------------------------------------------------- 1 | import { Skeleton } from "../components/ui/skeleton"; 2 | 3 | export default function Example() { 4 | return ( 5 |
6 |
7 | 8 |
9 | 10 | 11 |
12 |
13 |
14 | ); 15 | } 16 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/slider.example.tsx: -------------------------------------------------------------------------------- 1 | import { Slider } from "~/components/ui/slider" 2 | 3 | export default function Example() { 4 | return ( 5 | console.log("Slider value:", value)} 11 | /> 12 | ) 13 | } -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/table.example.tsx: -------------------------------------------------------------------------------- 1 | import { For } from "solid-js"; 2 | import { 3 | Table, 4 | TableBody, 5 | TableCaption, 6 | TableCell, 7 | TableHead, 8 | TableHeader, 9 | TableRow, 10 | } from "../components/ui/table"; 11 | 12 | const invoices = [ 13 | { 14 | invoice: "INV001", 15 | paymentStatus: "Paid", 16 | totalAmount: "$250.00", 17 | paymentMethod: "Credit Card", 18 | }, 19 | { 20 | invoice: "INV002", 21 | paymentStatus: "Pending", 22 | totalAmount: "$150.00", 23 | paymentMethod: "PayPal", 24 | }, 25 | { 26 | invoice: "INV003", 27 | paymentStatus: "Unpaid", 28 | totalAmount: "$350.00", 29 | paymentMethod: "Bank Transfer", 30 | }, 31 | { 32 | invoice: "INV004", 33 | paymentStatus: "Paid", 34 | totalAmount: "$450.00", 35 | paymentMethod: "Credit Card", 36 | }, 37 | { 38 | invoice: "INV005", 39 | paymentStatus: "Paid", 40 | totalAmount: "$550.00", 41 | paymentMethod: "PayPal", 42 | }, 43 | { 44 | invoice: "INV006", 45 | paymentStatus: "Pending", 46 | totalAmount: "$200.00", 47 | paymentMethod: "Bank Transfer", 48 | }, 49 | { 50 | invoice: "INV007", 51 | paymentStatus: "Unpaid", 52 | totalAmount: "$300.00", 53 | paymentMethod: "Credit Card", 54 | }, 55 | ]; 56 | 57 | export default function Example() { 58 | return ( 59 |
60 | 61 | A list of your recent invoices. 62 | 63 | 64 | Invoice 65 | Status 66 | Method 67 | Amount 68 | 69 | 70 | 71 | 72 | {(invoice) => ( 73 | 74 | {invoice.invoice} 75 | {invoice.paymentStatus} 76 | {invoice.paymentMethod} 77 | {invoice.totalAmount} 78 | 79 | )} 80 | 81 | 82 |
83 |
84 | ); 85 | } 86 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/tabs.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from "../components/ui/button"; 2 | import { 3 | Card, 4 | CardContent, 5 | CardDescription, 6 | CardFooter, 7 | CardHeader, 8 | CardTitle, 9 | } from "../components/ui/card"; 10 | import { Input } from "../components/ui/input"; 11 | import { Label } from "../components/ui/label"; 12 | import { 13 | Tabs, 14 | TabsContent, 15 | TabsList, 16 | TabsTrigger, 17 | } from "../components/ui/tabs"; 18 | 19 | export default function Example() { 20 | return ( 21 |
22 | 23 | 24 | Account 25 | Password 26 | 27 | 28 | 29 | 30 | Account 31 | 32 | Make changes to your account here. Click save when you're done. 33 | 34 | 35 | 36 |
37 | 38 | 39 |
40 |
41 | 42 | 43 |
44 |
45 | 46 | 47 | 48 |
49 |
50 | 51 | 52 | 53 | Password 54 | 55 | Change your password here. After saving, you'll be logged out. 56 | 57 | 58 | 59 |
60 | 61 | 62 |
63 |
64 | 65 | 66 |
67 |
68 | 69 | 70 | 71 |
72 |
73 |
74 |
75 | ); 76 | } 77 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/examples/tooltip.example.tsx: -------------------------------------------------------------------------------- 1 | import { Button } from "../components/ui/button"; 2 | import { 3 | Tooltip, 4 | TooltipContent, 5 | TooltipTrigger, 6 | } from "../components/ui/tooltip"; 7 | 8 | export default function Example() { 9 | return ( 10 |
11 | 12 | 13 | 14 | 15 | 16 |

Add to library

17 |
18 |
19 |
20 | ); 21 | } 22 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/index.css: -------------------------------------------------------------------------------- 1 | @tailwind base; 2 | @tailwind components; 3 | @tailwind utilities; 4 | 5 | @layer base { 6 | /* :root { 7 | --background: 0 0% 100%; 8 | --foreground: 240 10% 3.9%; 9 | --card: 0 0% 100%; 10 | --card-foreground: 240 10% 3.9%; 11 | --popover: 0 0% 100%; 12 | --popover-foreground: 240 10% 3.9%; 13 | --primary: 240 5.9% 10%; 14 | --primary-foreground: 0 0% 98%; 15 | --secondary: 240 4.8% 95.9%; 16 | --secondary-foreground: 240 5.9% 10%; 17 | --muted: 240 4.8% 95.9%; 18 | --muted-foreground: 240 3.8% 46.1%; 19 | --accent: 240 4.8% 95.9%; 20 | --accent-foreground: 240 5.9% 10%; 21 | --destructive: 0 84.2% 60.2%; 22 | --destructive-foreground: 0 0% 98%; 23 | --border: 240 5.9% 90%; 24 | --input: 240 5.9% 90%; 25 | --ring: 240 5.9% 10%; 26 | --radius: 0.5rem; 27 | } */ 28 | 29 | :root { 30 | --background: 240 10% 3.9%; 31 | --foreground: 0 0% 98%; 32 | --card: 240 10% 3.9%; 33 | --card-foreground: 0 0% 98%; 34 | --popover: 240 10% 3.9%; 35 | --popover-foreground: 0 0% 98%; 36 | --primary: 0 0% 98%; 37 | --primary-foreground: 240 5.9% 10%; 38 | --secondary: 240 3.7% 15.9%; 39 | --secondary-foreground: 0 0% 98%; 40 | --muted: 240 3.7% 15.9%; 41 | --muted-foreground: 240 5% 64.9%; 42 | --accent: 240 3.7% 15.9%; 43 | --accent-foreground: 0 0% 98%; 44 | --destructive: 0 62.8% 30.6%; 45 | --destructive-foreground: 0 0% 98%; 46 | --border: 240 3.7% 15.9%; 47 | --input: 240 3.7% 15.9%; 48 | --ring: 240 4.9% 83.9%; 49 | --radius: 0.5rem; 50 | } 51 | } 52 | 53 | 54 | .checkbox-outline:has(+ :focus-visible) { 55 | @apply ring-2 ring-ring ring-offset-2 outline-none; 56 | } 57 | 58 | @layer base { 59 | * { 60 | @apply border-border; 61 | } 62 | body { 63 | @apply bg-background text-foreground; 64 | font-feature-settings: 65 | 'rlig' 1, 66 | 'calt' 1; 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/index.tsx: -------------------------------------------------------------------------------- 1 | /* @refresh reload */ 2 | import { render } from 'solid-js/web'; 3 | 4 | import './index.css'; 5 | import App from './App'; 6 | 7 | const root = document.getElementById('root'); 8 | 9 | if (import.meta.env.DEV && !(root instanceof HTMLElement)) { 10 | throw new Error( 11 | 'Root element not found. Did you forget to add it to your index.html? Or maybe the id attribute got misspelled?', 12 | ); 13 | } 14 | 15 | render(() => , root!); 16 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/lib/utils.ts: -------------------------------------------------------------------------------- 1 | import { type ClassValue, clsx } from 'clsx' 2 | import { twMerge } from 'tailwind-merge' 3 | 4 | export function cn(...inputs: ClassValue[]) { 5 | return twMerge(clsx(inputs)) 6 | } 7 | -------------------------------------------------------------------------------- /packages/frameworks/solid/src/logo.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /packages/frameworks/solid/tailwind.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | content: ["./src/**/*.{html,js,jsx,svelte,ts,tsx,vue}"], 3 | darkMode: ["class"], 4 | theme: { 5 | extend: { 6 | colors: { 7 | border: "hsl(var(--border))", 8 | input: "hsl(var(--input))", 9 | ring: "hsl(var(--ring))", 10 | background: "hsl(var(--background))", 11 | foreground: "hsl(var(--foreground))", 12 | primary: { 13 | DEFAULT: "hsl(var(--primary))", 14 | foreground: "hsl(var(--primary-foreground))", 15 | }, 16 | secondary: { 17 | DEFAULT: "hsl(var(--secondary))", 18 | foreground: "hsl(var(--secondary-foreground))", 19 | }, 20 | destructive: { 21 | DEFAULT: "hsl(var(--destructive))", 22 | foreground: "hsl(var(--destructive-foreground))", 23 | }, 24 | muted: { 25 | DEFAULT: "hsl(var(--muted))", 26 | foreground: "hsl(var(--muted-foreground))", 27 | }, 28 | accent: { 29 | DEFAULT: "hsl(var(--accent))", 30 | foreground: "hsl(var(--accent-foreground))", 31 | }, 32 | popover: { 33 | DEFAULT: "hsl(var(--popover))", 34 | foreground: "hsl(var(--popover-foreground))", 35 | }, 36 | card: { 37 | DEFAULT: "hsl(var(--card))", 38 | foreground: "hsl(var(--card-foreground))", 39 | }, 40 | }, 41 | borderRadius: { 42 | lg: "var(--radius)", 43 | md: "calc(var(--radius) - 2px)", 44 | sm: "calc(var(--radius) - 4px)", 45 | }, 46 | keyframes: { 47 | "accordion-down": { 48 | from: { height: 0 }, 49 | to: { height: "var(--accordion-content-height)" }, 50 | }, 51 | "accordion-up": { 52 | from: { height: "var(--accordion-content-height)" }, 53 | to: { height: 0 }, 54 | }, 55 | }, 56 | animation: { 57 | "accordion-down": "accordion-down 0.2s ease-out", 58 | "accordion-up": "accordion-up 0.2s ease-out", 59 | }, 60 | "animate-fadeIn": "opacity-0 animation: fadeIn 1s ease forwards", 61 | }, 62 | }, 63 | plugins: [require("tailwindcss-animate")], 64 | }; 65 | -------------------------------------------------------------------------------- /packages/frameworks/solid/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "strict": true, 4 | "target": "ESNext", 5 | "module": "ESNext", 6 | "moduleResolution": "node", 7 | "allowSyntheticDefaultImports": true, 8 | "esModuleInterop": true, 9 | "jsx": "preserve", 10 | "jsxImportSource": "solid-js", 11 | "types": ["vite/client"], 12 | "noEmit": true, 13 | "isolatedModules": true, 14 | "baseUrl": "./", 15 | "paths": { 16 | "~/*": ["./src/*"] 17 | } 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /packages/frameworks/solid/vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vite' 2 | import solidPlugin from 'vite-plugin-solid' 3 | 4 | // This is only used for import alias, not required. 5 | import tsconfigPaths from 'vite-tsconfig-paths' 6 | 7 | export default defineConfig({ 8 | plugins: [solidPlugin(), tsconfigPaths()], 9 | server: { 10 | port: 3000, 11 | }, 12 | build: { 13 | target: 'esnext', 14 | }, 15 | }) 16 | -------------------------------------------------------------------------------- /packages/frameworks/vue/.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .vscode/* 17 | !.vscode/extensions.json 18 | .idea 19 | .DS_Store 20 | *.suo 21 | *.ntvs* 22 | *.njsproj 23 | *.sln 24 | *.sw? 25 | -------------------------------------------------------------------------------- /packages/frameworks/vue/.vscode/extensions.json: -------------------------------------------------------------------------------- 1 | { 2 | "recommendations": ["Vue.volar", "Vue.vscode-typescript-vue-plugin"] 3 | } 4 | -------------------------------------------------------------------------------- /packages/frameworks/vue/README.md: -------------------------------------------------------------------------------- 1 | # Vue -------------------------------------------------------------------------------- /packages/frameworks/vue/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Vite + Vue 8 | 9 | 10 |
11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /packages/frameworks/vue/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "vue", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "scripts": { 7 | "dev": "vite", 8 | "build": "vite build", 9 | "preview": "vite preview" 10 | }, 11 | "dependencies": { 12 | "@ark-ui/vue": "^0.11.0", 13 | "@vueuse/core": "^10.9.0", 14 | "lucide-vue-next": "^0.344.0", 15 | "tailwindcss-animate": "^1.0.7", 16 | "vue": "^3.4.19" 17 | }, 18 | "devDependencies": { 19 | "@vitejs/plugin-vue": "^5.0.4", 20 | "autoprefixer": "^10.4.18", 21 | "postcss": "^8.4.35", 22 | "tailwindcss": "^3.4.1", 23 | "vite": "^5.1.4" 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /packages/frameworks/vue/postcss.config.js: -------------------------------------------------------------------------------- 1 | export default { 2 | plugins: { 3 | tailwindcss: {}, 4 | autoprefixer: {}, 5 | }, 6 | } 7 | -------------------------------------------------------------------------------- /packages/frameworks/vue/public/vite.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /packages/frameworks/vue/src/App.vue: -------------------------------------------------------------------------------- 1 | 4 | 5 | -------------------------------------------------------------------------------- /packages/frameworks/vue/src/components/ui/Accordion.vue: -------------------------------------------------------------------------------- 1 | 9 | 10 | 22 | -------------------------------------------------------------------------------- /packages/frameworks/vue/src/main.js: -------------------------------------------------------------------------------- 1 | import { createApp } from 'vue' 2 | import './style.css' 3 | import App from './App.vue' 4 | 5 | createApp(App).mount('#app') 6 | -------------------------------------------------------------------------------- /packages/frameworks/vue/src/style.css: -------------------------------------------------------------------------------- 1 | @tailwind base; 2 | @tailwind components; 3 | @tailwind utilities; 4 | 5 | @layer base { 6 | /* :root { 7 | --background: 0 0% 100%; 8 | --foreground: 240 10% 3.9%; 9 | --card: 0 0% 100%; 10 | --card-foreground: 240 10% 3.9%; 11 | --popover: 0 0% 100%; 12 | --popover-foreground: 240 10% 3.9%; 13 | --primary: 240 5.9% 10%; 14 | --primary-foreground: 0 0% 98%; 15 | --secondary: 240 4.8% 95.9%; 16 | --secondary-foreground: 240 5.9% 10%; 17 | --muted: 240 4.8% 95.9%; 18 | --muted-foreground: 240 3.8% 46.1%; 19 | --accent: 240 4.8% 95.9%; 20 | --accent-foreground: 240 5.9% 10%; 21 | --destructive: 0 84.2% 60.2%; 22 | --destructive-foreground: 0 0% 98%; 23 | --border: 240 5.9% 90%; 24 | --input: 240 5.9% 90%; 25 | --ring: 240 5.9% 10%; 26 | --radius: 0.5rem; 27 | } */ 28 | 29 | :root { 30 | --background: 240 10% 3.9%; 31 | --foreground: 0 0% 98%; 32 | --card: 240 10% 3.9%; 33 | --card-foreground: 0 0% 98%; 34 | --popover: 240 10% 3.9%; 35 | --popover-foreground: 0 0% 98%; 36 | --primary: 0 0% 98%; 37 | --primary-foreground: 240 5.9% 10%; 38 | --secondary: 240 3.7% 15.9%; 39 | --secondary-foreground: 0 0% 98%; 40 | --muted: 240 3.7% 15.9%; 41 | --muted-foreground: 240 5% 64.9%; 42 | --accent: 240 3.7% 15.9%; 43 | --accent-foreground: 0 0% 98%; 44 | --destructive: 0 62.8% 30.6%; 45 | --destructive-foreground: 0 0% 98%; 46 | --border: 240 3.7% 15.9%; 47 | --input: 240 3.7% 15.9%; 48 | --ring: 240 4.9% 83.9%; 49 | --radius: 0.5rem; 50 | } 51 | } 52 | 53 | .checkbox-outline:has(+ :focus-visible) { 54 | @apply ring-2 ring-ring ring-offset-2 outline-none; 55 | } 56 | 57 | @layer base { 58 | * { 59 | @apply border-border; 60 | } 61 | body { 62 | @apply bg-background text-foreground; 63 | font-feature-settings: 64 | 'rlig' 1, 65 | 'calt' 1; 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /packages/frameworks/vue/tailwind.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | content: ["./src/**/*.{html,js,jsx,svelte,ts,tsx,vue}"], 3 | darkMode: ["class"], 4 | theme: { 5 | extend: { 6 | colors: { 7 | border: "hsl(var(--border))", 8 | input: "hsl(var(--input))", 9 | ring: "hsl(var(--ring))", 10 | background: "hsl(var(--background))", 11 | foreground: "hsl(var(--foreground))", 12 | primary: { 13 | DEFAULT: "hsl(var(--primary))", 14 | foreground: "hsl(var(--primary-foreground))", 15 | }, 16 | secondary: { 17 | DEFAULT: "hsl(var(--secondary))", 18 | foreground: "hsl(var(--secondary-foreground))", 19 | }, 20 | destructive: { 21 | DEFAULT: "hsl(var(--destructive))", 22 | foreground: "hsl(var(--destructive-foreground))", 23 | }, 24 | muted: { 25 | DEFAULT: "hsl(var(--muted))", 26 | foreground: "hsl(var(--muted-foreground))", 27 | }, 28 | accent: { 29 | DEFAULT: "hsl(var(--accent))", 30 | foreground: "hsl(var(--accent-foreground))", 31 | }, 32 | popover: { 33 | DEFAULT: "hsl(var(--popover))", 34 | foreground: "hsl(var(--popover-foreground))", 35 | }, 36 | card: { 37 | DEFAULT: "hsl(var(--card))", 38 | foreground: "hsl(var(--card-foreground))", 39 | }, 40 | }, 41 | borderRadius: { 42 | lg: "var(--radius)", 43 | md: "calc(var(--radius) - 2px)", 44 | sm: "calc(var(--radius) - 4px)", 45 | }, 46 | keyframes: { 47 | "accordion-down": { 48 | from: { height: 0 }, 49 | to: { height: "var(--accordion-content-height)" }, 50 | }, 51 | "accordion-up": { 52 | from: { height: "var(--accordion-content-height)" }, 53 | to: { height: 0 }, 54 | }, 55 | }, 56 | animation: { 57 | "accordion-down": "accordion-down 0.2s ease-out", 58 | "accordion-up": "accordion-up 0.2s ease-out", 59 | }, 60 | }, 61 | }, 62 | plugins: [require("tailwindcss-animate")], 63 | }; 64 | -------------------------------------------------------------------------------- /packages/frameworks/vue/vite.config.js: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vite' 2 | import vue from '@vitejs/plugin-vue' 3 | 4 | // https://vitejs.dev/config/ 5 | export default defineConfig({ 6 | plugins: [vue()], 7 | }) 8 | --------------------------------------------------------------------------------