feat(Icon)!: migrate from @egoist/tailwindcss-icons to new @nuxt/icon (#1789)

This commit is contained in:
Benjamin Canac
2024-06-24 12:46:41 +02:00
committed by GitHub
parent bfa2e707d8
commit c904604c23
31 changed files with 110 additions and 259 deletions

View File

@@ -32,18 +32,24 @@ The Nuxt Starter template is available from the `nuxi init` command.
npx nuxi@latest init -t ui
```
Please check [nuxt/starter](https://github.com/nuxt/starter/tree/ui) for details.
## Modules
Nuxt UI will automatically install the [@nuxtjs/tailwindcss](https://tailwindcss.nuxtjs.org/), [@nuxtjs/color-mode](https://color-mode.nuxtjs.org/) and [nuxt-icon](https://github.com/nuxt-modules/icon) modules for you.
Nuxt UI will automatically install the [@nuxt/icon](https://github.com/nuxt/icon), [@nuxtjs/tailwindcss](https://tailwindcss.nuxtjs.org/) and [@nuxtjs/color-mode](https://color-mode.nuxtjs.org/) modules for you.
::callout{icon="i-heroicons-exclamation-triangle"}
You should remove them from your `modules` and `dependencies` if you've previously installed them.
::
### `@nuxt/icon`
This module is installed to provide an easy way to use icons in your application. You can use the `UIcon` component to display any icon from Iconify.
::callout{icon="i-heroicons-light-bulb"}
You can read more about this in the [Theming](/getting-started/theming#icons) section.
::
### `@nuxtjs/tailwindcss`
This module is pre-configured and will automatically load the following plugins:
@@ -86,14 +92,6 @@ This module is installed to provide dark mode support out of the box thanks to t
You can read more about this in the [Theming](/getting-started/theming#dark-mode) section.
::
### `nuxt-icon`
This module is installed when using the `dynamic` prop on the `Icon` component or globally through the `ui.icons.dynamic` option in your `app.config.ts`.
::callout{icon="i-heroicons-light-bulb"}
You can read more about this in the [Theming](/getting-started/theming#dynamic-icons) section and on the [Icon](/components/icon) component page.
::
## TypeScript
This module is written in TypeScript and provides typings for all the components and composables. You can look at the [source code](https://github.com/nuxt/ui/tree/dev/src/runtime/types) to see all the available types.
@@ -231,7 +229,6 @@ You can also add the following to your `.vscode/settings.json` to enable Intelli
|-----------------------|-----------------|-------------------------------------------------------------------------------------------------------------|
| `prefix` | `u` | Define the prefix of the imported components. |
| `global` | `false` | Expose components globally. |
| `icons` | `['heroicons']` | Icon collections to load. |
| `safelistColors` | `['primary']` | Force safelisting of colors to need be purged. |
| `disableGlobalStyles` | `false` | Disable [global CSS styles](https://github.com/nuxt/ui/blob/dev/src/runtime/ui.css) injected by the module. |
@@ -241,8 +238,7 @@ Configure options in your `nuxt.config.ts` as such:
export default defineNuxtConfig({
modules: ['@nuxt/ui'],
ui: {
global: true,
icons: ['mdi', 'simple-icons']
global: true
}
})
```

View File

@@ -258,6 +258,7 @@ const isDark = computed({
}
})
</script>
<template>
<ClientOnly>
<UButton
@@ -277,9 +278,11 @@ const isDark = computed({
## Icons
You can use any icon (100,000+) from [Iconify](https://iconify.design/).
Thanks to [`@nuxt/icon`](https://github.com/nuxt/icon), use 200,000+ ready to use icons based on [Iconify](https://iconify.design).
Some components have an `icon` prop that allows you to add an icon to the component.
You can use any name from the https://icones.js.org collection such as the `i-` prefix (for example, `i-heroicons-cog`) with:
- any `icon` prop available across the components:
```vue
<template>
@@ -287,31 +290,17 @@ Some components have an `icon` prop that allows you to add an icon to the compon
</template>
```
You can also use the [Icon](/components/icon) component to add an icon anywhere in your app by following this pattern: `i-{collection_name}-{icon_name}`.
- the `UIcon` component to use icons anywhere:
```vue
<template>
<UIcon name="i-heroicons-moon" />
<UIcon name="i-heroicons-moon" class="w-5 h-5 text-primary-500" />
</template>
```
### Collections
By default, the module uses [Heroicons](https://heroicons.com/) but you can change it from the module options in your `nuxt.config.ts`.
```ts [nuxt.config.ts]
export default defineNuxtConfig({
ui: {
icons: ['mdi', 'simple-icons']
}
})
```
::callout{icon="i-heroicons-light-bulb"}
Search the icon you want to use on https://icones.js.org built by [@antfu](https://github.com/antfu).
::
Thanks to [@egoist/tailwindcss-icons](https://github.com/egoist/tailwindcss-icons) plugin, only the icons you use in your app will be bundled in your CSS. However, you need to install the icon collections you specified in the `ui.icons` key:
It's highly recommended to install the icons collections locally with:
::code-group
@@ -329,55 +318,11 @@ npm install @iconify-json/{collection_name}
::
If you choose to use the full `@iconify/json` icon collection (50MB), you can specifiy `icons: 'all'` or `icons: {}` in your `nuxt.config.ts` to use any icon in your app.
For example, to use the `i-uil-github` icon, install it's collection with `@iconify-json/uil`. This way the icons can be served locally or from your serverless functions, which is faster and more reliable on both SSR and client-side.
```ts [nuxt.config.ts]
export default defineNuxtConfig({
ui: {
icons: {}
}
})
```
### Custom config
If you have specific needs, like using a custom icon collection, you can use the `icons` option in your `nuxt.config.ts` as an object to override the config of the [@egoist/tailwindcss-icons](https://github.com/egoist/tailwindcss-icons#plugin-options) plugin.
```ts [nuxt.config.ts]
import { getIconCollections } from '@egoist/tailwindcss-icons'
export default defineNuxtConfig({
ui: {
icons: {
// might solve stretch bug on generate, see https://github.com/egoist/tailwindcss-icons/issues/23
extraProperties: {
'mask-size': 'contain',
'mask-position': 'center'
},
collections: {
foo: {
icons: {
'arrow-left': {
// svg body
body: '<path fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" d="M10.5 19.5L3 12m0 0l7.5-7.5M3 12h18" />',
// svg width and height, optional
width: 24,
height: 24
}
}
},
...getIconCollections(['heroicons', 'simple-icons'])
}
}
}
})
```
### Dynamic icons
The `Icon` component also has a `dynamic` prop to use the [nuxt-icon](https://github.com/nuxt-modules/icon/) module instead of the [@egoist/tailwindcss-icons](https://github.com/egoist/tailwindcss-icons#plugin-options) plugin.
Read more about this in the [Icon](/components/icon#dynamic) component page.
::callout{icon="i-heroicons-cog-6-tooth" to="https://github.com/nuxt/icon?tab=readme-ov-file#custom-local-collections" target="_blank"}
Read more about custom collections in the `@nuxt/icon` documentation.
::
### Defaults

View File

@@ -1,56 +1,5 @@
---
description: Display any icon (100,000+) from Iconify.
links:
- label: GitHub
icon: i-simple-icons-github
to: https://github.com/nuxt/ui/blob/dev/src/runtime/components/elements/Icon.vue
description: Use 200,000+ ready to use icons from Iconify.
to: https://github.com/nuxt/icon
target: _blank
---
## Usage
Use the `name` prop by following this pattern: `i-{collection_name}-{icon_name}`. You can search any icon from [Iconify](https://iconify.design/) using https://icones.js.org.
::component-card
---
props:
name: 'i-heroicons-light-bulb'
---
::
::callout{icon="i-heroicons-exclamation-triangle"}
You won't be able to use all icons in the `name` prop here as icons are bundled using [egoist/tailwindcss-icons](https://github.com/egoist/tailwindcss-icons).
::
::callout{icon="i-heroicons-light-bulb"}
Don't forget to install and specify the icon collections you need in your `nuxt.config.ts`, read more about this in [Theming](/getting-started/theming#icons).
::
### Dynamic
You can use the `dynamic` prop to enable dynamic icon loading. This will use [`nuxt-icon`](https://github.com/nuxt-modules/icon) instead and allow you to use any icon from [Iconify](https://iconify.design/) as well as the `{collection_name}:{icon_name}` pattern.
This can be quite useful when using [dynamic class names](https://tailwindcss.com/docs/content-configuration#dynamic-class-names) or for icons that are not bundled by default (fetched from a database for example).
::component-card
---
props:
name: 'i-ph-rocket-launch'
dynamic: true
---
::
You can also change the default behavior of the `dynamic` prop by setting the `ui.icons.dynamic` option in your `app.config.ts`.
```ts [app.config.ts]
export default defineAppConfig({
ui: {
icons: {
dynamic: true
}
}
})
```
## Props
:component-props

View File

@@ -34,7 +34,6 @@ export default defineNuxtConfig({
},
ui: {
global: true,
icons: ['heroicons', 'simple-icons'],
safelistColors: excludeColors(colors)
},
content: {

View File

@@ -5,6 +5,7 @@
"dependencies": {
"@iconify-json/heroicons": "^1.1.21",
"@iconify-json/simple-icons": "^1.1.107",
"@iconify-json/vscode-icons": "^1.1.34",
"@nuxt/content": "^2.13.0",
"@nuxt/eslint-config": "^0.3.13",
"@nuxt/fonts": "^0.7.0",

View File

@@ -34,10 +34,10 @@
"test": "vitest"
},
"dependencies": {
"@egoist/tailwindcss-icons": "^1.8.1",
"@headlessui/tailwindcss": "^0.2.1",
"@headlessui/vue": "^1.7.22",
"@iconify-json/heroicons": "^1.1.21",
"@nuxt/icon": "^1.0.0",
"@nuxt/kit": "^3.12.2",
"@nuxtjs/color-mode": "^3.4.1",
"@nuxtjs/tailwindcss": "^6.12.0",
@@ -51,7 +51,6 @@
"@vueuse/math": "^10.11.0",
"defu": "^6.1.4",
"fuse.js": "^6.6.2",
"nuxt-icon": "^0.6.10",
"ohash": "^1.1.3",
"pathe": "^1.1.2",
"scule": "^1.3.0",
@@ -71,8 +70,8 @@
"release-it": "^17.3.0",
"typescript": "^5.4.5",
"unbuild": "^2.0.0",
"valibot30": "npm:valibot@0.30.0",
"valibot": "^0.31.1",
"valibot30": "npm:valibot@0.30.0",
"vitest": "^1.6.0",
"vitest-environment-nuxt": "^1.0.0",
"vue-tsc": "^2.0.16",

90
pnpm-lock.yaml generated
View File

@@ -13,9 +13,6 @@ importers:
.:
dependencies:
'@egoist/tailwindcss-icons':
specifier: ^1.8.1
version: 1.8.1(tailwindcss@3.4.4)
'@headlessui/tailwindcss':
specifier: ^0.2.1
version: 0.2.1(tailwindcss@3.4.4)
@@ -25,6 +22,9 @@ importers:
'@iconify-json/heroicons':
specifier: ^1.1.21
version: 1.1.21
'@nuxt/icon':
specifier: ^1.0.0
version: 1.0.0(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@3.29.4))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@3.29.4)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@3.29.4))(postcss@8.4.38)(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue@3.4.29(typescript@5.4.5))
'@nuxt/kit':
specifier: ^3.12.2
version: 3.12.2(magicast@0.3.4)(rollup@3.29.4)
@@ -64,9 +64,6 @@ importers:
fuse.js:
specifier: ^6.6.2
version: 6.6.2
nuxt-icon:
specifier: ^0.6.10
version: 0.6.10(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@3.29.4))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@3.29.4)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@3.29.4))(postcss@8.4.38)(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue@3.4.29(typescript@5.4.5))
ohash:
specifier: ^1.1.3
version: 1.1.3
@@ -149,6 +146,9 @@ importers:
'@iconify-json/simple-icons':
specifier: ^1.1.107
version: 1.1.107
'@iconify-json/vscode-icons':
specifier: ^1.1.34
version: 1.1.35
'@nuxt/content':
specifier: ^2.13.0
version: 2.13.0(ioredis@5.4.1)(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@4.18.0))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@4.18.0)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@4.18.0)(webpack@5.92.0))(postcss@8.4.38)(rollup@4.18.0)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@4.18.0)(vue@3.4.29(typescript@5.4.5))
@@ -550,11 +550,6 @@ packages:
peerDependencies:
postcss-selector-parser: ^6.0.13
'@egoist/tailwindcss-icons@1.8.1':
resolution: {integrity: sha512-hqZeASrhT6BOeaBHYDPB0yBH/zgMKqmm7y2Rsq0c4iRnNVv1RWEiXMBMJB38JsDMTHME450FKa/wvdaIhED+Iw==}
peerDependencies:
tailwindcss: '*'
'@es-joy/jsdoccomment@0.43.1':
resolution: {integrity: sha512-I238eDtOolvCuvtxrnqtlBaw0BwdQuYqK7eA6XIonicMdOOOb75mqdIzkGDUbS04+1Di007rgm9snFRNeVrOog==}
engines: {node: '>=16'}
@@ -1084,15 +1079,24 @@ packages:
'@iconify-json/tabler@1.1.113':
resolution: {integrity: sha512-dT34D0gyqxgK2t91+8scQ+U387yZ/zb4r7/3CHqhmvaVMsnOT8DFtX0FhJzdr6ldnVH82pGAp59GGr97IT/UfQ==}
'@iconify-json/vscode-icons@1.1.35':
resolution: {integrity: sha512-mUootLfDN4M9u5CL+gjJIGoVo/IaTGRo3WnysNTqTf9T5vkoe+EscJkx9aLbLs6gjSPQ+449SyuyTbBaF+nXww==}
'@iconify/collections@1.0.430':
resolution: {integrity: sha512-8yA2M1jKf+XCXclxsBAjI8FtnxpX6gkLhmLy00xRft1Sn0Tr7ht9exFhM86A6dfM+9517sMuFN91kdmZxLs7tg==}
'@iconify/collections@1.0.434':
resolution: {integrity: sha512-cel21NyheP9aiWIx2c9gZPyWEjLeBO+Azc55LQI/2W4HnTWKAHa1wFJu36ra8p4f//PswuceLcbxvVSDsKLzag==}
'@iconify/types@2.0.0':
resolution: {integrity: sha512-+wluvCrRhXrhyOmRDJ3q8mux9JkKy5SJ/v8ol2tu4FVjyYvtEzkc/3pK15ET6RKg4b4w4BmTk1+gsCUhf21Ykg==}
'@iconify/utils@2.1.24':
resolution: {integrity: sha512-H8r2KpL5uKyrkb3z9/3HD/22JcxqW3BJyjEWZhX2T7DehnYVZthEap1cNsEl/UtCDC3TlpNmwiPX8wg3y8E4dg==}
'@iconify/utils@2.1.25':
resolution: {integrity: sha512-Y+iGko8uv/Fz5bQLLJyNSZGOdMW0G7cnlEX1CiNcKsRXX9cq/y/vwxrIAtLCZhKHr3m0VJmsjVPsvnM4uX8YLg==}
'@iconify/vue@4.1.2':
resolution: {integrity: sha512-CQnYqLiQD5LOAaXhBrmj1mdL2/NCJvwcC4jtW2Z8ukhThiFkLDkutarTOV2trfc9EXqUqRs0KqXOL9pZ/IyysA==}
peerDependencies:
@@ -1266,6 +1270,9 @@ packages:
'@nuxt/fonts@0.7.0':
resolution: {integrity: sha512-nng9m7IbdjPkKbNY26xygsuIeld3WjejGBmB4xN3lZDo8kKtThqzLn+M0enYQZBNGQShLaIAoFa+ccFF50qZRg==}
'@nuxt/icon@1.0.0':
resolution: {integrity: sha512-um33vHvjSfbx7wqUzb/fGcbGgPXVU6dszw4oliagKjAIexLMpQ2Bob1+iTiwmTfmUypd5edLsumXZB5DKH59/g==}
'@nuxt/image@1.7.0':
resolution: {integrity: sha512-zSj32bLgbV9AvLkLX0pF52J5KBfSyj0eSIdpXCtTJATSZlqgcJigoCvmabC1nbcMIp0SZ29Bu9+acQpGTQKz+g==}
engines: {node: ^14.16.0 || >=16.11.0}
@@ -8132,13 +8139,6 @@ snapshots:
dependencies:
postcss-selector-parser: 6.1.0
'@egoist/tailwindcss-icons@1.8.1(tailwindcss@3.4.4)':
dependencies:
'@iconify/utils': 2.1.24
tailwindcss: 3.4.4
transitivePeerDependencies:
- supports-color
'@es-joy/jsdoccomment@0.43.1':
dependencies:
'@types/eslint': 8.56.10
@@ -8474,10 +8474,18 @@ snapshots:
dependencies:
'@iconify/types': 2.0.0
'@iconify-json/vscode-icons@1.1.35':
dependencies:
'@iconify/types': 2.0.0
'@iconify/collections@1.0.430':
dependencies:
'@iconify/types': 2.0.0
'@iconify/collections@1.0.434':
dependencies:
'@iconify/types': 2.0.0
'@iconify/types@2.0.0': {}
'@iconify/utils@2.1.24':
@@ -8492,6 +8500,18 @@ snapshots:
transitivePeerDependencies:
- supports-color
'@iconify/utils@2.1.25':
dependencies:
'@antfu/install-pkg': 0.1.1
'@antfu/utils': 0.7.8
'@iconify/types': 2.0.0
debug: 4.3.5
kolorist: 1.8.0
local-pkg: 0.5.0
mlly: 1.7.1
transitivePeerDependencies:
- supports-color
'@iconify/vue@4.1.2(vue@3.4.29(typescript@5.4.5))':
dependencies:
'@iconify/types': 2.0.0
@@ -9108,6 +9128,26 @@ snapshots:
- uWebSockets.js
- vite
'@nuxt/icon@1.0.0(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@3.29.4))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@3.29.4)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@3.29.4))(postcss@8.4.38)(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue@3.4.29(typescript@5.4.5))':
dependencies:
'@iconify/collections': 1.0.434
'@iconify/types': 2.0.0
'@iconify/utils': 2.1.25
'@iconify/vue': 4.1.2(vue@3.4.29(typescript@5.4.5))
'@nuxt/devtools-kit': 1.3.3(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@3.29.4))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@3.29.4)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@3.29.4))(postcss@8.4.38)(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))
'@nuxt/kit': 3.12.2(magicast@0.3.4)(rollup@3.29.4)
consola: 3.2.3
fast-glob: 3.3.2
local-pkg: 0.5.0
pathe: 1.1.2
transitivePeerDependencies:
- magicast
- nuxt
- rollup
- supports-color
- vite
- vue
'@nuxt/image@1.7.0(ioredis@5.4.1)(magicast@0.3.4)(rollup@4.18.0)':
dependencies:
'@nuxt/kit': 3.12.1(magicast@0.3.4)(rollup@4.18.0)
@@ -14923,20 +14963,6 @@ snapshots:
- rollup
- supports-color
nuxt-icon@0.6.10(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@3.29.4))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@3.29.4)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@3.29.4))(postcss@8.4.38)(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue@3.4.29(typescript@5.4.5)):
dependencies:
'@iconify/collections': 1.0.430
'@iconify/vue': 4.1.2(vue@3.4.29(typescript@5.4.5))
'@nuxt/devtools-kit': 1.3.3(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@3.29.4))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@3.29.4)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@3.29.4))(postcss@8.4.38)(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@3.29.4)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))
'@nuxt/kit': 3.12.2(magicast@0.3.4)(rollup@3.29.4)
transitivePeerDependencies:
- magicast
- nuxt
- rollup
- supports-color
- vite
- vue
nuxt-icon@0.6.10(magicast@0.3.4)(nuxt@3.12.2(@opentelemetry/api@1.9.0)(@parcel/watcher@2.4.1)(@types/node@20.14.2)(@unocss/reset@0.60.4)(encoding@0.1.13)(eslint@8.57.0)(floating-vue@5.2.2(@nuxt/kit@3.12.2(magicast@0.3.4)(rollup@4.18.0))(vue@3.4.29(typescript@5.4.5)))(fuse.js@6.6.2)(ioredis@5.4.1)(magicast@0.3.4)(optionator@0.9.4)(rollup@4.18.0)(sass@1.77.6)(terser@5.31.1)(typescript@5.4.5)(unocss@0.60.4(@unocss/webpack@0.60.4(rollup@4.18.0)(webpack@5.92.0))(postcss@8.4.38)(rollup@4.18.0)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1)))(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue-tsc@2.0.16(typescript@5.4.5)))(rollup@4.18.0)(vite@5.3.1(@types/node@20.14.2)(sass@1.77.6)(terser@5.31.1))(vue@3.4.29(typescript@5.4.5)):
dependencies:
'@iconify/collections': 1.0.430

View File

@@ -1,6 +1,5 @@
import { createRequire } from 'node:module'
import { defineNuxtModule, installModule, addComponentsDir, addImportsDir, createResolver, addPlugin } from '@nuxt/kit'
import type { CollectionNames, IconsPluginOptions } from '@egoist/tailwindcss-icons'
import { name, version } from '../package.json'
import createTemplates from './templates'
import * as config from './runtime/ui.config'
@@ -48,8 +47,6 @@ export interface ModuleOptions {
*/
global?: boolean
icons: CollectionNames[] | 'all' | IconsPluginOptions
safelistColors?: string[]
/**
* Disables the global css styles added by the module.
@@ -68,7 +65,6 @@ export default defineNuxtModule<ModuleOptions>({
},
defaults: {
prefix: 'U',
icons: ['heroicons'],
safelistColors: ['primary'],
disableGlobalStyles: false
},
@@ -90,7 +86,7 @@ export default defineNuxtModule<ModuleOptions>({
// Modules
await installModule('nuxt-icon')
await installModule('@nuxt/icon', { componentName: 'UIcon' })
await installModule('@nuxtjs/color-mode', { classSuffix: '' })
await installTailwind(options, nuxt, resolve)

View File

@@ -89,10 +89,7 @@ import type { PropType, AriaAttributes } from 'vue'
import { upperFirst } from 'scule'
import { defu } from 'defu'
import { useVModel } from '@vueuse/core'
import UIcon from '../elements/Icon.vue'
import UButton from '../elements/Button.vue'
import UProgress from '../elements/Progress.vue'
import UCheckbox from '../forms/Checkbox.vue'
import { UIcon, UButton, UProgress, UCheckbox } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig, get } from '../../utils'
import type { Strategy, Button, ProgressColor, ProgressAnimation } from '../../types'

View File

@@ -69,8 +69,7 @@
import { ref, computed, toRef, defineComponent, watch } from 'vue'
import type { PropType } from 'vue'
import { Disclosure as HDisclosure, DisclosureButton as HDisclosureButton, DisclosurePanel as HDisclosurePanel, provideUseId } from '@headlessui/vue'
import UIcon from '../elements/Icon.vue'
import UButton from '../elements/Button.vue'
import { UIcon, UButton } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig, omit } from '../../utils'
import type { AccordionItem, Strategy } from '../../types'

View File

@@ -43,9 +43,7 @@
import { computed, toRef, defineComponent } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import UButton from '../elements/Button.vue'
import { UIcon, UAvatar, UButton } from '#components'
import { useUI } from '../../composables/useUI'
import type { Avatar, Button, AlertColor, AlertVariant, AlertAction, Strategy } from '../../types'
import { mergeConfig } from '../../utils'

View File

@@ -24,7 +24,7 @@
import { defineComponent, ref, computed, toRef, watch } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import { UIcon } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig } from '../../utils'
import type { AvatarSize, AvatarChipColor, AvatarChipPosition, Strategy } from '../../types'

View File

@@ -20,8 +20,7 @@
import { computed, defineComponent, toRef } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import ULink from '../elements/Link.vue'
import { UIcon, ULink } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig, nuxtLinkProps, getNuxtLinkProps } from '../../utils'
import { useInjectButtonGroup } from '../../composables/useButtonGroup'

View File

@@ -61,9 +61,7 @@ import type { PropType } from 'vue'
import { Menu as HMenu, MenuButton as HMenuButton, MenuItems as HMenuItems, MenuItem as HMenuItem, provideUseId } from '@headlessui/vue'
import { defu } from 'defu'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import UKbd from '../elements/Kbd.vue'
import { UIcon, UAvatar, UKbd } from '#components'
import { useUI } from '../../composables/useUI'
import { usePopper } from '../../composables/usePopper'
import { mergeConfig, getNuxtLinkProps } from '../../utils'

View File

@@ -1,33 +0,0 @@
<template>
<Icon v-if="dynamic" :name="name" />
<span v-else :class="name" />
</template>
<script lang="ts">
import { defineComponent, computed } from 'vue'
import { useAppConfig } from '#imports'
export default defineComponent({
props: {
name: {
type: String,
required: true
},
dynamic: {
type: Boolean,
default: false
}
},
setup (props) {
const appConfig = useAppConfig()
// @ts-ignore
const dynamic = computed(() => props.dynamic || appConfig.ui?.icons?.dynamic)
return {
// eslint-disable-next-line vue/no-dupe-keys
dynamic
}
}
})
</script>

View File

@@ -31,7 +31,7 @@
import { computed, defineComponent, toRef } from 'vue'
import type { SlotsType, PropType } from 'vue'
import { twJoin } from 'tailwind-merge'
import UIcon from './Icon.vue'
import { UIcon } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig } from '../../utils'
import type { Strategy, MeterColor, MeterSize } from '../../types'

View File

@@ -1,7 +1,7 @@
import { h, cloneVNode, computed, toRef, defineComponent } from 'vue'
import type { ComputedRef, VNode, SlotsType, PropType } from 'vue'
import { twJoin } from 'tailwind-merge'
import UIcon from './Icon.vue'
import { UIcon } from '#components'
import Meter from './Meter.vue'
import { useUI } from '../../composables/useUI'
import { mergeConfig, getSlotsChildren } from '../../utils'

View File

@@ -35,7 +35,7 @@
import { ref, computed, toRef, onMounted, defineComponent } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import { UIcon } from '#components'
import { defu } from 'defu'
import { useUI } from '../../composables/useUI'
import { useFormGroup } from '../../composables/useFormGroup'

View File

@@ -104,8 +104,7 @@ import {
import { computedAsync, useDebounceFn } from '@vueuse/core'
import { defu } from 'defu'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import { UIcon, UAvatar } from '#components'
import { useUI } from '../../composables/useUI'
import { usePopper } from '../../composables/usePopper'
import { useFormGroup } from '../../composables/useFormGroup'

View File

@@ -56,7 +56,7 @@
import { computed, toRef, defineComponent } from 'vue'
import type { PropType, ComputedRef } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import { UIcon } from '#components'
import { useUI } from '../../composables/useUI'
import { useFormGroup } from '../../composables/useFormGroup'
import { mergeConfig, get } from '../../utils'

View File

@@ -140,8 +140,7 @@ import {
import { computedAsync, useDebounceFn } from '@vueuse/core'
import { defu } from 'defu'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import { UIcon, UAvatar } from '#components'
import { useUI } from '../../composables/useUI'
import { usePopper } from '../../composables/usePopper'
import { useFormGroup } from '../../composables/useFormGroup'

View File

@@ -34,7 +34,7 @@ import { computed, toRef, defineComponent } from 'vue'
import type { PropType } from 'vue'
import { Switch as HSwitch, provideUseId } from '@headlessui/vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import { UIcon } from '#components'
import { useUI } from '../../composables/useUI'
import { useFormGroup } from '../../composables/useFormGroup'
import { mergeConfig } from '../../utils'

View File

@@ -22,8 +22,7 @@
import { toRef, computed, defineComponent } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import { UIcon, UAvatar } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig } from '../../utils'
import type { Avatar, DividerSize, Strategy } from '../../types'

View File

@@ -37,8 +37,7 @@
import { defineComponent, toRef } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import ULink from '../elements/Link.vue'
import { UIcon, ULink } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig, getULinkProps } from '../../utils'
import type { BreadcrumbLink, Strategy } from '../../types'

View File

@@ -70,8 +70,7 @@ import { useFuse } from '@vueuse/integrations/useFuse'
import type { UseFuseOptions } from '@vueuse/integrations/useFuse'
import { twJoin } from 'tailwind-merge'
import { defu } from 'defu'
import UIcon from '../elements/Icon.vue'
import UButton from '../elements/Button.vue'
import { UIcon, UButton } from '#components'
import CommandPaletteGroup from './CommandPaletteGroup.vue'
import { useUI } from '../../composables/useUI'
import { mergeConfig } from '../../utils'

View File

@@ -73,9 +73,7 @@
import { computed, defineComponent } from 'vue'
import type { PropType } from 'vue'
import { ComboboxOption as HComboboxOption, provideUseId } from '@headlessui/vue'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import UKbd from '../elements/Kbd.vue'
import { UIcon, UAvatar, UKbd } from '#components'
import type { Group } from '../../types'
import { commandPalette } from '#ui/ui.config'
import { useId } from '#imports'

View File

@@ -55,10 +55,7 @@
import { toRef, defineComponent, computed } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import UBadge from '../elements/Badge.vue'
import ULink from '../elements/Link.vue'
import { UIcon, UAvatar, UBadge, ULink } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig, getULinkProps } from '../../utils'
import type { HorizontalNavigationLink, Strategy } from '../../types'

View File

@@ -56,11 +56,7 @@
import { toRef, defineComponent, computed } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import UBadge from '../elements/Badge.vue'
import ULink from '../elements/Link.vue'
import UDivider from '../layout/Divider.vue'
import { UIcon, UAvatar, UBadge, ULink, UDivider } from '#components'
import { useUI } from '../../composables/useUI'
import { mergeConfig, getULinkProps } from '../../utils'
import type { VerticalNavigationLink, Strategy } from '../../types'

View File

@@ -46,9 +46,7 @@
import { ref, computed, toRef, onMounted, onUnmounted, watch, watchEffect, defineComponent } from 'vue'
import type { PropType } from 'vue'
import { twMerge, twJoin } from 'tailwind-merge'
import UIcon from '../elements/Icon.vue'
import UAvatar from '../elements/Avatar.vue'
import UButton from '../elements/Button.vue'
import { UIcon, UAvatar, UButton } from '#components'
import { useUI } from '../../composables/useUI'
import { useTimer } from '../../composables/useTimer'
import { mergeConfig } from '../../utils'

View File

@@ -38,7 +38,6 @@ export default async function installTailwind (
getContents: ({ nuxt }) => `
const { defaultExtractor: createDefaultExtractor } = require('tailwindcss/lib/lib/defaultExtractor.js')
const { customSafelistExtractor, generateSafelist } = require(${JSON.stringify(resolve(runtimeDir, 'utils', 'colors'))})
const { iconsPlugin, getIconCollections } = require('@egoist/tailwindcss-icons')
const defaultExtractor = createDefaultExtractor({ tailwindConfig: { separator: ':' } })
@@ -48,8 +47,7 @@ export default async function installTailwind (
require('@tailwindcss/aspect-ratio'),
require('@tailwindcss/typography'),
require('@tailwindcss/container-queries'),
require('@headlessui/tailwindcss'),
iconsPlugin(${Array.isArray(moduleOptions.icons) || moduleOptions.icons === 'all' ? `{ collections: getIconCollections(${JSON.stringify(moduleOptions.icons)}) }` : typeof moduleOptions.icons === 'object' ? JSON.stringify(moduleOptions.icons) : {}})
require('@headlessui/tailwindcss')
],
content: {
files: [

View File

@@ -1,7 +1,7 @@
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
exports[`Button > renders <UButton icon="i-heroicons-pencil-square" size="sm" color="primary" square variant="solid" /> correctly 1`] = `
"<button type="button" class="focus:outline-none disabled:cursor-not-allowed disabled:opacity-75 flex-shrink-0 font-medium rounded-md text-sm gap-x-1.5 p-1.5 shadow-sm text-white dark:text-gray-900 bg-primary-500 hover:bg-primary-600 disabled:bg-primary-500 dark:bg-primary-400 dark:hover:bg-primary-500 dark:disabled:bg-primary-400 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-500 dark:focus-visible:outline-primary-400 inline-flex items-center"><span class="i-heroicons-pencil-square flex-shrink-0 h-5 w-5" aria-hidden="true"></span>
"<button type="button" class="focus:outline-none disabled:cursor-not-allowed disabled:opacity-75 flex-shrink-0 font-medium rounded-md text-sm gap-x-1.5 p-1.5 shadow-sm text-white dark:text-gray-900 bg-primary-500 hover:bg-primary-600 disabled:bg-primary-500 dark:bg-primary-400 dark:hover:bg-primary-500 dark:disabled:bg-primary-400 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-500 dark:focus-visible:outline-primary-400 inline-flex items-center"><span class="iconify i-heroicons:pencil-square flex-shrink-0 h-5 w-5" aria-hidden="true"></span>
<!--v-if-->
<!--v-if-->
</button>"
@@ -22,7 +22,7 @@ exports[`Button > renders black solid correctly 1`] = `
`;
exports[`Button > renders leading icon correctly 1`] = `
"<button type="button" class="focus:outline-none disabled:cursor-not-allowed disabled:opacity-75 flex-shrink-0 font-medium rounded-md text-sm gap-x-1.5 px-2.5 py-1.5 shadow-sm text-white dark:text-gray-900 bg-primary-500 hover:bg-primary-600 disabled:bg-primary-500 dark:bg-primary-400 dark:hover:bg-primary-500 dark:disabled:bg-primary-400 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-500 dark:focus-visible:outline-primary-400 inline-flex items-center"><span class="heroicons-check flex-shrink-0 h-5 w-5" aria-hidden="true"></span>label
"<button type="button" class="focus:outline-none disabled:cursor-not-allowed disabled:opacity-75 flex-shrink-0 font-medium rounded-md text-sm gap-x-1.5 px-2.5 py-1.5 shadow-sm text-white dark:text-gray-900 bg-primary-500 hover:bg-primary-600 disabled:bg-primary-500 dark:bg-primary-400 dark:hover:bg-primary-500 dark:disabled:bg-primary-400 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-500 dark:focus-visible:outline-primary-400 inline-flex items-center"><span class="iconify i-heroicons:check flex-shrink-0 h-5 w-5" aria-hidden="true"></span>label
<!--v-if-->
</button>"
`;