diff --git a/.github/workflows/module.yml b/.github/workflows/module.yml index 24cbb8d6..dd6104bc 100644 --- a/.github/workflows/module.yml +++ b/.github/workflows/module.yml @@ -43,9 +43,6 @@ jobs: - name: Prepare run: pnpm run dev:prepare - - name: Devtools prepare - run: pnpm run devtools:prepare - - name: Lint run: pnpm run lint diff --git a/build.config.ts b/build.config.ts index fef778b4..6f7143a7 100644 --- a/build.config.ts +++ b/build.config.ts @@ -2,8 +2,6 @@ import { defineBuildConfig } from 'unbuild' export default defineBuildConfig({ entries: [ - // Include devtools runtime files - { input: './src/devtools/runtime', builder: 'mkdist', outDir: 'dist/devtools/runtime' }, // Vue support './src/unplugin', './src/vite' @@ -12,8 +10,7 @@ export default defineBuildConfig({ emitCJS: true }, replace: { - 'process.env.DEV': 'false', - 'process.env.NUXT_UI_DEVTOOLS_LOCAL': 'false' + 'process.env.DEV': 'false' }, hooks: { 'mkdist:entry:options'(ctx, entry, options) { diff --git a/devtools/app/app.config.ts b/devtools/app/app.config.ts deleted file mode 100644 index aec89678..00000000 --- a/devtools/app/app.config.ts +++ /dev/null @@ -1,8 +0,0 @@ -export default defineAppConfig({ - ui: { - colors: { - primary: 'green', - neutral: 'zinc' - } - } -}) diff --git a/devtools/app/app.vue b/devtools/app/app.vue deleted file mode 100644 index bf279960..00000000 --- a/devtools/app/app.vue +++ /dev/null @@ -1,198 +0,0 @@ - - - - - - - - - - {{ (error.data as any)?.error ?? 'Unexpected error' }} - - - - - - - - - - - - - - - - - - - - Open docs - - - - - - - - - - - - - - - - - - - - diff --git a/devtools/app/components/CollapseContainer.vue b/devtools/app/components/CollapseContainer.vue deleted file mode 100644 index 3da4858d..00000000 --- a/devtools/app/components/CollapseContainer.vue +++ /dev/null @@ -1,43 +0,0 @@ - - - - - - - - - - - {{ collapsed ? 'Expand' : 'Collapse' }} - - - diff --git a/devtools/app/components/ComponentPreview.vue b/devtools/app/components/ComponentPreview.vue deleted file mode 100644 index f1e5c312..00000000 --- a/devtools/app/components/ComponentPreview.vue +++ /dev/null @@ -1,151 +0,0 @@ - - - - - - - - - Ensure your app.vue file includes a <NuxtPage /> component, as the component preview is mounted as a page. - - - - - - - - - - - - diff --git a/devtools/app/components/ComponentPropInput.vue b/devtools/app/components/ComponentPropInput.vue deleted file mode 100644 index 1e9f48c2..00000000 --- a/devtools/app/components/ComponentPropInput.vue +++ /dev/null @@ -1,39 +0,0 @@ - - - - - - - {{ meta?.name }} - - - - - - - - - - - diff --git a/devtools/app/components/UILogo.vue b/devtools/app/components/UILogo.vue deleted file mode 100644 index 031531bf..00000000 --- a/devtools/app/components/UILogo.vue +++ /dev/null @@ -1,10 +0,0 @@ - - - diff --git a/devtools/app/components/inputs/ArrayInput.vue b/devtools/app/components/inputs/ArrayInput.vue deleted file mode 100644 index fd9c6e1b..00000000 --- a/devtools/app/components/inputs/ArrayInput.vue +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - - - - - - - - Remove - - - - - - - Add value - - - diff --git a/devtools/app/components/inputs/BooleanInput.vue b/devtools/app/components/inputs/BooleanInput.vue deleted file mode 100644 index 14c0d2de..00000000 --- a/devtools/app/components/inputs/BooleanInput.vue +++ /dev/null @@ -1,20 +0,0 @@ - - - - - - - diff --git a/devtools/app/components/inputs/NumberInput.vue b/devtools/app/components/inputs/NumberInput.vue deleted file mode 100644 index 13883d0d..00000000 --- a/devtools/app/components/inputs/NumberInput.vue +++ /dev/null @@ -1,15 +0,0 @@ - - - - - - - diff --git a/devtools/app/components/inputs/ObjectInput.vue b/devtools/app/components/inputs/ObjectInput.vue deleted file mode 100644 index cac12d02..00000000 --- a/devtools/app/components/inputs/ObjectInput.vue +++ /dev/null @@ -1,38 +0,0 @@ - - - - - - - { - if (!modelValue) modelValue ||= {} - else modelValue[attributeSchema.name] = value - }" - /> - - diff --git a/devtools/app/components/inputs/StringEnumInput.vue b/devtools/app/components/inputs/StringEnumInput.vue deleted file mode 100644 index 945ab4f6..00000000 --- a/devtools/app/components/inputs/StringEnumInput.vue +++ /dev/null @@ -1,60 +0,0 @@ - - - - - - - diff --git a/devtools/app/components/inputs/StringInput.vue b/devtools/app/components/inputs/StringInput.vue deleted file mode 100644 index bc99b932..00000000 --- a/devtools/app/components/inputs/StringInput.vue +++ /dev/null @@ -1,15 +0,0 @@ - - - - - - - diff --git a/devtools/app/composables/usePropSchema.ts b/devtools/app/composables/usePropSchema.ts deleted file mode 100644 index 8c9b529b..00000000 --- a/devtools/app/composables/usePropSchema.ts +++ /dev/null @@ -1,44 +0,0 @@ -import type { PropertyMeta } from 'vue-component-meta' -import BooleanInput, { booleanInputSchema } from '../components/inputs/BooleanInput.vue' -import StringInput, { stringInputSchema } from '../components/inputs/StringInput.vue' -import NumberInput, { numberInputSchema } from '../components/inputs/NumberInput.vue' -import StringEnumInput, { stringEnumInputSchema } from '../components/inputs/StringEnumInput.vue' -import ObjectInput, { objectInputSchema } from '../components/inputs/ObjectInput.vue' -import ArrayInput, { arrayInputSchema } from '../components/inputs/ArrayInput.vue' - -// List of available inputs. -const availableInputs = [ - { id: 'string', schema: stringInputSchema, component: StringInput }, - { id: 'number', schema: numberInputSchema, component: NumberInput }, - { id: 'boolean', schema: booleanInputSchema, component: BooleanInput }, - { id: 'stringEnum', schema: stringEnumInputSchema, component: StringEnumInput }, - { id: 'object', schema: objectInputSchema, component: ObjectInput }, - { id: 'array', schema: arrayInputSchema, component: ArrayInput } -] - -export function usePropSchema() { - function resolveInputSchema(schema: PropertyMeta['schema']): { schema: PropertyMeta['schema'], input: any } | undefined { - // Return the first input in the list of available inputs that matches the schema. - for (const input of availableInputs) { - const result = input.schema.safeParse(schema) - if (result.success) { - // Returns the output from zod to get the transformed output. - // It only includes attributes defined in the zod schema. - return { schema: result.data as PropertyMeta['schema'], input } - } - } - - if (typeof schema === 'string') return - - // If the schema is a complex enum or array return the first nested schema that matches an input. - if (schema.kind === 'enum' && schema.schema) { - const enumSchemas = typeof schema.schema === 'object' ? Object.values(schema.schema) : schema.schema - for (const enumSchema of enumSchemas) { - const result = resolveInputSchema(enumSchema) - if (result) return result - } - } - } - - return { resolveInputSchema } -} diff --git a/devtools/app/composables/useShiki.ts b/devtools/app/composables/useShiki.ts deleted file mode 100644 index 1f55e375..00000000 --- a/devtools/app/composables/useShiki.ts +++ /dev/null @@ -1,34 +0,0 @@ -import { createHighlighterCore } from 'shiki/core' -import type { BuiltinLanguage, HighlighterCore } from 'shiki' -import MaterialThemeLighter from 'shiki/themes/material-theme-lighter.mjs' -import MaterialThemePalenight from 'shiki/themes/material-theme-palenight.mjs' -import VueLang from 'shiki/langs/vue.mjs' -import MarkdownLang from 'shiki/langs/markdown.mjs' -import { createOnigurumaEngine } from 'shiki/engine/oniguruma' - -export const highlighter = shallowRef() - -// A custom composable for syntax highlighting with Shiki since `@nuxt/mdc` relies on -// a server endpoint to highlight code. -export function useShiki() { - async function codeToHtml(code: string, lang: BuiltinLanguage | 'text' = 'text') { - if (!highlighter.value) { - highlighter.value = await createHighlighterCore({ - themes: [MaterialThemeLighter, MaterialThemePalenight], - langs: [VueLang, MarkdownLang], - engine: createOnigurumaEngine(import('shiki/wasm')) - }) - } - - return highlighter.value.codeToHtml(code, { - lang, - themes: { - dark: 'material-theme-palenight', - default: 'material-theme-lighter', - light: 'material-theme-lighter' - } - }) - } - - return { codeToHtml } -} diff --git a/devtools/app/plugins/prettier.client.ts b/devtools/app/plugins/prettier.client.ts deleted file mode 100644 index 70a0b964..00000000 --- a/devtools/app/plugins/prettier.client.ts +++ /dev/null @@ -1,54 +0,0 @@ -import type { Options } from 'prettier' -import PrettierWorker from '@/workers/prettier.js?worker&inline' - -export interface SimplePrettier { - format: (source: string, options?: Options) => Promise -} - -function createPrettierWorkerApi(worker: Worker): SimplePrettier { - let counter = 0 - const handlers: any = {} - - worker.addEventListener('message', (event) => { - const { uid, message, error } = event.data - - if (!handlers[uid]) { - return - } - - const [resolve, reject] = handlers[uid] - // eslint-disable-next-line @typescript-eslint/no-dynamic-delete - delete handlers[uid] - - if (error) { - reject(error) - } else { - resolve(message) - } - }) - - function postMessage(message: any) { - const uid = ++counter - return new Promise((resolve, reject) => { - handlers[uid] = [resolve, reject] - worker.postMessage({ uid, message }) - }) - } - - return { - format(source: string, options?: Options) { - return postMessage({ type: 'format', source, options }) - } - } -} - -export default defineNuxtPlugin(async () => { - const worker = new PrettierWorker() - const prettier = createPrettierWorkerApi(worker) - - return { - provide: { - prettier - } - } -}) diff --git a/devtools/app/workers/prettier.js b/devtools/app/workers/prettier.js deleted file mode 100644 index a636f1ce..00000000 --- a/devtools/app/workers/prettier.js +++ /dev/null @@ -1,36 +0,0 @@ -/* eslint-disable no-undef */ -self.onmessage = async function (event) { - self.postMessage({ - uid: event.data.uid, - message: await handleMessage(event.data.message) - }) -} - -function handleMessage(message) { - switch (message.type) { - case 'format': - return handleFormatMessage(message) - } -} - -async function handleFormatMessage(message) { - if (!globalThis.prettier) { - await Promise.all([ - import('https://unpkg.com/prettier@3.5.0/standalone.js'), - import('https://unpkg.com/prettier@3.5.0/plugins/html.js'), - import('https://unpkg.com/prettier@3.5.0/plugins/postcss.js'), - import('https://unpkg.com/prettier@3.5.0/plugins/babel.js'), - import('https://unpkg.com/prettier@3.5.0/plugins/estree.js'), - import('https://unpkg.com/prettier@3.5.0/plugins/typescript.js') - ]) - } - - const { options, source } = message - const formatted = await prettier.format(source, { - parser: 'vue', - plugins: prettierPlugins, - ...options - }) - - return formatted -} diff --git a/devtools/nuxt.config.ts b/devtools/nuxt.config.ts deleted file mode 100644 index a7ef7a41..00000000 --- a/devtools/nuxt.config.ts +++ /dev/null @@ -1,38 +0,0 @@ -import { resolve } from 'node:path' - -export default defineNuxtConfig({ - - modules: ['../src/module', '@nuxt/test-utils/module'], - - ssr: false, - - devtools: { enabled: false }, - - app: { - baseURL: '/__nuxt_ui__/devtools' - }, - - future: { - compatibilityVersion: 4 - }, - compatibilityDate: '2024-04-03', - - nitro: { - hooks: { - 'prerender:routes': function (routes) { - routes.clear() - } - }, - output: { - publicDir: resolve(__dirname, '../dist/client/devtools') - } - }, - - vite: { - server: { - hmr: { - clientPort: process.env.PORT ? +process.env.PORT : undefined - } - } - } -}) diff --git a/devtools/package.json b/devtools/package.json deleted file mode 100644 index 64f9cadd..00000000 --- a/devtools/package.json +++ /dev/null @@ -1,19 +0,0 @@ -{ - "name": "@nuxt/ui-devtools", - "private": true, - "type": "module", - "scripts": { - "build": "nuxt build", - "dev": "nuxt dev", - "generate": "nuxt generate", - "preview": "nuxt preview", - "test": "vitest" - }, - "dependencies": { - "@nuxt/ui": "latest", - "knitwork": "^1.2.0", - "nuxt": "^3.15.4", - "prettier": "^3.5.2", - "zod": "^3.24.2" - } -} diff --git a/devtools/public/favicon.svg b/devtools/public/favicon.svg deleted file mode 100644 index 20be0c71..00000000 --- a/devtools/public/favicon.svg +++ /dev/null @@ -1 +0,0 @@ - diff --git a/devtools/test/composables/usePropSchema.test.ts b/devtools/test/composables/usePropSchema.test.ts deleted file mode 100644 index 68c102d4..00000000 --- a/devtools/test/composables/usePropSchema.test.ts +++ /dev/null @@ -1,24 +0,0 @@ -// @vitest-environment node -import { it, expect, describe } from 'vitest' -import { usePropSchema } from '../../app/composables/usePropSchema' -import { stringSchema, optionalStringSchema, booleanSchema, numberSchema, optionalNumberSchema, optionalBooleanSchema, objectSchema, arraySchema, arrayOptionalSchema, stringEnumSchema } from '../fixtures/schemas' - -describe('usePropSchema', () => { - const { resolveInputSchema } = usePropSchema() - - it.each([ - ['string', { schema: stringSchema, inputId: 'string' }], - ['optional string', { schema: optionalStringSchema, inputId: 'string' }], - ['number', { schema: numberSchema, inputId: 'number' }], - ['optional number', { schema: optionalNumberSchema, inputId: 'number' }], - ['boolean', { schema: booleanSchema, inputId: 'boolean' }], - ['string enum', { schema: stringEnumSchema, inputId: 'stringEnum' }], - ['object', { schema: objectSchema, inputId: 'object' }], - ['optional boolean', { schema: optionalBooleanSchema, inputId: 'boolean' }], - ['array', { schema: arraySchema, inputId: 'array' }], - ['optional array', { schema: arrayOptionalSchema, inputId: 'array' }] - ])('resolveInputSchema should resolve %s schema', async (_: string, options) => { - const result = resolveInputSchema(options.schema as any) - expect(result?.input.id).toBe(options.inputId) - }) -}) diff --git a/devtools/test/fixtures/schemas.ts b/devtools/test/fixtures/schemas.ts deleted file mode 100644 index bc33a14e..00000000 --- a/devtools/test/fixtures/schemas.ts +++ /dev/null @@ -1,133 +0,0 @@ -export const stringSchema = 'string' as const - -export const optionalStringSchema = { - kind: 'enum', - type: 'string | undefined', - schema: { - 0: 'undefined', - 1: 'string' - } -} - -export const numberSchema = 'number' as const -export const optionalNumberSchema = { - kind: 'enum', - type: 'number | undefined', - schema: { - 0: 'undefined', - 1: 'number' - } -} - -export const booleanSchema = 'boolean' as const -export const optionalBooleanSchema = { - kind: 'enum', - type: 'boolean | undefined', - schema: { - 0: 'undefined', - 1: 'boolean' - } -} - -export const objectSchema = { - kind: 'object', - type: 'AccordionItem', - schema: { - label: { - name: 'label', - global: false, - description: '', - tags: [], - required: false, - type: 'string | undefined', - schema: { - kind: 'enum', - type: 'string | undefined', - schema: { - 0: 'undefined', - 1: 'string' - } - } - } - } -} - -export const arraySchema = { - kind: 'array', - type: 'AccordionItem[]', - schema: [ - { - kind: 'object', - type: 'AccordionItem', - schema: { - label: { - name: 'label', - global: false, - description: '', - tags: [], - required: false, - type: 'string | undefined', - schema: { - kind: 'enum', - type: 'string | undefined', - schema: { - 0: 'undefined', - 1: 'string' - } - } - } - } - } - ] -} - -export const arrayOptionalSchema = { - kind: 'enum', - type: 'AccordionItem[] | undefined', - schema: { - 0: 'undefined', - 1: { - kind: 'array', - type: 'AccordionItem[]', - schema: [ - { - kind: 'object', - type: 'AccordionItem', - schema: { - label: { - name: 'label', - global: false, - description: '', - tags: [], - required: false, - type: 'string | undefined', - schema: { - kind: 'enum', - type: 'string | undefined', - schema: { - 0: 'undefined', - 1: 'string' - } - } - } - } - } - ] - } - } -} - -export const stringEnumSchema = { - kind: 'enum', - type: '"true" | "false" | "page" | "step" | "location" | "date" | "time" | undefined', - schema: { - 0: 'undefined', - 1: '"true"', - 2: '"false"', - 3: '"page"', - 4: '"step"', - 5: '"location"', - 6: '"date"', - 7: '"time"' - } -} diff --git a/devtools/test/vitest.config.ts b/devtools/test/vitest.config.ts deleted file mode 100644 index d297d232..00000000 --- a/devtools/test/vitest.config.ts +++ /dev/null @@ -1,7 +0,0 @@ -import { defineVitestConfig } from '@nuxt/test-utils/config' - -export default defineVitestConfig({ - test: { - environment: 'nuxt' - } -}) diff --git a/devtools/tsconfig.json b/devtools/tsconfig.json deleted file mode 100644 index a746f2a7..00000000 --- a/devtools/tsconfig.json +++ /dev/null @@ -1,4 +0,0 @@ -{ - // https://nuxt.com/docs/guide/concepts/typescript - "extends": "./.nuxt/tsconfig.json" -} diff --git a/docs/app/composables/useLinks.ts b/docs/app/composables/useLinks.ts index 6eb79e32..b4e377c4 100644 --- a/docs/app/composables/useLinks.ts +++ b/docs/app/composables/useLinks.ts @@ -78,12 +78,35 @@ export function useLinks() { }] }, { label: 'Figma', - icon: 'i-lucide-figma', + icon: 'i-simple-icons-figma', to: '/figma' }, { - label: 'Roadmap', - icon: 'i-lucide-map', - to: '/roadmap' + label: 'Community', + icon: 'i-lucide-users', + children: [{ + label: 'Roadmap', + description: 'Track our development progress in real-time.', + icon: 'i-lucide-map', + to: '/roadmap' + }, { + label: 'Devtools Integration', + description: 'Integrate Nuxt UI with Nuxt Devtools with Compodium.', + icon: 'i-lucide-code', + to: 'https://github.com/romhml/compodium', + target: '_blank' + }, { + label: 'Raycast Extension', + description: 'Access Nuxt UI components without leaving your editor.', + icon: 'i-simple-icons-raycast', + to: 'https://github.com/HugoRCD/nuxt-ui-raycast-extension', + target: '_blank' + }, { + label: 'Figma to Code', + description: 'Convert Figma designs to Nuxt UI code.', + icon: 'i-simple-icons-figma', + to: 'https://github.com/Justineo/tempad-dev-plugin-nuxt-ui', + target: '_blank' + }] }, { label: 'Releases', icon: 'i-lucide-rocket', diff --git a/docs/content/1.getting-started/1.index.md b/docs/content/1.getting-started/1.index.md index fb0b8db5..97b991f8 100644 --- a/docs/content/1.getting-started/1.index.md +++ b/docs/content/1.getting-started/1.index.md @@ -79,16 +79,24 @@ Learn how to install and configure Nuxt UI in a Vue project in the **Vue install ### Nuxt DevTools Integration -Nuxt UI is deeply integrated with Nuxt Devtools, providing a powerful development experience: +You can play with Nuxt UI components as well as your app components directly from Nuxt Devtools with the [compodium](https://github.com/romhml/compodium) module, providing a powerful development experience: - **Component Inspector**: Inspect and analyze Nuxt UI components in real-time - **Live Preview**: Modify component props and see changes instantly - **Code Generation**: Get the corresponding code for your component configurations -::video{poster="https://res.cloudinary.com/nuxt/video/upload/so_0/v1736788078/nuxt-ui/nuxt-ui3-devtools_wbmgmc.jpg" controls class="w-full h-auto rounded"} - :source{src="https://res.cloudinary.com/nuxt/video/upload/v1736788078/nuxt-ui/nuxt-ui3-devtools_wbmgmc.webm" type="video/webm"} - :source{src="https://res.cloudinary.com/nuxt/video/upload/v1736788078/nuxt-ui/nuxt-ui3-devtools_wbmgmc.mp4" type="video/mp4"} - :source{src="https://res.cloudinary.com/nuxt/video/upload/v1736788078/nuxt-ui/nuxt-ui3-devtools_wbmgmc.ogg" type="video/ogg"} +::note +Install the module to your Nuxt application with one command: + +```bash [Terminal] +npx nuxi module add compodium +``` +:: + +::video{poster="https://res.cloudinary.com/nuxt/video/upload/so_0/v1740751953/nuxt-ui/nuxt-compodium_y2bvqw.jpg" controls class="w-full h-auto rounded"} + :source{src="https://res.cloudinary.com/nuxt/video/upload/v1740751953/nuxt-ui/nuxt-compodium_y2bvqw.webm" type="video/webm"} + :source{src="https://res.cloudinary.com/nuxt/video/upload/v1740751953/nuxt-ui/nuxt-compodium_y2bvqw.mp4" type="video/mp4"} + :source{src="https://res.cloudinary.com/nuxt/video/upload/v1740751953/nuxt-ui/nuxt-compodium_y2bvqw.ogg" type="video/ogg"} :: ## Migration diff --git a/docs/content/1.getting-started/2.installation/1.nuxt.md b/docs/content/1.getting-started/2.installation/1.nuxt.md index 4382685a..eaea3920 100644 --- a/docs/content/1.getting-started/2.installation/1.nuxt.md +++ b/docs/content/1.getting-started/2.installation/1.nuxt.md @@ -219,23 +219,6 @@ export default defineNuxtConfig({ This option adds the `transition-colors` class on components with hover or active states. :: -### `devtools.enabled` - -Use the `devtools.enabled` option to enable or disable the Nuxt UI devtools. - -- Default: `true`{lang="ts-type"} - -```ts [nuxt.config.ts] -export default defineNuxtConfig({ - modules: ['@nuxt/ui'], - ui: { - devtools: { - enabled: false - } - } -}) -``` - ## Continuous Releases Nuxt UI v3 uses [pkg.pr.new](https://github.com/stackblitz-labs/pkg.pr.new) for continuous preview releases, providing developers with instant access to the latest features and bug fixes without waiting for official releases. diff --git a/docs/content/1.getting-started/contribution.md b/docs/content/1.getting-started/contribution.md index ebb7d992..ff9240a3 100644 --- a/docs/content/1.getting-started/contribution.md +++ b/docs/content/1.getting-started/contribution.md @@ -37,7 +37,6 @@ The documentation lives in the `docs` folder as a Nuxt app using `@nuxt/content` The module code resides in the `src` folder. Here's a breakdown of its structure: ```bash -├── devtools/ ├── plugins/ ├── runtime/ │ ├── components/ # Where all the components are located diff --git a/docs/nuxt.config.ts b/docs/nuxt.config.ts index db5c09d5..8b3bdc76 100644 --- a/docs/nuxt.config.ts +++ b/docs/nuxt.config.ts @@ -38,7 +38,9 @@ export default defineNuxtConfig({ } }, - devtools: { enabled: true }, + devtools: { + enabled: true + }, app: { head: { diff --git a/eslint.config.mjs b/eslint.config.mjs index 41fe1a28..7844e440 100644 --- a/eslint.config.mjs +++ b/eslint.config.mjs @@ -16,6 +16,4 @@ export default createConfigForNuxt({ '@typescript-eslint/ban-types': 'off', '@typescript-eslint/no-empty-object-type': 'off', '@typescript-eslint/no-explicit-any': 'off' -}).prepend({ - ignores: ['src/devtools/.component-meta'] }) diff --git a/package.json b/package.json index d7ec9c8d..7aa82e54 100644 --- a/package.json +++ b/package.json @@ -58,21 +58,18 @@ "vue-plugin.d.ts" ], "scripts": { - "build": "nuxt-module-build build && pnpm devtools:build", + "build": "nuxt-module-build build", "prepack": "pnpm build", "dev": "DEV=true nuxi dev playground", "dev:vue": "DEV=true vite playground-vue", "dev:build": "nuxi build playground", - "dev:prepare": "nuxt-module-build build --stub && nuxt-module-build prepare && nuxi prepare playground && nuxi prepare docs && nuxi prepare devtools && vite build playground-vue", - "devtools": "NUXT_UI_DEVTOOLS_LOCAL=true nuxi dev playground", - "devtools:build": "nuxi generate devtools", - "devtools:prepare": "DEVTOOLS=true nuxt-component-meta playground --outputDir ../src/devtools/.component-meta/", + "dev:prepare": "nuxt-module-build build --stub && nuxt-module-build prepare && nuxi prepare playground && nuxi prepare docs && vite build playground-vue", "docs": "DEV=true nuxi dev docs", "docs:build": "nuxi build docs", "docs:prepare": "nuxt-component-meta docs", "lint": "eslint .", "lint:fix": "eslint . --fix", - "typecheck": "vue-tsc --noEmit && nuxi typecheck playground && nuxi typecheck docs && nuxi typecheck devtools && cd playground-vue && vue-tsc --noEmit", + "typecheck": "vue-tsc --noEmit && nuxi typecheck playground && nuxi typecheck docs && cd playground-vue && vue-tsc --noEmit", "test": "vitest", "test:vue": "vitest -c vitest.vue.config.ts", "test:vue:build": "vite build playground-vue", @@ -82,7 +79,6 @@ "@iconify/vue": "^4.3.0", "@internationalized/date": "^3.7.0", "@internationalized/number": "^3.6.0", - "@nuxt/devtools-kit": "^2.1.0", "@nuxt/fonts": "^0.10.3", "@nuxt/icon": "^1.10.3", "@nuxt/kit": "^3.15.4", @@ -105,7 +101,6 @@ "embla-carousel-vue": "^8.5.2", "embla-carousel-wheel-gestures": "^8.0.1", "fuse.js": "^7.1.0", - "get-port-please": "^3.1.2", "knitwork": "^1.2.0", "magic-string": "^0.30.17", "mlly": "^1.7.4", @@ -113,7 +108,6 @@ "pathe": "^2.0.3", "reka-ui": "^2.0.0", "scule": "^1.3.0", - "sirv": "^3.0.1", "tailwind-variants": "^0.3.1", "tailwindcss": "^4.0.9", "tinyglobby": "^0.2.12", @@ -133,9 +127,7 @@ "eslint": "^9.21.0", "happy-dom": "^17.1.2", "joi": "^17.13.3", - "knitwork": "^1.2.0", "nuxt": "^3.15.4", - "nuxt-component-meta": "^0.10.0", "release-it": "^18.1.2", "superstruct": "^2.0.2", "valibot": "^0.42.1", diff --git a/playground/nuxt.config.ts b/playground/nuxt.config.ts index 571cc6cc..da045551 100644 --- a/playground/nuxt.config.ts +++ b/playground/nuxt.config.ts @@ -1,7 +1,3 @@ -import { createResolver } from '@nuxt/kit' - -const { resolve } = createResolver(import.meta.url) - export default defineNuxtConfig({ modules: [ '../src/module', @@ -14,27 +10,9 @@ export default defineNuxtConfig({ css: ['~/assets/css/main.css'], - ui: { - fonts: !process.env.DEVTOOLS - }, - future: { compatibilityVersion: 4 }, - compatibilityDate: '2024-07-09', - - // @ts-expect-error - `nuxt-component-meta` is used as CLI - componentMeta: { - exclude: [ - resolve('./app/components') - ], - metaFields: { - type: false, - props: true, - slots: true, - events: false, - exposed: false - } - } + compatibilityDate: '2024-07-09' }) diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 76d8fef2..e4031f98 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -29,9 +29,6 @@ importers: '@internationalized/number': specifier: ^3.6.0 version: 3.6.0 - '@nuxt/devtools-kit': - specifier: ^2.1.0 - version: 2.1.0(magicast@0.3.5)(rollup@4.32.1)(vite@6.2.0(@types/node@22.13.5)(jiti@2.4.2)(lightningcss@1.29.1)(terser@5.39.0)(yaml@2.7.0)) '@nuxt/fonts': specifier: ^0.10.3 version: 0.10.3(db0@0.2.4(better-sqlite3@11.8.1))(ioredis@5.5.0)(magicast@0.3.5)(rollup@4.32.1)(vite@6.2.0(@types/node@22.13.5)(jiti@2.4.2)(lightningcss@1.29.1)(terser@5.39.0)(yaml@2.7.0)) @@ -98,9 +95,6 @@ importers: fuse.js: specifier: ^7.1.0 version: 7.1.0 - get-port-please: - specifier: ^3.1.2 - version: 3.1.2 knitwork: specifier: ^1.2.0 version: 1.2.0 @@ -122,9 +116,6 @@ importers: scule: specifier: ^1.3.0 version: 1.3.0 - sirv: - specifier: ^3.0.1 - version: 3.0.1 tailwind-variants: specifier: ^0.3.1 version: 0.3.1(tailwindcss@4.0.9) @@ -183,9 +174,6 @@ importers: nuxt: specifier: ^3.15.4 version: 3.15.4(@parcel/watcher@2.5.1)(@types/node@22.13.5)(better-sqlite3@11.8.1)(db0@0.2.4(better-sqlite3@11.8.1))(eslint@9.21.0(jiti@2.4.2))(ioredis@5.5.0)(lightningcss@1.29.1)(magicast@0.3.5)(optionator@0.9.4)(rollup@4.32.1)(terser@5.39.0)(typescript@5.6.3)(vite@6.2.0(@types/node@22.13.5)(jiti@2.4.2)(lightningcss@1.29.1)(terser@5.39.0)(yaml@2.7.0))(vue-tsc@2.2.0(typescript@5.6.3))(yaml@2.7.0) - nuxt-component-meta: - specifier: ^0.10.0 - version: 0.10.0(magicast@0.3.5)(rollup@4.32.1) release-it: specifier: ^18.1.2 version: 18.1.2(@types/node@22.13.5)(typescript@5.6.3) @@ -226,24 +214,6 @@ importers: specifier: ^1.3.0 version: 1.3.0 - devtools: - dependencies: - '@nuxt/ui': - specifier: workspace:* - version: link:.. - knitwork: - specifier: ^1.2.0 - version: 1.2.0 - nuxt: - specifier: ^3.15.4 - version: 3.15.4(@parcel/watcher@2.5.1)(@types/node@22.13.5)(better-sqlite3@11.8.1)(db0@0.2.4(better-sqlite3@11.8.1))(eslint@9.21.0(jiti@2.4.2))(ioredis@5.5.0)(lightningcss@1.29.1)(magicast@0.3.5)(optionator@0.9.4)(rollup@4.32.1)(terser@5.39.0)(typescript@5.6.3)(vite@6.2.0(@types/node@22.13.5)(jiti@2.4.2)(lightningcss@1.29.1)(terser@5.39.0)(yaml@2.7.0))(vue-tsc@2.2.0(typescript@5.6.3))(yaml@2.7.0) - prettier: - specifier: ^3.5.2 - version: 3.5.2 - zod: - specifier: ^3.24.2 - version: 3.24.2 - docs: dependencies: '@iconify-json/logos': diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index 84024be0..7dd585fd 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -2,6 +2,5 @@ packages: - "./" - "cli" - "docs" - - "devtools" - "playground" - "playground-vue" diff --git a/src/defaults.ts b/src/defaults.ts index ccc44df7..0a88d6a6 100644 --- a/src/defaults.ts +++ b/src/defaults.ts @@ -22,9 +22,6 @@ export const defaultOptions = { theme: { colors: undefined, transitions: true - }, - devtools: { - enabled: true } } diff --git a/src/devtools/meta.ts b/src/devtools/meta.ts deleted file mode 100644 index abe21e28..00000000 --- a/src/devtools/meta.ts +++ /dev/null @@ -1,148 +0,0 @@ -import type { ViteDevServer } from 'vite' -import { kebabCase, camelCase } from 'scule' -import defu from 'defu' -import fs from 'node:fs' -import type { Resolver } from '@nuxt/kit' -import type { ComponentMeta } from 'vue-component-meta' -import type { DevtoolsMeta } from '../runtime/composables/extendDevtoolsMeta' -import type { ModuleOptions } from '../module' - -export type Component = { - slug: string - label: string - meta?: ComponentMeta & { devtools: DevtoolsMeta } - defaultVariants: Record -} - -const devtoolsComponentMeta: Record = {} - -function extractDevtoolsMeta(code: string): string | null { - const match = code.match(/extendDevtoolsMeta(?:<.*?>)?\(/) - if (!match) return null - - const startIndex = code.indexOf(match[0]) + match[0].length - let openBraceCount = 0 - let closeBraceCount = 0 - let endIndex = startIndex - - for (let i = startIndex; i < code.length; i++) { - if (code[i] === '{') openBraceCount++ - if (code[i] === '}') closeBraceCount++ - - if (openBraceCount > 0 && openBraceCount === closeBraceCount) { - endIndex = i + 1 - break - } - } - // Return only the object inside extendDevtoolsMeta - return code.slice(startIndex, endIndex).trim() -} - -// A Plugin to parse additional metadata for the Nuxt UI Devtools. -export function devtoolsMetaPlugin({ resolve, options, templates }: { resolve: Resolver['resolve'], options: ModuleOptions, templates: Record }) { - return { - name: 'ui-devtools-component-meta', - enforce: 'pre' as const, - - async transform(code: string, id: string) { - if (!id.match(/\/runtime\/components\/\w+.vue/)) return - const fileName = id.split('/')[id.split('/').length - 1] - - if (code && fileName) { - const slug = kebabCase(fileName.replace(/\..*/, '')) - const match = extractDevtoolsMeta(code) - - if (match) { - const metaObject = new Function(`return ${match}`)() - devtoolsComponentMeta[slug] = { meta: { devtools: { ...metaObject } } } - } - } - - return { - code - } - }, - - configureServer(server: ViteDevServer) { - server.middlewares.use('/__nuxt_ui__/devtools/api/component-meta', async (_req, res) => { - res.setHeader('Content-Type', 'application/json') - try { - const componentMeta = await import('./.component-meta/component-meta') - - const meta = defu( - Object.entries(componentMeta.default).reduce((acc, [key, value]: [string, any]) => { - if (!key.startsWith('U')) return acc - - const name = key.substring(1) - const slug = kebabCase(name) - const template = templates?.[camelCase(name)] - - if (devtoolsComponentMeta[slug] === undefined) { - const path = resolve(`./runtime/components/${name}.vue`) - const code = fs.readFileSync(path, 'utf-8') - const match = extractDevtoolsMeta(code) - if (match) { - const metaObject = new Function(`return ${match}`)() - devtoolsComponentMeta[slug] = { meta: { devtools: { ...metaObject } } } - } else { - devtoolsComponentMeta[slug] = null - } - } - - value.meta.props = value.meta.props.map((prop: any) => { - let defaultValue = prop.default - ? prop.default - : prop?.tags?.find((tag: any) => - tag.name === 'defaultValue' - && !tag.text?.includes('appConfig'))?.text - ?? template?.defaultVariants?.[prop.name] - - if (typeof defaultValue === 'string') defaultValue = defaultValue?.replace(/\s+as\s+\w+$/g, '').replaceAll(/["'`]/g, '') - if (defaultValue === 'true') defaultValue = true - if (defaultValue === 'false') defaultValue = false - if (!Number.isNaN(Number.parseInt(defaultValue))) defaultValue = Number.parseInt(defaultValue) - - return { - ...prop, - default: defaultValue - } - }) - - const label = key.replace(/^U/, options.prefix ?? 'U') - acc[kebabCase(key.replace(/^U/, ''))] = { ...value, label, slug } - return acc - }, {} as Record), - devtoolsComponentMeta - ) - res.end(JSON.stringify(meta)) - } catch (error) { - console.error(`Failed to fetch component meta`, error) - res.statusCode = 500 - res.end(JSON.stringify({ error: 'Failed to fetch component meta' })) - } - }) - - server.middlewares.use('/__nuxt_ui__/devtools/api/component-example', async (req, res) => { - const query = new URL(req.url!, 'http://localhost').searchParams - const name = query.get('component') - if (!name) { - res.statusCode = 400 - res.end(JSON.stringify({ error: 'Component name is required' })) - return - } - - try { - const path = resolve(`./devtools/runtime/examples/${name}.vue`) - const source = fs.readFileSync(path, 'utf-8') - - res.setHeader('Content-Type', 'application/json') - res.end(JSON.stringify({ component: name, source })) - } catch (error) { - console.error(`Failed to read component source for ${name}:`, error) - res.statusCode = 500 - res.end(JSON.stringify({ error: 'Failed to read component source' })) - } - }) - } - } -} diff --git a/src/devtools/runtime/DevtoolsRenderer.vue b/src/devtools/runtime/DevtoolsRenderer.vue deleted file mode 100644 index 719a840b..00000000 --- a/src/devtools/runtime/DevtoolsRenderer.vue +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - - - - - diff --git a/src/devtools/runtime/examples/AvatarGroupExample.vue b/src/devtools/runtime/examples/AvatarGroupExample.vue deleted file mode 100644 index 805b964a..00000000 --- a/src/devtools/runtime/examples/AvatarGroupExample.vue +++ /dev/null @@ -1,7 +0,0 @@ - - - - - - - diff --git a/src/devtools/runtime/examples/ButtonGroupExample.vue b/src/devtools/runtime/examples/ButtonGroupExample.vue deleted file mode 100644 index 54d04c97..00000000 --- a/src/devtools/runtime/examples/ButtonGroupExample.vue +++ /dev/null @@ -1,8 +0,0 @@ - - - - - Button - - - diff --git a/src/devtools/runtime/examples/CardExample.vue b/src/devtools/runtime/examples/CardExample.vue deleted file mode 100644 index dbffb692..00000000 --- a/src/devtools/runtime/examples/CardExample.vue +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - - - - - - diff --git a/src/devtools/runtime/examples/CarouselExample.vue b/src/devtools/runtime/examples/CarouselExample.vue deleted file mode 100644 index f038abd5..00000000 --- a/src/devtools/runtime/examples/CarouselExample.vue +++ /dev/null @@ -1,13 +0,0 @@ - - - - - diff --git a/src/devtools/runtime/examples/ChipExample.vue b/src/devtools/runtime/examples/ChipExample.vue deleted file mode 100644 index c0c05fdc..00000000 --- a/src/devtools/runtime/examples/ChipExample.vue +++ /dev/null @@ -1,5 +0,0 @@ - - - - - diff --git a/src/devtools/runtime/examples/CollapsibleExample.vue b/src/devtools/runtime/examples/CollapsibleExample.vue deleted file mode 100644 index 48d7251a..00000000 --- a/src/devtools/runtime/examples/CollapsibleExample.vue +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/src/devtools/runtime/examples/CommandPaletteExample.vue b/src/devtools/runtime/examples/CommandPaletteExample.vue deleted file mode 100644 index 1ac15634..00000000 --- a/src/devtools/runtime/examples/CommandPaletteExample.vue +++ /dev/null @@ -1,29 +0,0 @@ - - - - - diff --git a/src/devtools/runtime/examples/ContainerExample.vue b/src/devtools/runtime/examples/ContainerExample.vue deleted file mode 100644 index da04c08e..00000000 --- a/src/devtools/runtime/examples/ContainerExample.vue +++ /dev/null @@ -1,5 +0,0 @@ - - - - - diff --git a/src/devtools/runtime/examples/ContextMenuExample.vue b/src/devtools/runtime/examples/ContextMenuExample.vue deleted file mode 100644 index 0a1d00ae..00000000 --- a/src/devtools/runtime/examples/ContextMenuExample.vue +++ /dev/null @@ -1,5 +0,0 @@ - - - - - diff --git a/src/devtools/runtime/examples/DrawerExample.vue b/src/devtools/runtime/examples/DrawerExample.vue deleted file mode 100644 index 125804e6..00000000 --- a/src/devtools/runtime/examples/DrawerExample.vue +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/src/devtools/runtime/examples/DropdownMenuExample.vue b/src/devtools/runtime/examples/DropdownMenuExample.vue deleted file mode 100644 index 49cc937e..00000000 --- a/src/devtools/runtime/examples/DropdownMenuExample.vue +++ /dev/null @@ -1,5 +0,0 @@ - - - - - diff --git a/src/devtools/runtime/examples/FormExample.vue b/src/devtools/runtime/examples/FormExample.vue deleted file mode 100644 index 199afddd..00000000 --- a/src/devtools/runtime/examples/FormExample.vue +++ /dev/null @@ -1,30 +0,0 @@ - - - - - - - - - - - - Submit - - - diff --git a/src/devtools/runtime/examples/FormFieldExample.vue b/src/devtools/runtime/examples/FormFieldExample.vue deleted file mode 100644 index a0be07b1..00000000 --- a/src/devtools/runtime/examples/FormFieldExample.vue +++ /dev/null @@ -1,5 +0,0 @@ - - - - - diff --git a/src/devtools/runtime/examples/LinkExample.vue b/src/devtools/runtime/examples/LinkExample.vue deleted file mode 100644 index e5cbd6bc..00000000 --- a/src/devtools/runtime/examples/LinkExample.vue +++ /dev/null @@ -1,5 +0,0 @@ - - - Link - - diff --git a/src/devtools/runtime/examples/ModalExample.vue b/src/devtools/runtime/examples/ModalExample.vue deleted file mode 100644 index d4c6ef2c..00000000 --- a/src/devtools/runtime/examples/ModalExample.vue +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/src/devtools/runtime/examples/PopoverExample.vue b/src/devtools/runtime/examples/PopoverExample.vue deleted file mode 100644 index a02ef4ec..00000000 --- a/src/devtools/runtime/examples/PopoverExample.vue +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/src/devtools/runtime/examples/SkeletonExample.vue b/src/devtools/runtime/examples/SkeletonExample.vue deleted file mode 100644 index 5b2fab1e..00000000 --- a/src/devtools/runtime/examples/SkeletonExample.vue +++ /dev/null @@ -1,3 +0,0 @@ - - - diff --git a/src/devtools/runtime/examples/SlideoverExample.vue b/src/devtools/runtime/examples/SlideoverExample.vue deleted file mode 100644 index 79a07dc7..00000000 --- a/src/devtools/runtime/examples/SlideoverExample.vue +++ /dev/null @@ -1,8 +0,0 @@ - - - - - - - - diff --git a/src/devtools/runtime/examples/StepperExample.vue b/src/devtools/runtime/examples/StepperExample.vue deleted file mode 100644 index e92d4df8..00000000 --- a/src/devtools/runtime/examples/StepperExample.vue +++ /dev/null @@ -1,44 +0,0 @@ - - - - - - - {{ item.title }} - - - - Back - - - Next - - - - - diff --git a/src/devtools/runtime/examples/ToasterExample.vue b/src/devtools/runtime/examples/ToasterExample.vue deleted file mode 100644 index 96e97536..00000000 --- a/src/devtools/runtime/examples/ToasterExample.vue +++ /dev/null @@ -1,11 +0,0 @@ - - - - - - - diff --git a/src/devtools/runtime/examples/TooltipExample.vue b/src/devtools/runtime/examples/TooltipExample.vue deleted file mode 100644 index 8d950aa0..00000000 --- a/src/devtools/runtime/examples/TooltipExample.vue +++ /dev/null @@ -1,5 +0,0 @@ - - - - - diff --git a/src/module.ts b/src/module.ts index cf84046f..ee9fadbf 100644 --- a/src/module.ts +++ b/src/module.ts @@ -1,10 +1,6 @@ import { defu } from 'defu' -import { createResolver, defineNuxtModule, addComponentsDir, addImportsDir, addVitePlugin, addPlugin, installModule, extendPages, hasNuxtModule } from '@nuxt/kit' -import { addTemplates, buildTemplates } from './templates' -import { addCustomTab, startSubprocess } from '@nuxt/devtools-kit' -import sirv from 'sirv' -import { getPort } from 'get-port-please' -import { devtoolsMetaPlugin } from './devtools/meta' +import { createResolver, defineNuxtModule, addComponentsDir, addImportsDir, addVitePlugin, addPlugin, installModule, hasNuxtModule } from '@nuxt/kit' +import { addTemplates } from './templates' import { defaultOptions, getDefaultUiConfig, resolveColors } from './defaults' export type * from './runtime/types' @@ -50,17 +46,6 @@ export interface ModuleOptions { */ transitions?: boolean } - - /** - * Configuration for the Nuxt UI devtools. - */ - devtools?: { - /** - * Enable or disable Nuxt UI devtools. - * @defaultValue `true` - */ - enabled?: boolean - } } export default defineNuxtModule({ @@ -123,79 +108,5 @@ export default defineNuxtModule({ addImportsDir(resolve('./runtime/composables')) addTemplates(options, nuxt, resolve) - - if (nuxt.options.dev && nuxt.options.devtools.enabled && options.devtools?.enabled) { - const templates = buildTemplates(options) - nuxt.options.vite = defu(nuxt.options?.vite, { plugins: [devtoolsMetaPlugin({ resolve, templates, options })] }) - - // Runs UI devtools in a subprocess for local development - if (process.env.NUXT_UI_DEVTOOLS_LOCAL) { - const PORT = await getPort({ port: 42124 }) - nuxt.hook('app:resolve', () => { - startSubprocess( - { - command: 'pnpm', - args: ['nuxi', 'dev'], - cwd: './devtools', - stdio: 'pipe', - env: { - PORT: PORT.toString() - } - }, - { - id: 'ui:devtools:local', - name: 'Nuxt UI DevTools Local', - icon: 'logos-nuxt-icon' - }, - nuxt - ) - }) - - nuxt.hook('vite:extendConfig', (config) => { - config.server ||= {} - config.server.proxy ||= {} - config.server.proxy['/__nuxt_ui__/devtools'] = { - target: `http://localhost:${PORT}`, - changeOrigin: true, - followRedirects: true, - ws: true, - rewriteWsOrigin: true - } - }) - } else { - nuxt.hook('vite:serverCreated', async (server) => { - server.middlewares.use('/__nuxt_ui__/devtools', sirv(resolve('../dist/client/devtools'), { - single: true, - dev: true - })) - }) - } - - nuxt.options.routeRules = defu(nuxt.options.routeRules, { '/__nuxt_ui__/**': { ssr: false } }) - extendPages((pages) => { - if (pages.length) { - pages.unshift({ - name: 'ui-devtools', - path: '/__nuxt_ui__/components/:slug', - file: resolve('./devtools/runtime/DevtoolsRenderer.vue'), - meta: { - // https://github.com/nuxt/nuxt/pull/29366 - // isolate: true - layout: false - } - }) - } - }) - - addCustomTab({ - name: 'nuxt-ui', - title: 'Nuxt UI', - icon: '/__nuxt_ui__/devtools/favicon.svg', - view: { - type: 'iframe', - src: '/__nuxt_ui__/devtools' - } - }) - } } }) diff --git a/src/runtime/components/Accordion.vue b/src/runtime/components/Accordion.vue index 0178c1dd..d9c9a1ca 100644 --- a/src/runtime/components/Accordion.vue +++ b/src/runtime/components/Accordion.vue @@ -3,7 +3,6 @@ import type { AccordionRootProps, AccordionRootEmits } from 'reka-ui' import type { AppConfig } from '@nuxt/schema' import _appConfig from '#build/app.config' import theme from '#build/ui/accordion' -import { extendDevtoolsMeta } from '../composables/extendDevtoolsMeta' import { tv } from '../utils/tv' import type { DynamicSlots } from '../types/utils' @@ -54,37 +53,6 @@ export type AccordionSlots = { content: SlotProps body: SlotProps } & DynamicSlots> - -extendDevtoolsMeta({ - defaultProps: { - items: [{ - label: 'Getting Started', - icon: 'i-lucide-info', - content: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed neque elit, tristique placerat feugiat ac, facilisis vitae arcu. Proin eget egestas augue. Praesent ut sem nec arcu pellentesque aliquet. Duis dapibus diam vel metus tempus vulputate.' - }, { - label: 'Installation', - icon: 'i-lucide-download', - disabled: true, - content: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed neque elit, tristique placerat feugiat ac, facilisis vitae arcu. Proin eget egestas augue. Praesent ut sem nec arcu pellentesque aliquet. Duis dapibus diam vel metus tempus vulputate.' - }, { - label: 'Theming', - icon: 'i-lucide-pipette', - content: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed neque elit, tristique placerat feugiat ac, facilisis vitae arcu. Proin eget egestas augue. Praesent ut sem nec arcu pellentesque aliquet. Duis dapibus diam vel metus tempus vulputate.' - }, { - label: 'Layouts', - icon: 'i-lucide-layout-dashboard', - content: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed neque elit, tristique placerat feugiat ac, facilisis vitae arcu. Proin eget egestas augue. Praesent ut sem nec arcu pellentesque aliquet. Duis dapibus diam vel metus tempus vulputate.' - }, { - label: 'Components', - icon: 'i-lucide-layers-3', - content: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed neque elit, tristique placerat feugiat ac, facilisis vitae arcu. Proin eget egestas augue. Praesent ut sem nec arcu pellentesque aliquet. Duis dapibus diam vel metus tempus vulputate.' - }, { - label: 'Utilities', - icon: 'i-lucide-wrench', - content: 'Lorem ipsum dolor sit amet, consectetur adipiscing elit. Sed neque elit, tristique placerat feugiat ac, facilisis vitae arcu. Proin eget egestas augue. Praesent ut sem nec arcu pellentesque aliquet. Duis dapibus diam vel metus tempus vulputate.' - }] - } -}) diff --git a/src/runtime/components/Breadcrumb.vue b/src/runtime/components/Breadcrumb.vue index 64b9663c..af2eb387 100644 --- a/src/runtime/components/Breadcrumb.vue +++ b/src/runtime/components/Breadcrumb.vue @@ -2,7 +2,6 @@ import type { AppConfig } from '@nuxt/schema' import _appConfig from '#build/app.config' import theme from '#build/ui/breadcrumb' -import { extendDevtoolsMeta } from '../composables/extendDevtoolsMeta' import { tv } from '../utils/tv' import type { AvatarProps, LinkProps } from '../types' import type { DynamicSlots, PartialString } from '../types/utils' @@ -48,31 +47,6 @@ export type BreadcrumbSlots = { 'item-trailing': SlotProps 'separator'(props?: {}): any } & DynamicSlots> - -extendDevtoolsMeta({ - defaultProps: { - items: [ - { label: 'Home', to: '/' }, - { - slot: 'dropdown', - icon: 'i-lucide-ellipsis', - children: [{ - label: 'Documentation' - }, { - label: 'Themes' - }, { - label: 'GitHub' - }] - }, { - label: 'Components', - disabled: true - }, { - label: 'Breadcrumb', - to: '/components/breadcrumb' - } - ] - } -})
- {{ (error.data as any)?.error ?? 'Unexpected error' }} -
Ensure your app.vue file includes a <NuxtPage /> component, as the component preview is mounted as a page.
app.vue
<NuxtPage />
- {{ meta?.name }} -