mirror of
https://github.com/ArthurDanjou/ui.git
synced 2026-01-15 12:39:35 +01:00
Compare commits
45 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
56230ea915 | ||
|
|
126b5fcfd4 | ||
|
|
d3536d8768 | ||
|
|
59f62d322f | ||
|
|
b85a8e7203 | ||
|
|
8830d848fd | ||
|
|
cfce1524b2 | ||
|
|
f845e89a76 | ||
|
|
d9ca5d188a | ||
|
|
2429bcf5a7 | ||
|
|
f45f4a3e56 | ||
|
|
09e957e702 | ||
|
|
1ecd7cefde | ||
|
|
aafdfdb59c | ||
|
|
453ff6ca20 | ||
|
|
55832b6b99 | ||
|
|
6b93bbe5cd | ||
|
|
1402553145 | ||
|
|
5d84dfd05b | ||
|
|
7dc59a05ec | ||
|
|
4bd994985d | ||
|
|
c83d3b7147 | ||
|
|
f022665351 | ||
|
|
f29c325dc7 | ||
|
|
876f9578c2 | ||
|
|
f69f584188 | ||
|
|
377b4189ca | ||
|
|
f76a9f0ab0 | ||
|
|
37b2271bf0 | ||
|
|
fa49d52f17 | ||
|
|
fd4b608150 | ||
|
|
fef93f3198 | ||
|
|
0826ef8d59 | ||
|
|
0e3066d865 | ||
|
|
fb9d6cb544 | ||
|
|
531a89cdb8 | ||
|
|
6970c2d665 | ||
|
|
9719ea3858 | ||
|
|
a4af6b3805 | ||
|
|
3493c138d9 | ||
|
|
d08e64d53f | ||
|
|
6aecb082d2 | ||
|
|
63e27f8b4b | ||
|
|
7970aefcb0 | ||
|
|
a893d7fa2e |
62
CHANGELOG.md
62
CHANGELOG.md
@@ -2,6 +2,68 @@
|
||||
|
||||
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
|
||||
|
||||
### [1.2.11](https://github.com/nuxtlabs/ui/compare/v1.2.10...v1.2.11) (2023-05-04)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **defineShortcuts:** use `useEventListener` ([#150](https://github.com/nuxtlabs/ui/issues/150)) ([59f62d3](https://github.com/nuxtlabs/ui/commit/59f62d322f07919d16a8d35340c3aa038cd09520))
|
||||
|
||||
### [1.2.10](https://github.com/nuxtlabs/ui/compare/v1.2.9...v1.2.10) (2023-04-07)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **CommandPalette:** typecheck ([cfce152](https://github.com/nuxtlabs/ui/commit/cfce1524b209212d9ce635b61376ff0d6bc3601b))
|
||||
|
||||
### [1.2.9](https://github.com/nuxtlabs/ui/compare/v1.2.8...v1.2.9) (2023-04-07)
|
||||
|
||||
### [1.2.8](https://github.com/nuxtlabs/ui/compare/v1.2.7...v1.2.8) (2023-04-04)
|
||||
|
||||
### [1.2.7](https://github.com/nuxtlabs/ui/compare/v1.2.6...v1.2.7) (2023-04-04)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **useTimer:** remaining after pause ([aafdfdb](https://github.com/nuxtlabs/ui/commit/aafdfdb59c365c542f93703dd52b4306ac935040))
|
||||
|
||||
### [1.2.6](https://github.com/nuxtlabs/ui/compare/v1.2.5...v1.2.6) (2023-04-04)
|
||||
|
||||
### [1.2.5](https://github.com/nuxtlabs/ui/compare/v1.2.4...v1.2.5) (2023-04-04)
|
||||
|
||||
### [1.2.4](https://github.com/nuxtlabs/ui/compare/v1.2.3...v1.2.4) (2023-04-04)
|
||||
|
||||
### [1.2.3](https://github.com/nuxtlabs/ui/compare/v1.2.2...v1.2.3) (2023-03-22)
|
||||
|
||||
### [1.2.2](https://github.com/nuxtlabs/ui/compare/v1.2.1...v1.2.2) (2023-03-20)
|
||||
|
||||
### [1.2.1](https://github.com/nuxtlabs/ui/compare/v1.2.0...v1.2.1) (2023-03-20)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **defineShortcuts:** shift + alphabetic character handling ([#140](https://github.com/nuxtlabs/ui/issues/140)) ([377b418](https://github.com/nuxtlabs/ui/commit/377b4189ca85603db0b7f040949260ba7494c46f))
|
||||
|
||||
## [1.2.0](https://github.com/nuxtlabs/ui/compare/v1.1.4...v1.2.0) (2023-03-09)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **defineShortcuts:** add missing import ([37b2271](https://github.com/nuxtlabs/ui/commit/37b2271bf04adfe6bee4d984fa12452b2168318c))
|
||||
* **Tooltip:** `shortcutsClass` prop type ([fa49d52](https://github.com/nuxtlabs/ui/commit/fa49d52f17752eaa06f997a9b6e8df8adcab983f))
|
||||
|
||||
### [1.1.4](https://github.com/nuxtlabs/ui/compare/v1.1.3...v1.1.4) (2023-03-02)
|
||||
|
||||
### [1.1.3](https://github.com/nuxtlabs/ui/compare/v1.1.2...v1.1.3) (2023-03-02)
|
||||
|
||||
### [1.1.2](https://github.com/nuxtlabs/ui/compare/v1.1.1...v1.1.2) (2023-02-28)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **Tooltip:** truncate ([d08e64d](https://github.com/nuxtlabs/ui/commit/d08e64d53fa439f34d51909bcb6812f1bcd95d83))
|
||||
* **VerticalNavigation:** links `to` type ([7970aef](https://github.com/nuxtlabs/ui/commit/7970aefcb032ce01fcb11e9285fa61ce87f59519))
|
||||
|
||||
### [1.1.1](https://github.com/nuxtlabs/ui/compare/v1.1.0...v1.1.1) (2023-02-20)
|
||||
|
||||
## [1.1.0](https://github.com/nuxtlabs/ui/compare/v1.0.0...v1.1.0) (2023-02-17)
|
||||
|
||||
@@ -84,7 +84,7 @@ const sections = [
|
||||
{ label: 'Forms', links: [{ label: 'Checkbox', to: '/components/Checkbox' }, { label: 'Input', to: '/components/Input' }, { label: 'FormGroup', to: '/components/FormGroup' }, { label: 'Radio', to: '/components/Radio' }, { label: 'Select', to: '/components/Select' }, { label: 'SelectCustom', to: '/components/SelectCustom' }, { label: 'Textarea', to: '/components/Textarea' }, { label: 'Toggle', to: '/components/Toggle' }] },
|
||||
{ label: 'Layout', links: [{ label: 'Card', to: '/components/Card' }, { label: 'Container', to: '/components/Container' }] },
|
||||
{ label: 'Navigation', links: [{ label: 'Pills', to: '/components/Pills' }, { label: 'Tabs', to: '/components/Tabs' }, { label: 'VerticalNavigation', to: '/components/VerticalNavigation' }, { label: 'CommandPalette', to: '/components/CommandPalette' }] },
|
||||
{ label: 'Overlays', links: [{ label: 'Modal', to: '/components/Modal' }, { label: 'Notification', to: '/components/Notification' }, { label: 'Popover', to: '/components/Popover' }, { label: 'Slideover', to: '/components/Slideover' }, { label: 'Tooltip', to: '/components/Tooltip' }] }
|
||||
{ label: 'Overlays', links: [{ label: 'ContextMenu', to: '/components/ContextMenu' }, { label: 'Modal', to: '/components/Modal' }, { label: 'Notification', to: '/components/Notification' }, { label: 'Popover', to: '/components/Popover' }, { label: 'Slideover', to: '/components/Slideover' }, { label: 'Tooltip', to: '/components/Tooltip' }] }
|
||||
]
|
||||
</script>
|
||||
|
||||
|
||||
@@ -3,6 +3,14 @@ import nuxtUI from '../src/module'
|
||||
|
||||
// https://v3.nuxtjs.org/docs/directory-structure/nuxt.config
|
||||
export default defineNuxtConfig({
|
||||
app: {
|
||||
head: {
|
||||
htmlAttrs: {
|
||||
lang: 'en'
|
||||
}
|
||||
}
|
||||
},
|
||||
// @ts-ignore
|
||||
modules: [
|
||||
// @ts-ignore
|
||||
nuxtUI
|
||||
|
||||
@@ -56,7 +56,6 @@
|
||||
v-if="prop.type === 'Boolean'"
|
||||
v-model="prop.value"
|
||||
:name="prop.key"
|
||||
:label="prop.key"
|
||||
/>
|
||||
<USelect
|
||||
v-else-if="prop.values"
|
||||
@@ -121,6 +120,31 @@ const toggle = ref(false)
|
||||
const modal = ref(false)
|
||||
const slideover = ref(false)
|
||||
|
||||
const x = ref(0)
|
||||
const y = ref(0)
|
||||
const isContextMenuOpen = ref(false)
|
||||
const virtualElement = ref({ getBoundingClientRect: () => ({}) })
|
||||
|
||||
onMounted(() => {
|
||||
document.addEventListener('mousemove', ({ clientX, clientY }) => {
|
||||
x.value = clientX
|
||||
y.value = clientY
|
||||
})
|
||||
})
|
||||
|
||||
function openContextMenu () {
|
||||
const top = unref(y)
|
||||
const left = unref(x)
|
||||
|
||||
virtualElement.value.getBoundingClientRect = () => ({
|
||||
width: 0,
|
||||
height: 0,
|
||||
top,
|
||||
left
|
||||
})
|
||||
isContextMenuOpen.value = true
|
||||
}
|
||||
|
||||
const defaultProps = {
|
||||
Button: {
|
||||
label: 'Button text'
|
||||
@@ -261,6 +285,31 @@ const defaultProps = {
|
||||
title: 'Notification title',
|
||||
callback: 'console.log(\'Timer expired\')'
|
||||
},
|
||||
ContextMenu: {
|
||||
modelValue: isContextMenuOpen,
|
||||
'onUpdate:modelValue': (v) => { isContextMenuOpen.value = v },
|
||||
virtualElement,
|
||||
component: {
|
||||
name: 'Card',
|
||||
props: {
|
||||
variant: 'secondary',
|
||||
label: 'Open context menu',
|
||||
onClick: () => { isContextMenuOpen.value = false },
|
||||
onContextmenu: (e) => {
|
||||
e?.preventDefault()
|
||||
openContextMenu()
|
||||
},
|
||||
class: 'relative w-[300px] h-[100px]'
|
||||
}
|
||||
},
|
||||
slots: {
|
||||
default: {
|
||||
tag: 'div',
|
||||
html: 'Context menu content',
|
||||
class: 'rounded border u-border-gray-200 p-2'
|
||||
}
|
||||
}
|
||||
},
|
||||
Modal: {
|
||||
modelValue: modal,
|
||||
'onUpdate:modelValue': (v) => { modal.value = v },
|
||||
|
||||
@@ -104,7 +104,7 @@
|
||||
</template>
|
||||
|
||||
<template #panel>
|
||||
<div class="p-4 u-bg-white border u-border-gray-200 rounded-md">
|
||||
<div class="p-2">
|
||||
Panel
|
||||
</div>
|
||||
</template>
|
||||
@@ -128,16 +128,26 @@
|
||||
<UButton icon="i-heroicons-bell" variant="red" label="Trigger an error" @click="onNotificationClick" />
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<div class="font-medium text-sm mb-1 u-text-gray-700">
|
||||
Copy text to clipboard:
|
||||
</div>
|
||||
<div class="flex gap-2">
|
||||
<UInput v-model="textToCopy" name="textToCopy" />
|
||||
<UButton icon="i-heroicons-document-duplicate-solid" variant="primary" label="Copy text" @click="onCopyTextClick" />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<div class="font-medium text-sm mb-1 u-text-gray-700">
|
||||
Context menu:
|
||||
</div>
|
||||
|
||||
<UCard ref="contextMenuRef" class="relative" body-class="h-64" @click="isContextMenuOpen = false" @contextmenu.prevent="openContextMenu">
|
||||
<UCard class="relative" body-class="h-64" @click="isContextMenuOpen = false" @contextmenu.prevent="openContextMenu">
|
||||
<UContextMenu v-model="isContextMenuOpen" :virtual-element="virtualElement" width-class="w-48">
|
||||
<UCard @click.stop>
|
||||
<div class="p-2">
|
||||
Menu
|
||||
</UCard>
|
||||
</div>
|
||||
</UContextMenu>
|
||||
</UCard>
|
||||
</div>
|
||||
@@ -230,6 +240,7 @@
|
||||
|
||||
<script setup>
|
||||
const isModalOpen = ref(false)
|
||||
const textToCopy = ref('Copied text')
|
||||
|
||||
const people = ref([
|
||||
{ id: 1, name: 'Durward Reynolds', disabled: false },
|
||||
@@ -251,12 +262,13 @@ const form = reactive({
|
||||
persons: ref([people.value[0]])
|
||||
})
|
||||
|
||||
const { $toast } = useNuxtApp()
|
||||
const toast = useToast()
|
||||
const clipboard = useCopyToClipboard()
|
||||
|
||||
const x = ref(0)
|
||||
const y = ref(0)
|
||||
const isContextMenuOpen = ref(false)
|
||||
const contextMenuRef = ref(null)
|
||||
const virtualElement = ref({ getBoundingClientRect: () => ({}) })
|
||||
|
||||
const commandPaletteGroups = computed(() => ([{
|
||||
key: 'people',
|
||||
@@ -277,8 +289,6 @@ onMounted(() => {
|
||||
})
|
||||
})
|
||||
|
||||
const virtualElement = ref({ getBoundingClientRect: () => ({}) })
|
||||
|
||||
function openContextMenu () {
|
||||
const top = unref(y)
|
||||
const left = unref(x)
|
||||
@@ -348,6 +358,10 @@ const customDropdownItems = [
|
||||
]
|
||||
|
||||
const onNotificationClick = () => {
|
||||
$toast.error({ title: 'Error', description: 'This is an error message' })
|
||||
toast.error({ title: 'Error', description: 'This is an error message' })
|
||||
}
|
||||
|
||||
const onCopyTextClick = () => {
|
||||
clipboard.copy(textToCopy.value, { title: 'Text copied successfully!' })
|
||||
}
|
||||
</script>
|
||||
|
||||
36
package.json
36
package.json
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@nuxthq/ui",
|
||||
"version": "1.1.1",
|
||||
"version": "1.2.11",
|
||||
"repository": "https://github.com/nuxtlabs/ui",
|
||||
"license": "MIT",
|
||||
"exports": {
|
||||
@@ -25,34 +25,34 @@
|
||||
"release": "yarn lint && standard-version && git push --follow-tags"
|
||||
},
|
||||
"dependencies": {
|
||||
"@egoist/tailwindcss-icons": "^1.0.5",
|
||||
"@headlessui/vue": "^1.7.10",
|
||||
"@iconify-json/heroicons": "^1.1.9",
|
||||
"@nuxt/kit": "^3.2.0",
|
||||
"@egoist/tailwindcss-icons": "^1.0.7",
|
||||
"@headlessui/vue": "1.7.10",
|
||||
"@iconify-json/heroicons": "^1.1.10",
|
||||
"@nuxt/kit": "^3.3.3",
|
||||
"@nuxtjs/color-mode": "^3.2.0",
|
||||
"@nuxtjs/tailwindcss": "^6.4.1",
|
||||
"@popperjs/core": "^2.11.6",
|
||||
"@nuxtjs/tailwindcss": "^6.6.5",
|
||||
"@popperjs/core": "^2.11.7",
|
||||
"@tailwindcss/aspect-ratio": "^0.4.2",
|
||||
"@tailwindcss/forms": "^0.5.3",
|
||||
"@tailwindcss/line-clamp": "^0.4.2",
|
||||
"@tailwindcss/typography": "^0.5.9",
|
||||
"@vueuse/core": "^9.12.0",
|
||||
"@vueuse/integrations": "^9.12.0",
|
||||
"@vueuse/core": "^9.13.0",
|
||||
"@vueuse/integrations": "^9.13.0",
|
||||
"@vueuse/math": "^9.13.0",
|
||||
"defu": "^6.1.2",
|
||||
"fuse.js": "^6.6.2",
|
||||
"lodash-es": "^4.17.21",
|
||||
"tailwindcss": "^3.2.7"
|
||||
"tailwindcss": "^3.3.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@iconify-json/mdi": "^1.1.47",
|
||||
"@iconify-json/mdi": "^1.1.50",
|
||||
"@nuxt/module-builder": "^0.2.1",
|
||||
"@nuxtjs/eslint-config-typescript": "^12.0.0",
|
||||
"@types/lodash-es": "^4.17.6",
|
||||
"@types/node": "^18.13.0",
|
||||
"eslint": "^8.34.0",
|
||||
"nuxt": "^3.2.0",
|
||||
"@types/lodash-es": "^4.17.7",
|
||||
"@types/node": "^18.15.11",
|
||||
"eslint": "^8.37.0",
|
||||
"nuxt": "^3.3.3",
|
||||
"standard-version": "^9.5.0",
|
||||
"unbuild": "^1.1.2",
|
||||
"vue-tsc": "^1.1.2"
|
||||
"unbuild": "^1.2.0",
|
||||
"vue-tsc": "^1.2.0"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
import { defineNuxtModule, installModule, addComponentsDir, addImportsDir, addTemplate, addPlugin, createResolver } from '@nuxt/kit'
|
||||
import { defineNuxtModule, installModule, addComponentsDir, addImportsDir, addTemplate, createResolver } from '@nuxt/kit'
|
||||
import { defu } from 'defu'
|
||||
import colors from 'tailwindcss/colors.js'
|
||||
import type { Config } from 'tailwindcss'
|
||||
@@ -136,7 +136,6 @@ export default defineNuxtModule<ModuleOptions>({
|
||||
theme,
|
||||
plugins: [
|
||||
require('@tailwindcss/forms'),
|
||||
require('@tailwindcss/line-clamp'),
|
||||
require('@tailwindcss/aspect-ratio'),
|
||||
require('@tailwindcss/typography')
|
||||
],
|
||||
@@ -155,9 +154,6 @@ export default defineNuxtModule<ModuleOptions>({
|
||||
cssPath: resolve(runtimeDir, 'tailwind.css')
|
||||
})
|
||||
|
||||
addPlugin(resolve(runtimeDir, 'plugins', 'toast.client'))
|
||||
addPlugin(resolve(runtimeDir, 'plugins', 'clipboard.client'))
|
||||
|
||||
addComponentsDir({
|
||||
path: resolve(runtimeDir, 'components', 'elements'),
|
||||
prefix,
|
||||
|
||||
@@ -38,12 +38,8 @@ const props = defineProps({
|
||||
default: true
|
||||
},
|
||||
chip: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
},
|
||||
chipVariant: {
|
||||
type: String,
|
||||
default: 'primary',
|
||||
default: null,
|
||||
validator (value: string) {
|
||||
return Object.keys($ui.avatar.chip.variant).includes(value)
|
||||
}
|
||||
@@ -92,8 +88,8 @@ const avatarClass = computed(() => {
|
||||
const chipClass = computed(() => {
|
||||
return classNames(
|
||||
$ui.avatar.chip.base,
|
||||
$ui.avatar.chip.variant[props.chip],
|
||||
$ui.avatar.chip.position[props.chipPosition],
|
||||
$ui.avatar.chip.variant[props.chipVariant],
|
||||
$ui.avatar.chip.size[props.size]
|
||||
)
|
||||
})
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
|
||||
<div v-if="open && items.length" ref="container" :class="[containerClass, widthClass]" @mouseover="onMouseOver">
|
||||
<transition appear v-bind="transitionClass">
|
||||
<MenuItems :class="baseClass" static>
|
||||
<MenuItems :class="[baseClass, divideClass, ringClass, roundedClass, shadowClass, backgroundClass]" static>
|
||||
<div v-for="(subItems, index) of items" :key="index" :class="groupClass">
|
||||
<MenuItem v-for="(item, subIndex) of subItems" :key="subIndex" v-slot="{ active, disabled: itemDisabled }" :disabled="item.disabled">
|
||||
<Component
|
||||
@@ -104,6 +104,26 @@ const props = defineProps({
|
||||
type: String,
|
||||
default: () => $ui.dropdown.width
|
||||
},
|
||||
backgroundClass: {
|
||||
type: String,
|
||||
default: () => $ui.dropdown.background
|
||||
},
|
||||
shadowClass: {
|
||||
type: String,
|
||||
default: () => $ui.dropdown.shadow
|
||||
},
|
||||
roundedClass: {
|
||||
type: String,
|
||||
default: () => $ui.dropdown.rounded
|
||||
},
|
||||
ringClass: {
|
||||
type: String,
|
||||
default: () => $ui.dropdown.ring
|
||||
},
|
||||
divideClass: {
|
||||
type: String,
|
||||
default: () => $ui.dropdown.divide
|
||||
},
|
||||
baseClass: {
|
||||
type: String,
|
||||
default: () => $ui.dropdown.base
|
||||
|
||||
@@ -15,22 +15,26 @@
|
||||
>
|
||||
<div :class="['flex justify-between select-none items-center rounded-md px-3 py-2 gap-3 relative', active && 'bg-gray-100 dark:bg-gray-800 u-text-gray-900', command.disabled ? 'cursor-not-allowed' : 'cursor-pointer']">
|
||||
<div class="flex items-center gap-2 min-w-0">
|
||||
<Icon v-if="command.icon" :name="command.icon" :class="['h-4 w-4 flex-shrink-0', active ? 'text-opacity-100 dark:text-opacity-100' : 'text-opacity-40 dark:text-opacity-40', command.iconClass || 'text-gray-900 dark:text-gray-50']" aria-hidden="true" />
|
||||
<Avatar
|
||||
v-else-if="command.avatar"
|
||||
v-bind="{ size: 'xxxs', ...command.avatar }"
|
||||
class="flex-shrink-0"
|
||||
aria-hidden="true"
|
||||
/>
|
||||
<span v-else-if="command.chip" class="flex-shrink-0 w-2 h-2 mx-1 rounded-full" :style="{ background: `#${command.chip}` }" />
|
||||
<slot :name="`${group.key}-icon`" :group="group" :command="command">
|
||||
<Icon v-if="command.icon" :name="command.icon" :class="['h-4 w-4 flex-shrink-0', active ? 'text-opacity-100 dark:text-opacity-100' : 'text-opacity-40 dark:text-opacity-40', command.iconClass || 'text-gray-900 dark:text-gray-50']" aria-hidden="true" />
|
||||
<Avatar
|
||||
v-else-if="command.avatar"
|
||||
v-bind="{ size: 'xxxs', ...command.avatar }"
|
||||
class="flex-shrink-0"
|
||||
aria-hidden="true"
|
||||
/>
|
||||
<span v-else-if="command.chip" class="flex-shrink-0 w-2 h-2 mx-1 rounded-full" :style="{ background: `#${command.chip}` }" />
|
||||
</slot>
|
||||
|
||||
<div class="flex items-center gap-1.5 min-w-0" :class="{ 'opacity-50': command.disabled }">
|
||||
<slot :name="`${group.key}-command`" :group="group" :command="command">
|
||||
<span v-if="command.prefix" class="u-text-gray-400">{{ command.prefix }}</span>
|
||||
<span v-if="command.prefix" class="flex-shrink-0" :class="command.prefixClass || 'u-text-gray-400'">{{ command.prefix }}</span>
|
||||
|
||||
<span class="truncate" :class="{ 'flex-none': command.suffix || command.matches?.length }">{{ command[commandAttribute] }}</span>
|
||||
|
||||
<!-- eslint-disable-next-line vue/no-v-html -->
|
||||
<span v-if="command.matches?.length" class="truncate" :class="{ 'flex-none': command.suffix }" v-html="highlight(command.matches[0])" />
|
||||
<span v-else class="truncate" :class="{ 'flex-none': command.suffix }">{{ command[commandAttribute] }}</span>
|
||||
<span v-if="command.suffix" class="u-text-gray-400 truncate">{{ command.suffix }}</span>
|
||||
<span v-if="command.matches?.length" class="truncate" :class="command.suffixClass || 'u-text-gray-400'" v-html="highlight(command[commandAttribute], command.matches[0])" />
|
||||
<span v-else-if="command.suffix" class="truncate" :class="command.suffixClass || 'u-text-gray-400'">{{ command.suffix }}</span>
|
||||
</slot>
|
||||
</div>
|
||||
</div>
|
||||
@@ -40,7 +44,7 @@
|
||||
<span v-if="group.active" class="flex-shrink-0 u-text-gray-500">{{ group.active }}</span>
|
||||
</slot>
|
||||
<slot v-else :name="`${group.key}-inactive`" :group="group" :command="command">
|
||||
<span v-if="command.shortcuts?.length" class="flex-shrink-0 text-xs font-semibold u-text-gray-500">
|
||||
<span v-if="command.shortcuts?.length" :class="$ui.commandPalette.option.shortcuts">
|
||||
<kbd v-for="shortcut of command.shortcuts" :key="shortcut" class="font-sans">{{ shortcut }}</kbd>
|
||||
</span>
|
||||
<span v-else-if="!command.disabled && group.inactive" class="flex-shrink-0 u-text-gray-500">{{ group.inactive }}</span>
|
||||
@@ -85,13 +89,36 @@ const label = computed(() => {
|
||||
return typeof label === 'function' ? label(props.query) : label
|
||||
})
|
||||
|
||||
function highlight ({ indices, value }: { indices: number[][], value:string }, i = 1): string {
|
||||
const pair = indices[indices.length - i]
|
||||
if (!pair) {
|
||||
return value
|
||||
function highlight (text: string, { indices, value }: { indices: number[][], value:string }): string {
|
||||
if (text === value) {
|
||||
return ''
|
||||
}
|
||||
|
||||
return `${highlight({ indices, value: value.substring(0, pair[0]) }, i + 1)}<mark>${value.substring(pair[0], pair[1] + 1)}</mark>${value.substring(pair[1] + 1)}`
|
||||
let content = ''
|
||||
let nextUnhighlightedIndiceStartingIndex = 0
|
||||
|
||||
indices.forEach((indice) => {
|
||||
const lastIndiceNextIndex = indice[1] + 1
|
||||
const isMatched = (lastIndiceNextIndex - indice[0]) >= props.query.length
|
||||
|
||||
content += [
|
||||
value.substring(nextUnhighlightedIndiceStartingIndex, indice[0]),
|
||||
isMatched && '<mark>',
|
||||
value.substring(indice[0], lastIndiceNextIndex),
|
||||
isMatched && '</mark>'
|
||||
].filter(Boolean).join('')
|
||||
|
||||
nextUnhighlightedIndiceStartingIndex = lastIndiceNextIndex
|
||||
})
|
||||
|
||||
content += value.substring(nextUnhighlightedIndiceStartingIndex)
|
||||
|
||||
const index = content.indexOf('<mark>')
|
||||
if (index > 60) {
|
||||
content = `...${content.substring(index - 60)}`
|
||||
}
|
||||
|
||||
return content
|
||||
}
|
||||
</script>
|
||||
|
||||
|
||||
@@ -49,7 +49,7 @@ import $ui from '#build/ui'
|
||||
defineProps({
|
||||
links: {
|
||||
type: Array as PropType<{
|
||||
to?: RouteLocationNormalized
|
||||
to?: RouteLocationNormalized | string
|
||||
exact?: boolean
|
||||
label: string
|
||||
icon?: string
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<template>
|
||||
<div v-if="isOpen" ref="container" :class="[containerClass, widthClass]">
|
||||
<transition appear v-bind="transitionClass">
|
||||
<div :class="baseClass">
|
||||
<div :class="[baseClass, ringClass, roundedClass, shadowClass, backgroundClass]">
|
||||
<slot />
|
||||
</div>
|
||||
</transition>
|
||||
@@ -38,6 +38,22 @@ const props = defineProps({
|
||||
type: String,
|
||||
default: () => $ui.contextMenu.width
|
||||
},
|
||||
backgroundClass: {
|
||||
type: String,
|
||||
default: () => $ui.contextMenu.background
|
||||
},
|
||||
shadowClass: {
|
||||
type: String,
|
||||
default: () => $ui.contextMenu.shadow
|
||||
},
|
||||
roundedClass: {
|
||||
type: String,
|
||||
default: () => $ui.contextMenu.rounded
|
||||
},
|
||||
ringClass: {
|
||||
type: String,
|
||||
default: () => $ui.contextMenu.ring
|
||||
},
|
||||
baseClass: {
|
||||
type: String,
|
||||
default: () => $ui.contextMenu.base
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
v-bind="notification"
|
||||
:class="notification.click && 'cursor-pointer'"
|
||||
@click="notification.click && notification.click(notification)"
|
||||
@close="$toast.removeNotification(notification.id)"
|
||||
@close="toast.removeNotification(notification.id)"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
@@ -18,10 +18,11 @@
|
||||
|
||||
<script setup lang="ts">
|
||||
import type { ToastNotification } from '../../types'
|
||||
import { useToast } from '../../composables/useToast'
|
||||
import Notification from './Notification.vue'
|
||||
import { useNuxtApp, useState } from '#imports'
|
||||
import { useState } from '#imports'
|
||||
|
||||
const { $toast } = useNuxtApp()
|
||||
const toast = useToast()
|
||||
const notifications = useState<ToastNotification[]>('notifications', () => [])
|
||||
</script>
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
|
||||
<div v-if="open" ref="container" :class="[containerClass, widthClass]" @mouseover="onMouseOver">
|
||||
<transition appear v-bind="transitionClass">
|
||||
<PopoverPanel :class="baseClass" static>
|
||||
<PopoverPanel :class="[baseClass, ringClass, roundedClass, shadowClass, backgroundClass]" static>
|
||||
<slot name="panel" :open="open" :close="close" />
|
||||
</PopoverPanel>
|
||||
</transition>
|
||||
@@ -62,6 +62,22 @@ const props = defineProps({
|
||||
type: String,
|
||||
default: () => $ui.popover.base
|
||||
},
|
||||
backgroundClass: {
|
||||
type: String,
|
||||
default: () => $ui.popover.background
|
||||
},
|
||||
shadowClass: {
|
||||
type: String,
|
||||
default: () => $ui.popover.shadow
|
||||
},
|
||||
roundedClass: {
|
||||
type: String,
|
||||
default: () => $ui.popover.rounded
|
||||
},
|
||||
ringClass: {
|
||||
type: String,
|
||||
default: () => $ui.popover.ring
|
||||
},
|
||||
transitionClass: {
|
||||
type: Object,
|
||||
default: () => $ui.popover.transition
|
||||
|
||||
@@ -8,10 +8,10 @@
|
||||
<transition appear v-bind="transitionClass">
|
||||
<div :class="[baseClass, backgroundClass, roundedClass, shadowClass, ringClass]">
|
||||
<slot name="text">
|
||||
<span class="truncate">{{ text }}</span>
|
||||
{{ text }}
|
||||
</slot>
|
||||
|
||||
<span v-if="shortcuts?.length" class="inline-flex items-center justify-end flex-shrink-0 gap-0.5 ml-1">
|
||||
<span v-if="shortcuts?.length" :class="shortcutsClass">
|
||||
<span class="mr-1 u-text-gray-700">·</span>
|
||||
<kbd v-for="shortcut of shortcuts" :key="shortcut" class="flex items-center justify-center font-sans px-1 h-4 min-w-[16px] text-[10px] u-bg-gray-100 rounded u-text-gray-900">
|
||||
{{ shortcut }}
|
||||
@@ -84,6 +84,10 @@ const props = defineProps({
|
||||
type: Object as PropType<PopperOptions>,
|
||||
default: () => ({})
|
||||
},
|
||||
shortcutsClass: {
|
||||
type: String,
|
||||
default: () => $ui.tooltip.shortcuts
|
||||
},
|
||||
openDelay: {
|
||||
type: Number,
|
||||
default: 0
|
||||
|
||||
103
src/runtime/composables/defineShortcuts.ts
Normal file
103
src/runtime/composables/defineShortcuts.ts
Normal file
@@ -0,0 +1,103 @@
|
||||
import type { ComputedRef, WatchSource } from 'vue'
|
||||
import { logicAnd, logicNot } from '@vueuse/math'
|
||||
import { useEventListener } from '@vueuse/core'
|
||||
import { computed } from 'vue'
|
||||
import { useShortcuts } from './useShortcuts'
|
||||
|
||||
export interface ShortcutConfig {
|
||||
handler: Function
|
||||
usingInput?: string | boolean
|
||||
whenever?: WatchSource<Boolean>[]
|
||||
}
|
||||
|
||||
export interface ShortcutsConfig {
|
||||
[key: string]: ShortcutConfig | Function
|
||||
}
|
||||
|
||||
interface Shortcut {
|
||||
handler: Function
|
||||
condition: ComputedRef<Boolean>
|
||||
// KeyboardEvent attributes
|
||||
key: string
|
||||
ctrlKey: boolean
|
||||
metaKey: boolean
|
||||
shiftKey: boolean
|
||||
altKey: boolean
|
||||
// code?: string
|
||||
// keyCode?: number
|
||||
}
|
||||
|
||||
export const defineShortcuts = (config: ShortcutsConfig) => {
|
||||
const { macOS, usingInput } = useShortcuts()
|
||||
|
||||
let shortcuts: Shortcut[] = []
|
||||
|
||||
const onKeyDown = (e: KeyboardEvent) => {
|
||||
const alphabeticalKey = /^[a-z]{1}$/i.test(e.key)
|
||||
|
||||
for (const shortcut of shortcuts) {
|
||||
if (e.key.toLowerCase() !== shortcut.key) { continue }
|
||||
if (e.metaKey !== shortcut.metaKey) { continue }
|
||||
if (e.ctrlKey !== shortcut.ctrlKey) { continue }
|
||||
// shift modifier is only checked in combination with alphabetical keys
|
||||
// (shift with non-alphabetical keys would change the key)
|
||||
if (alphabeticalKey && e.shiftKey !== shortcut.shiftKey) { continue }
|
||||
// alt modifier changes the combined key anyways
|
||||
// if (e.altKey !== shortcut.altKey) { continue }
|
||||
|
||||
if (shortcut.condition.value) {
|
||||
e.preventDefault()
|
||||
shortcut.handler()
|
||||
}
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
// Map config to full detailled shortcuts
|
||||
shortcuts = Object.entries(config).map(([key, shortcutConfig]) => {
|
||||
if (!shortcutConfig) {
|
||||
return null
|
||||
}
|
||||
|
||||
// Parse key and modifiers
|
||||
const keySplit = key.toLowerCase().split('_').map(k => k)
|
||||
let shortcut: Partial<Shortcut> = {
|
||||
key: keySplit.filter(k => !['meta', 'ctrl', 'shift', 'alt'].includes(k)).join('_'),
|
||||
metaKey: keySplit.includes('meta'),
|
||||
ctrlKey: keySplit.includes('ctrl'),
|
||||
shiftKey: keySplit.includes('shift'),
|
||||
altKey: keySplit.includes('alt')
|
||||
}
|
||||
|
||||
// Convert Meta to Ctrl for non-MacOS
|
||||
if (!macOS.value && shortcut.metaKey && !shortcut.ctrlKey) {
|
||||
shortcut.metaKey = false
|
||||
shortcut.ctrlKey = true
|
||||
}
|
||||
|
||||
// Retrieve handler function
|
||||
if (typeof shortcutConfig === 'function') {
|
||||
shortcut.handler = shortcutConfig
|
||||
} else if (typeof shortcutConfig === 'object') {
|
||||
shortcut = { ...shortcut, handler: shortcutConfig.handler }
|
||||
}
|
||||
|
||||
if (!shortcut.handler) {
|
||||
console.trace('[Shortcut] Invalid value')
|
||||
return null
|
||||
}
|
||||
|
||||
// Create shortcut computed
|
||||
const conditions: ComputedRef<Boolean>[] = []
|
||||
if (!(shortcutConfig as ShortcutConfig).usingInput) {
|
||||
conditions.push(logicNot(usingInput))
|
||||
} else if (typeof (shortcutConfig as ShortcutConfig).usingInput === 'string') {
|
||||
conditions.push(computed(() => usingInput.value === (shortcutConfig as ShortcutConfig).usingInput))
|
||||
}
|
||||
shortcut.condition = logicAnd(...conditions, ...((shortcutConfig as ShortcutConfig).whenever || []))
|
||||
|
||||
return shortcut as Shortcut
|
||||
}).filter(Boolean) as Shortcut[]
|
||||
|
||||
useEventListener('keydown', onKeyDown)
|
||||
}
|
||||
@@ -1,8 +1,9 @@
|
||||
import { useClipboard } from '@vueuse/core'
|
||||
import { defineNuxtPlugin } from '#app'
|
||||
import { useToast } from './useToast'
|
||||
|
||||
export default defineNuxtPlugin((nuxtApp) => {
|
||||
export function useCopyToClipboard () {
|
||||
const { copy: copyToClipboard, isSupported } = useClipboard()
|
||||
const toast = useToast()
|
||||
|
||||
function copy (text: string, success: { title?: string, description?: string } = {}, failure: { title?: string, description?: string } = {}) {
|
||||
if (!isSupported) {
|
||||
@@ -14,9 +15,9 @@ export default defineNuxtPlugin((nuxtApp) => {
|
||||
return
|
||||
}
|
||||
|
||||
nuxtApp.$toast.success(success)
|
||||
toast.success(success)
|
||||
}, function (e) {
|
||||
nuxtApp.$toast.error({
|
||||
toast.error({
|
||||
...failure,
|
||||
description: failure.description || e.message
|
||||
})
|
||||
@@ -24,10 +25,6 @@ export default defineNuxtPlugin((nuxtApp) => {
|
||||
}
|
||||
|
||||
return {
|
||||
provide: {
|
||||
clipboard: {
|
||||
copy
|
||||
}
|
||||
}
|
||||
copy
|
||||
}
|
||||
})
|
||||
}
|
||||
32
src/runtime/composables/useShortcuts.ts
Normal file
32
src/runtime/composables/useShortcuts.ts
Normal file
@@ -0,0 +1,32 @@
|
||||
import { createSharedComposable, useActiveElement } from '@vueuse/core'
|
||||
import { ref, computed, onMounted } from 'vue'
|
||||
|
||||
export const _useShortcuts = () => {
|
||||
const macOS = computed(() => process.client && navigator && navigator.userAgent && navigator.userAgent.match(/Macintosh;/))
|
||||
|
||||
const metaSymbol = ref(' ')
|
||||
|
||||
const activeElement = useActiveElement()
|
||||
const usingInput = computed(() => {
|
||||
const usingInput = !!(activeElement.value?.tagName === 'INPUT' || activeElement.value?.tagName === 'TEXTAREA' || activeElement.value?.contentEditable === 'true')
|
||||
|
||||
if (usingInput) {
|
||||
return ((activeElement.value as any)?.name as string) || true
|
||||
}
|
||||
|
||||
return false
|
||||
})
|
||||
|
||||
onMounted(() => {
|
||||
metaSymbol.value = macOS.value ? '⌘' : 'Ctrl'
|
||||
})
|
||||
|
||||
return {
|
||||
macOS,
|
||||
metaSymbol,
|
||||
activeElement,
|
||||
usingInput
|
||||
}
|
||||
}
|
||||
|
||||
export const useShortcuts = createSharedComposable(_useShortcuts)
|
||||
@@ -1,16 +1,17 @@
|
||||
import { ref, computed } from 'vue-demi'
|
||||
import { useTimestamp } from '@vueuse/core'
|
||||
import type { UseTimestampOptions } from '@vueuse/core'
|
||||
|
||||
export function useTimer (cb: (...args: unknown[]) => any, interval: number) {
|
||||
export function useTimer (cb: (...args: unknown[]) => any, interval: number, options?: UseTimestampOptions<true>) {
|
||||
let timer: number | null = null
|
||||
const timestamp = useTimestamp({ controls: true })
|
||||
const { pause: tPause, resume: tResume, timestamp } = useTimestamp({ ...(options || {}), controls: true })
|
||||
const startTime = ref<number | null>(null)
|
||||
|
||||
const remaining = computed(() => {
|
||||
if (!startTime.value) {
|
||||
return
|
||||
return 0
|
||||
}
|
||||
return interval - (timestamp.timestamp.value - startTime.value)
|
||||
return interval - (timestamp.value - startTime.value)
|
||||
})
|
||||
|
||||
function set (...args: unknown[]) {
|
||||
@@ -37,18 +38,18 @@ export function useTimer (cb: (...args: unknown[]) => any, interval: number) {
|
||||
|
||||
function stop () {
|
||||
clear()
|
||||
timestamp.pause()
|
||||
tPause()
|
||||
}
|
||||
|
||||
function pause () {
|
||||
clear()
|
||||
timestamp.pause()
|
||||
tPause()
|
||||
}
|
||||
|
||||
function resume () {
|
||||
startTime.value = (startTime.value || 0) + (Date.now() - timestamp.timestamp.value)
|
||||
timestamp.resume()
|
||||
set()
|
||||
tResume()
|
||||
startTime.value = (startTime.value || 0) + (Date.now() - timestamp.value)
|
||||
}
|
||||
|
||||
start()
|
||||
|
||||
41
src/runtime/composables/useToast.ts
Normal file
41
src/runtime/composables/useToast.ts
Normal file
@@ -0,0 +1,41 @@
|
||||
import type { ToastNotification } from '../types'
|
||||
import { useState } from '#imports'
|
||||
|
||||
export function useToast () {
|
||||
const notifications = useState<ToastNotification[]>('notifications', () => [])
|
||||
|
||||
function addNotification (notification: Partial<ToastNotification>) {
|
||||
const body = {
|
||||
id: new Date().getTime().toString(),
|
||||
...notification
|
||||
}
|
||||
|
||||
const index = notifications.value.findIndex((n: ToastNotification) => n.id === body.id)
|
||||
if (index === -1) {
|
||||
notifications.value.push(body as ToastNotification)
|
||||
}
|
||||
|
||||
return body
|
||||
}
|
||||
|
||||
function removeNotification (id: string) {
|
||||
notifications.value = notifications.value.filter((n: ToastNotification) => n.id !== id)
|
||||
}
|
||||
|
||||
const success = (notification: Partial<ToastNotification> = {}) => addNotification({ type: 'success', ...notification })
|
||||
|
||||
const info = (notification: Partial<ToastNotification> = {}) => addNotification({ type: 'info', ...notification })
|
||||
|
||||
const warning = (notification: Partial<ToastNotification> = {}) => addNotification({ type: 'warning', ...notification })
|
||||
|
||||
const error = (notification: Partial<ToastNotification>) => addNotification({ type: 'error', title: 'An error occurred!', ...notification })
|
||||
|
||||
return {
|
||||
addNotification,
|
||||
removeNotification,
|
||||
success,
|
||||
info,
|
||||
warning,
|
||||
error
|
||||
}
|
||||
}
|
||||
@@ -1,45 +0,0 @@
|
||||
import { defineNuxtPlugin, useState } from '#app'
|
||||
import type { ToastNotification } from '../types'
|
||||
|
||||
export default defineNuxtPlugin(() => {
|
||||
const notifications = useState<ToastNotification[]>('notifications', () => [])
|
||||
|
||||
function addNotification (notification: Partial<ToastNotification>) {
|
||||
const body = {
|
||||
id: new Date().getTime().toString(),
|
||||
...notification
|
||||
}
|
||||
|
||||
const index = notifications.value.findIndex((n: ToastNotification) => n.id === body.id)
|
||||
if (index === -1) {
|
||||
notifications.value.push(body as ToastNotification)
|
||||
}
|
||||
|
||||
return body
|
||||
}
|
||||
|
||||
function removeNotification (id: string) {
|
||||
notifications.value = notifications.value.filter((n: ToastNotification) => n.id !== id)
|
||||
}
|
||||
|
||||
return {
|
||||
provide: {
|
||||
toast: {
|
||||
addNotification,
|
||||
removeNotification,
|
||||
success (notification: Partial<ToastNotification> = {}) {
|
||||
return addNotification({ type: 'success', ...notification })
|
||||
},
|
||||
info (notification: Partial<ToastNotification> = {}) {
|
||||
return addNotification({ type: 'info', ...notification })
|
||||
},
|
||||
warning (notification: Partial<ToastNotification> = {}) {
|
||||
return addNotification({ type: 'warning', ...notification })
|
||||
},
|
||||
error (notification: Partial<ToastNotification>) {
|
||||
return addNotification({ type: 'error', title: 'An error occurred!', ...notification })
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
@@ -224,12 +224,12 @@ export default function defaultPreset (variantColors: string[]) {
|
||||
base: 'u-bg-white shadow-lg rounded-md ring-1 u-ring-gray-200 focus:outline-none overflow-y-auto py-1 max-h-60',
|
||||
input: 'relative block w-full focus:ring-transparent text-sm px-4 py-2 u-text-gray-700 border-l-0 u-bg-white border-t-0 border-r-0 u-border-gray-200 focus:u-border-gray-200',
|
||||
option: {
|
||||
base: 'cursor-default select-none relative py-2 pl-4 pr-10 text-sm group',
|
||||
base: 'cursor-default select-none relative py-2 text-sm group',
|
||||
container: 'flex items-center gap-3',
|
||||
active: 'text-white bg-primary-600',
|
||||
inactive: 'u-text-gray-900',
|
||||
selected: 'font-semibold',
|
||||
unselected: 'font-normal',
|
||||
selected: 'font-semibold pl-4 pr-10',
|
||||
unselected: 'font-normal px-4',
|
||||
disabled: 'cursor-not-allowed opacity-50',
|
||||
empty: 'text-sm u-text-gray-400 px-4 py-2',
|
||||
icon: {
|
||||
@@ -366,7 +366,12 @@ export default function defaultPreset (variantColors: string[]) {
|
||||
wrapper: 'relative inline-flex text-left',
|
||||
container: 'z-20',
|
||||
width: 'w-48',
|
||||
base: 'u-bg-white divide-y u-divide-gray-100 rounded-md ring-1 u-ring-gray-200 shadow-lg focus:outline-none',
|
||||
background: 'u-bg-white',
|
||||
shadow: 'shadow-lg',
|
||||
rounded: 'rounded-md',
|
||||
ring: 'ring-1 u-ring-gray-200',
|
||||
base: 'focus:outline-none',
|
||||
divide: 'divide-y u-divide-gray-100',
|
||||
group: 'py-1',
|
||||
item: {
|
||||
base: 'group flex items-center gap-3 px-4 py-2 text-sm w-full',
|
||||
@@ -375,7 +380,7 @@ export default function defaultPreset (variantColors: string[]) {
|
||||
disabled: 'cursor-not-allowed opacity-50',
|
||||
icon: 'h-5 w-5 u-text-gray-400 group-hover:u-text-gray-500 flex-shrink-0',
|
||||
avatar: '-m-0.5 group-hover:u-bg-gray-200 flex-shrink-0',
|
||||
shortcuts: 'flex-shrink-0 text-xs font-semibold u-text-gray-500 ml-auto'
|
||||
shortcuts: 'hidden md:inline-flex flex-shrink-0 text-xs font-semibold u-text-gray-500 ml-auto'
|
||||
},
|
||||
transition: {
|
||||
enterActiveClass: 'transition duration-100 ease-out',
|
||||
@@ -520,7 +525,8 @@ export default function defaultPreset (variantColors: string[]) {
|
||||
shadow: 'shadow',
|
||||
rounded: 'rounded',
|
||||
ring: 'ring-1 u-ring-gray-200',
|
||||
base: 'invisible lg:visible h-6 px-2 py-1 text-xs font-normal',
|
||||
base: 'invisible lg:visible h-6 px-2 py-1 text-xs font-normal truncate',
|
||||
shortcuts: 'hidden md:inline-flex items-center justify-end flex-shrink-0 gap-0.5 ml-1',
|
||||
transition: {
|
||||
enterActiveClass: 'transition ease-out duration-200',
|
||||
enterFromClass: 'opacity-0 translate-y-1',
|
||||
@@ -538,7 +544,11 @@ export default function defaultPreset (variantColors: string[]) {
|
||||
wrapper: 'relative',
|
||||
container: 'z-20',
|
||||
width: '',
|
||||
base: '',
|
||||
background: 'u-bg-white',
|
||||
shadow: 'shadow-lg',
|
||||
rounded: 'rounded-md',
|
||||
ring: 'ring-1 u-ring-gray-200',
|
||||
base: 'overflow-hidden focus:outline-none',
|
||||
transition: {
|
||||
enterActiveClass: 'transition ease-out duration-200',
|
||||
enterFromClass: 'opacity-0 translate-y-1',
|
||||
@@ -556,7 +566,11 @@ export default function defaultPreset (variantColors: string[]) {
|
||||
wrapper: 'relative',
|
||||
container: 'z-20',
|
||||
width: '',
|
||||
base: '',
|
||||
background: 'u-bg-white',
|
||||
shadow: 'shadow-lg',
|
||||
rounded: 'rounded-md',
|
||||
ring: 'ring-1 u-ring-gray-200',
|
||||
base: 'overflow-hidden focus:outline-none',
|
||||
transition: {
|
||||
enterActiveClass: 'transition ease-out duration-200',
|
||||
enterFromClass: 'opacity-0 translate-y-1',
|
||||
@@ -598,7 +612,8 @@ export default function defaultPreset (variantColors: string[]) {
|
||||
icon: {
|
||||
name: 'i-heroicons-check-20-solid'
|
||||
}
|
||||
}
|
||||
},
|
||||
shortcuts: 'hidden md:inline-flex flex-shrink-0 text-xs font-semibold u-text-gray-500'
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
3
src/runtime/types/avatar.d.ts
vendored
3
src/runtime/types/avatar.d.ts
vendored
@@ -4,7 +4,6 @@ export interface Avatar {
|
||||
text: string
|
||||
size: string
|
||||
rounded: boolean
|
||||
chip: boolean
|
||||
chipVariant: string
|
||||
chip: string
|
||||
chipPosition: string
|
||||
}
|
||||
|
||||
7
src/runtime/types/toast.d.ts
vendored
7
src/runtime/types/toast.d.ts
vendored
@@ -14,10 +14,3 @@ export interface ToastNotification {
|
||||
click?: Function
|
||||
callback?: Function
|
||||
}
|
||||
|
||||
export interface ToastPlugin {
|
||||
addNotification: (notification: Partial<Notification>) => Notification
|
||||
removeNotification: (id: string) => void
|
||||
success: (options: { title?: string, description?: string }) => void
|
||||
error: (options: { title?: string, description?: string }) => void
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user