@saasmakers/ui 0.1.71 → 0.1.73

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -47,7 +47,6 @@ onMounted(() => {
47
47
  }
48
48
  })
49
49
 
50
- // Expose
51
50
  defineExpose({ chart })
52
51
  </script>
53
52
 
@@ -1,7 +1,7 @@
1
1
  <script lang="ts" setup>
2
2
  import type { BaseTags } from '../../types/bases'
3
3
 
4
- const props = withDefaults(defineProps<BaseTags>(), {
4
+ const props = withDefaults(defineProps<Omit<BaseTags, 'value'>>(), {
5
5
  active: false,
6
6
  clickable: true,
7
7
  draggable: false,
@@ -14,21 +14,21 @@ const props = withDefaults(defineProps<BaseTags>(), {
14
14
  selectableUnique: false,
15
15
  size: 'base',
16
16
  tags: () => [],
17
- value: () => [],
18
17
  wrap: false,
19
18
  })
20
19
 
21
20
  const emit = defineEmits<{
22
- 'attach': [event: MouseEvent, tagId?: number | string]
23
- 'back': [event: MouseEvent]
24
- 'click': [event: MouseEvent]
25
- 'create': [event: FocusEvent | KeyboardEvent, name: string]
26
- 'detach': [event: MouseEvent, tagId?: number | string]
27
- 'remove': [event: MouseEvent, tagId?: number | string]
28
- 'update': [event: FocusEvent | KeyboardEvent, name: string, tagId?: number | string]
29
- 'update:modelValue': [value: (number | string)[]]
21
+ attach: [event: MouseEvent, tagId?: number | string]
22
+ back: [event: MouseEvent]
23
+ click: [event: MouseEvent]
24
+ create: [event: FocusEvent | KeyboardEvent, name: string]
25
+ detach: [event: MouseEvent, tagId?: number | string]
26
+ remove: [event: MouseEvent, tagId?: number | string]
27
+ update: [event: FocusEvent | KeyboardEvent, name: string, tagId?: number | string]
30
28
  }>()
31
29
 
30
+ const modelValue = defineModel<(number | string)[]>({ default: () => [] })
31
+
32
32
  const keyForTagCreation = ref(Date.now())
33
33
  const keyForTagUpdate = ref(Date.now())
34
34
  const root = ref<HTMLDivElement>()
@@ -91,7 +91,7 @@ function onShowAllTags() {
91
91
 
92
92
  function onTagClick(event: MouseEvent, tagId?: number | string) {
93
93
  if (props.selectable && tagId) {
94
- let value = [...props.value]
94
+ let value = [...modelValue.value]
95
95
 
96
96
  if (value.includes(tagId)) {
97
97
  value.splice(value.indexOf(tagId), 1)
@@ -106,7 +106,7 @@ function onTagClick(event: MouseEvent, tagId?: number | string) {
106
106
  emit('attach', event, tagId)
107
107
  }
108
108
 
109
- emit('update:modelValue', value)
109
+ modelValue.value = value
110
110
  }
111
111
  }
112
112
 
@@ -184,7 +184,7 @@ function onRemoveTag(event: MouseEvent, tagId?: number | string) {
184
184
  <BaseTag
185
185
  :id="tag.id || tagIndex"
186
186
  :key="`${tag.id}_${tagIndex}`"
187
- :active="tag.id && value.includes(tag.id) || tag.active"
187
+ :active="tag.id && modelValue.includes(tag.id) || tag.active"
188
188
  :avatar="tag.avatar"
189
189
  :circle="tag.circle"
190
190
  :clickable="clickable"
@@ -1,7 +1,7 @@
1
1
  <script lang="ts" setup>
2
2
  import type { FieldCheckbox } from '../../types/fields'
3
3
 
4
- const props = withDefaults(defineProps<FieldCheckbox>(), {
4
+ withDefaults(defineProps<Omit<FieldCheckbox, 'modelValue'>>(), {
5
5
  description: '',
6
6
  disabled: false,
7
7
  fullWidth: false,
@@ -10,7 +10,6 @@ const props = withDefaults(defineProps<FieldCheckbox>(), {
10
10
  labelIcon: undefined,
11
11
  lineThrough: false,
12
12
  loading: false,
13
- modelValue: false,
14
13
  required: false,
15
14
  size: 'base',
16
15
  truncate: false,
@@ -18,27 +17,9 @@ const props = withDefaults(defineProps<FieldCheckbox>(), {
18
17
  validation: undefined,
19
18
  })
20
19
 
21
- const emit = defineEmits<{
22
- 'update:modelValue': [value: boolean ]
23
- }>()
20
+ const modelValue = defineModel<FieldCheckbox['modelValue']>({ default: false })
24
21
 
25
- const input = ref<HTMLInputElement>()
26
22
  const uuid = ref(`${Math.floor((1 + Math.random()) * 0x100000)}`)
27
-
28
- const value = computed({
29
- get() {
30
- return props.modelValue
31
- },
32
- set(value) {
33
- emit('update:modelValue', value || false)
34
- },
35
- })
36
-
37
- function onFieldChange(event: Event) {
38
- const value = (event.target as HTMLInputElement).checked
39
-
40
- emit('update:modelValue', value)
41
- }
42
23
  </script>
43
24
 
44
25
  <template>
@@ -51,8 +32,7 @@ function onFieldChange(event: Event) {
51
32
  <input
52
33
  v-if="!loading"
53
34
  :id="uuid"
54
- ref="input"
55
- v-model="value"
35
+ v-model="modelValue"
56
36
  class="cursor-pointer border border-gray-300 rounded-lg accent-indigo-700 transition-shadow flex-initial dark:border-gray-700 focus:border-gray-500 hover:border-gray-400 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 focus-visible:ring-indigo-500/40 dark:focus:border-gray-500 dark:hover:border-gray-600"
57
37
  :class="{
58
38
  'disabled:opacity-50 disabled:cursor-not-allowed': disabled,
@@ -64,7 +44,6 @@ function onFieldChange(event: Event) {
64
44
  }"
65
45
  :disabled="disabled"
66
46
  type="checkbox"
67
- @change="onFieldChange"
68
47
  >
69
48
 
70
49
  <BaseSpinner
@@ -1,15 +1,14 @@
1
1
  <script lang="ts" setup>
2
2
  import type { FieldDays } from '../../types/fields'
3
3
 
4
- const props = withDefaults(defineProps<FieldDays>(), { modelValue: () => [] })
5
-
6
4
  const emit = defineEmits<{
7
- 'change': [event: MouseEvent, value: number[]]
8
- 'update:modelValue': [value: number[]]
5
+ change: [event: MouseEvent, value: number[]]
9
6
  }>()
10
7
 
11
8
  const { t } = useI18n()
12
9
 
10
+ const modelValue = defineModel<FieldDays['modelValue']>({ default: () => [] })
11
+
13
12
  const daysToDisplay = computed(() => {
14
13
  return [
15
14
  {
@@ -44,12 +43,13 @@ const daysToDisplay = computed(() => {
44
43
  })
45
44
 
46
45
  function onUpdateDays(event: MouseEvent, day: number) {
47
- const days = [...props.modelValue]
46
+ const days = [...modelValue.value]
48
47
 
49
48
  days.includes(day) ? days.splice(days.indexOf(day), 1) : days.push(day)
50
49
 
50
+ modelValue.value = days
51
+
51
52
  emit('change', event, days)
52
- emit('update:modelValue', days)
53
53
  }
54
54
  </script>
55
55
 
@@ -3,16 +3,15 @@ import type { FieldEmojis } from '../../types/fields'
3
3
  import { emojis } from '@saasmakers/shared'
4
4
  import { refDebounced } from '@vueuse/core'
5
5
 
6
- withDefaults(defineProps<FieldEmojis>(), { modelValue: undefined })
7
-
8
6
  const emit = defineEmits<{
9
- 'click': [event: MouseEvent, emoji: string]
10
- 'update:modelValue': [value: string]
7
+ click: [event: MouseEvent, emoji: string]
11
8
  }>()
12
9
 
13
10
  const { locale, t } = useI18n()
14
11
  const { normalizeText } = useLayerUtils()
15
12
 
13
+ const modelValue = defineModel<FieldEmojis['modelValue']>({ default: '' })
14
+
16
15
  const searchRaw = ref('')
17
16
  const searchQuery = refDebounced(searchRaw, 250)
18
17
 
@@ -43,7 +42,7 @@ const emojisFiltered = computed(() => {
43
42
 
44
43
  function onEmojiClick(event: MouseEvent, emoji?: string) {
45
44
  emit('click', event, emoji || '')
46
- emit('update:modelValue', emoji || '')
45
+ modelValue.value = emoji || ''
47
46
  }
48
47
  </script>
49
48
 
@@ -1,7 +1,7 @@
1
1
  <script lang="ts" setup>
2
2
  import type { FieldInput } from '../../types/fields'
3
3
 
4
- const props = withDefaults(defineProps<FieldInput>(), {
4
+ const props = withDefaults(defineProps<Omit<FieldInput, 'modelValue'>>(), {
5
5
  alignment: 'left',
6
6
  autocomplete: true,
7
7
  autofocus: false,
@@ -18,7 +18,6 @@ const props = withDefaults(defineProps<FieldInput>(), {
18
18
  lowercaseOnly: false,
19
19
  max: undefined,
20
20
  min: undefined,
21
- modelValue: '',
22
21
  placeholder: '',
23
22
  required: false,
24
23
  size: 'base',
@@ -28,11 +27,10 @@ const props = withDefaults(defineProps<FieldInput>(), {
28
27
  })
29
28
 
30
29
  const emit = defineEmits<{
31
- 'blur': [event: FocusEvent]
32
- 'focus': [event: FocusEvent]
33
- 'keyup': [event: KeyboardEvent, value: string ]
34
- 'submit': [event: KeyboardEvent, value: string ]
35
- 'update:modelValue': [value: string ]
30
+ blur: [event: FocusEvent]
31
+ focus: [event: FocusEvent]
32
+ keyup: [event: KeyboardEvent, value: string ]
33
+ submit: [event: KeyboardEvent, value: string ]
36
34
  }>()
37
35
 
38
36
  defineSlots<{
@@ -41,6 +39,8 @@ defineSlots<{
41
39
  label?: () => VNode[]
42
40
  }>()
43
41
 
42
+ const modelValue = defineModel<FieldInput['modelValue']>({ default: '' })
43
+
44
44
  const input = ref<HTMLInputElement>()
45
45
  const uuid = ref(`${Math.floor((1 + Math.random()) * 0x100000)}`)
46
46
 
@@ -52,15 +52,6 @@ onMounted(() => {
52
52
  }
53
53
  })
54
54
 
55
- const value = computed({
56
- get() {
57
- return props.modelValue
58
- },
59
- set(value) {
60
- emit('update:modelValue', value || '')
61
- },
62
- })
63
-
64
55
  function blur() {
65
56
  if (input.value) {
66
57
  input.value.blur()
@@ -92,7 +83,7 @@ function onFieldInput(event: Event) {
92
83
  value = value.toString().toLowerCase()
93
84
  }
94
85
 
95
- emit('update:modelValue', value)
86
+ modelValue.value = value
96
87
  }
97
88
 
98
89
  function onFieldKeyDown(event: KeyboardEvent) {
@@ -102,7 +93,7 @@ function onFieldKeyDown(event: KeyboardEvent) {
102
93
  blur()
103
94
  }
104
95
 
105
- else if (event.key === 'Enter' && props.modelValue) {
96
+ else if (event.key === 'Enter' && modelValue.value) {
106
97
  emit('submit', event, value)
107
98
  }
108
99
 
@@ -120,7 +111,6 @@ function onFieldKeyDown(event: KeyboardEvent) {
120
111
  emit('keyup', event, value)
121
112
  }
122
113
 
123
- // Expose
124
114
  defineExpose({ focus })
125
115
  </script>
126
116
 
@@ -160,7 +150,6 @@ defineExpose({ focus })
160
150
  <input
161
151
  :id="uuid"
162
152
  ref="input"
163
- v-model="value"
164
153
  :autocomplete="autocomplete ? 'on' : 'off'"
165
154
  class="h-full w-full flex-1 appearance-none items-center rounded-lg outline-none placeholder-gray-600 dark:placeholder-gray-400 focus:placeholder-gray-900 hover:placeholder-gray-900 dark:focus:placeholder-gray-100 dark:hover:placeholder-gray-100"
166
155
  :class="{
@@ -190,6 +179,7 @@ defineExpose({ focus })
190
179
  :placeholder="placeholder"
191
180
  spellcheck="false"
192
181
  :type="type"
182
+ :value="modelValue"
193
183
  @blur="onFieldBlur"
194
184
  @focus="onFieldFocus"
195
185
  @input="onFieldInput"
@@ -2,7 +2,7 @@
2
2
  import type { FieldSelect, FieldSelectOption } from '../../types/fields'
3
3
  import { vOnClickOutside } from '@vueuse/components'
4
4
 
5
- const props = withDefaults(defineProps<FieldSelect>(), {
5
+ const props = withDefaults(defineProps<Omit<FieldSelect, 'modelValue'>>(), {
6
6
  border: 'full',
7
7
  caret: true,
8
8
  columns: () => [],
@@ -13,7 +13,6 @@ const props = withDefaults(defineProps<FieldSelect>(), {
13
13
  label: '',
14
14
  labelIcon: undefined,
15
15
  maxHeight: 'xs',
16
- modelValue: undefined,
17
16
  openOnHover: false,
18
17
  options: () => [],
19
18
  padding: true,
@@ -24,15 +23,16 @@ const props = withDefaults(defineProps<FieldSelect>(), {
24
23
  })
25
24
 
26
25
  const emit = defineEmits<{
27
- 'change': [event: MouseEvent, value: string]
28
- 'click': [event: MouseEvent, value: string]
29
- 'optionClick': [event: MouseEvent, value: string]
30
- 'update:modelValue': [value: string]
26
+ change: [event: MouseEvent, value: string]
27
+ click: [event: MouseEvent, value: string]
28
+ optionClick: [event: MouseEvent, value: string]
31
29
  }>()
32
30
 
33
31
  const { getIcon } = useLayerIcons()
34
32
  const { fadeIn } = useMotion()
35
33
 
34
+ const modelValue = defineModel<FieldSelect['modelValue']>({ default: '' })
35
+
36
36
  const opened = ref(false)
37
37
  const uuid = ref(`${Math.floor((1 + Math.random()) * 0x100000)}`)
38
38
 
@@ -66,7 +66,7 @@ const computedOptions = computed(() => {
66
66
 
67
67
  const selectedOption = computed(() => {
68
68
  return computedOptions.value.find((option) => {
69
- return option.value === props.modelValue
69
+ return option.value === modelValue.value
70
70
  })
71
71
  })
72
72
 
@@ -75,9 +75,9 @@ function reset() {
75
75
  }
76
76
 
77
77
  function selectOption(event: MouseEvent, value: string) {
78
- emit('change', event, value)
79
- emit('update:modelValue', value)
78
+ modelValue.value = value
80
79
 
80
+ emit('change', event, value)
81
81
  reset()
82
82
  }
83
83
 
@@ -2,9 +2,8 @@
2
2
  import type { FieldTabs, FieldTabsAction } from '../../types/fields'
3
3
  import { NuxtLinkLocale } from '#components'
4
4
 
5
- const props = withDefaults(defineProps<FieldTabs>(), {
5
+ const props = withDefaults(defineProps<Omit<FieldTabs, 'modelValue'>>(), {
6
6
  minimizeOnMobile: false,
7
- modelValue: undefined,
8
7
  multiple: false,
9
8
  size: 'base',
10
9
  tabs: undefined,
@@ -12,36 +11,39 @@ const props = withDefaults(defineProps<FieldTabs>(), {
12
11
  })
13
12
 
14
13
  const emit = defineEmits<{
15
- 'change': [event: MouseEvent, tabValue: number | string, action: FieldTabsAction, activeTabs: Array<number | string>]
16
- 'click': [event: MouseEvent, tabValue: number | string, activeTabs: Array<number | string>]
17
- 'update:modelValue': [value?: Array<number | string> | number | string]
14
+ change: [event: MouseEvent, tabValue: number | string, action: FieldTabsAction, activeTabs: Array<number | string>]
15
+ click: [event: MouseEvent, tabValue: number | string, activeTabs: Array<number | string>]
18
16
  }>()
19
17
 
18
+ const modelValue = defineModel<FieldTabs['modelValue']>({ default: () => [] })
19
+
20
20
  function onTabClick(event: MouseEvent, tabValue: number | string) {
21
21
  let activeTabs = [tabValue]
22
22
 
23
23
  // When multiple values are not allowed and tab is not already active
24
- if (!props.multiple && props.modelValue !== tabValue) {
24
+ if (!props.multiple && modelValue.value !== tabValue) {
25
25
  emit('change', event, tabValue, 'added', activeTabs)
26
26
  }
27
27
 
28
28
  // When multiple values are allowed
29
29
  if (props.multiple) {
30
30
  // Remove the tab when already active
31
- if (Array.isArray(props.modelValue) && props.modelValue.includes(tabValue)) {
32
- activeTabs = props.modelValue.filter(item => item !== tabValue)
31
+ if (Array.isArray(modelValue.value) && modelValue.value.includes(tabValue)) {
32
+ activeTabs = modelValue.value.filter(item => item !== tabValue)
33
33
 
34
34
  emit('change', event, tabValue, 'removed', activeTabs)
35
35
  }
36
36
  // Push the tab when not already active
37
37
  else {
38
- activeTabs = Array.isArray(props.modelValue) ? [...props.modelValue, tabValue] : [tabValue]
38
+ activeTabs = Array.isArray(modelValue.value) ? [...modelValue.value, tabValue] : [tabValue]
39
+
39
40
  emit('change', event, tabValue, 'added', activeTabs)
40
41
  }
41
42
  }
42
43
 
44
+ modelValue.value = props.multiple ? activeTabs : tabValue
45
+
43
46
  emit('click', event, tabValue, activeTabs)
44
- emit('update:modelValue', props.multiple ? activeTabs : tabValue)
45
47
  }
46
48
  </script>
47
49
 
@@ -1,7 +1,7 @@
1
1
  <script lang="ts" setup>
2
2
  import type { FieldTextarea } from '../../types/fields'
3
3
 
4
- const props = withDefaults(defineProps<FieldTextarea>(), {
4
+ const props = withDefaults(defineProps<Omit<FieldTextarea, 'modelValue'>>(), {
5
5
  autofocus: false,
6
6
  background: 'gray',
7
7
  border: true,
@@ -12,7 +12,6 @@ const props = withDefaults(defineProps<FieldTextarea>(), {
12
12
  label: '',
13
13
  labelIcon: undefined,
14
14
  loading: false,
15
- modelValue: '',
16
15
  padding: true,
17
16
  placeholder: '',
18
17
  required: false,
@@ -23,25 +22,17 @@ const props = withDefaults(defineProps<FieldTextarea>(), {
23
22
  })
24
23
 
25
24
  const emit = defineEmits<{
26
- 'blur': [event: FocusEvent, value: string]
27
- 'click': [event: MouseEvent, value: string]
28
- 'update:modelValue': [value: string]
25
+ blur: [event: FocusEvent, value: string]
26
+ click: [event: MouseEvent, value: string]
29
27
  }>()
30
28
 
29
+ const modelValue = defineModel<FieldTextarea['modelValue']>({ default: '' })
30
+
31
31
  const textarea = ref<HTMLTextAreaElement>()
32
32
  const uuid = ref(`${Math.floor((1 + Math.random()) * 0x100000)}`)
33
33
 
34
34
  const { isDesktopBrowser } = useDevice()
35
35
 
36
- const value = computed({
37
- get() {
38
- return `${props.modelValue}`
39
- },
40
- set(value) {
41
- emit('update:modelValue', value)
42
- },
43
- })
44
-
45
36
  onMounted(() => {
46
37
  if (props.autofocus && textarea.value && isDesktopBrowser.value) {
47
38
  textarea.value.focus()
@@ -49,21 +40,11 @@ onMounted(() => {
49
40
  })
50
41
 
51
42
  function onFieldBlur(event: FocusEvent) {
52
- const value = textarea.value?.value || ''
53
-
54
- emit('blur', event, value)
43
+ emit('blur', event, modelValue.value || '')
55
44
  }
56
45
 
57
46
  function onFieldClick(event: MouseEvent) {
58
- const value = textarea.value?.value || ''
59
-
60
- emit('click', event, value)
61
- }
62
-
63
- function onFieldInput() {
64
- const value = textarea.value?.value || ''
65
-
66
- emit('update:modelValue', value)
47
+ emit('click', event, modelValue.value || '')
67
48
  }
68
49
  </script>
69
50
 
@@ -86,7 +67,7 @@ function onFieldInput() {
86
67
  <textarea
87
68
  :id="uuid"
88
69
  ref="textarea"
89
- v-model="value"
70
+ v-model="modelValue"
90
71
  v-bind="{ 'data-enable-grammarly': 'false' }"
91
72
  class="w-full flex-1 appearance-none rounded-lg text-gray-900 font-medium tracking-tight uppercase outline-none dark:text-gray-100 placeholder-gray-600 dark:placeholder-gray-400 focus:placeholder-gray-900 hover:placeholder-gray-900 dark:focus:placeholder-gray-100 dark:hover:placeholder-gray-100"
92
73
  :class="{
@@ -110,7 +91,6 @@ function onFieldInput() {
110
91
  spellcheck="false"
111
92
  @blur="onFieldBlur"
112
93
  @click="onFieldClick"
113
- @input="onFieldInput"
114
94
  />
115
95
 
116
96
  <FieldMessage
@@ -1,7 +1,7 @@
1
1
  <script lang="ts" setup>
2
2
  import type { FieldTime } from '../../types/fields'
3
3
 
4
- const props = withDefaults(defineProps<FieldTime>(), {
4
+ const props = withDefaults(defineProps<Omit<FieldTime, 'modelValue'>>(), {
5
5
  background: 'gray',
6
6
  description: '',
7
7
  disabled: false,
@@ -10,7 +10,6 @@ const props = withDefaults(defineProps<FieldTime>(), {
10
10
  id: undefined,
11
11
  label: '',
12
12
  labelIcon: undefined,
13
- modelValue: '',
14
13
  name: undefined,
15
14
  required: false,
16
15
  size: 'base',
@@ -18,21 +17,16 @@ const props = withDefaults(defineProps<FieldTime>(), {
18
17
  })
19
18
 
20
19
  const emit = defineEmits<{
21
- 'blur': [event: FocusEvent, value: string, name?: string]
22
- 'update:modelValue': [value: string, name?: string]
20
+ blur: [event: FocusEvent, value: string, name?: string]
23
21
  }>()
24
22
 
23
+ const modelValue = defineModel<FieldTime['modelValue']>({ default: '' })
24
+
25
25
  const root = ref<HTMLDivElement>()
26
26
  const uuid = ref(`${Math.floor((1 + Math.random()) * 0x100000)}`)
27
27
 
28
28
  function onFieldBlur(event: FocusEvent) {
29
- emit('blur', event, props.modelValue, props.name)
30
- }
31
-
32
- function onFieldInput() {
33
- const value = root.value?.querySelector('input')?.value || ''
34
-
35
- emit('update:modelValue', value, props.name)
29
+ emit('blur', event, modelValue.value, props.name)
36
30
  }
37
31
  </script>
38
32
 
@@ -52,6 +46,7 @@ function onFieldInput() {
52
46
  <div class="item-center h-[42px] flex overflow-hidden border border-gray-200 rounded-lg pl-3 pr-2 dark:border-gray-800 focus-within:border-gray-400 hover:border-gray-300 dark:focus-within:border-gray-600 dark:hover:border-gray-700">
53
47
  <input
54
48
  :id="`${id}`"
49
+ v-model="modelValue"
55
50
  class="text-sm outline-none"
56
51
  :class="{
57
52
  'bg-gray-100 dark:bg-gray-900': background === 'gray',
@@ -59,7 +54,6 @@ function onFieldInput() {
59
54
  }"
60
55
  type="time"
61
56
  @blur="onFieldBlur"
62
- @input="onFieldInput"
63
57
  >
64
58
  </div>
65
59
 
@@ -1,36 +1,42 @@
1
+ import type { AreaDrawEvent, BarChartOptions, BarDrawEvent, BaseChart, DrawEvent, LineDrawEvent, Options } from 'chartist'
2
+ import { easings } from 'chartist'
3
+
1
4
  export default function useChartist() {
5
+ type EasingType = keyof typeof easings | number[]
6
+
2
7
  const progressiveLinePlugin = (params: {
3
8
  animateArea?: boolean
4
9
  delay?: number
5
10
  duration?: number
6
- easing?: any
11
+ easing?: EasingType
7
12
  stagger?: number
8
13
  } = {}) => {
9
14
  const {
10
15
  animateArea = true,
11
16
  delay = 0,
12
17
  duration = 500,
13
- easing = (window as any)?.Chartist?.Svg?.Easing?.easeOutQuart,
18
+ easing = easings.easeOutQuart,
14
19
  stagger = 0,
15
20
  } = params
16
21
 
17
- return (chart: any) => {
18
- chart.on('draw', (ctx: any) => {
22
+ return (chart: BaseChart) => {
23
+ chart.on('draw', (ctx: DrawEvent) => {
19
24
  const begin = delay + (stagger ? stagger * (ctx.seriesIndex ?? 0) : 0)
20
25
 
21
26
  // Animation for line charts
22
27
  if (ctx.type === 'line') {
23
- const node: SVGPathElement = ctx.element._node
28
+ const lineCtx = ctx as LineDrawEvent
29
+ const node = lineCtx.element.getNode<SVGPathElement>()
24
30
  const length = node.getTotalLength()
25
31
 
26
32
  // Set the stroke dasharray and dashoffset
27
- ctx.element.attr({
33
+ lineCtx.element.attr({
28
34
  'stroke-dasharray': `${length}px ${length}px`,
29
35
  'stroke-dashoffset': `${length}px`,
30
36
  })
31
37
 
32
38
  // Animate the stroke dashoffset to 0
33
- ctx.element.animate({
39
+ lineCtx.element.animate({
34
40
  'stroke-dashoffset': {
35
41
  begin,
36
42
  dur: duration,
@@ -42,67 +48,72 @@ export default function useChartist() {
42
48
  }, false)
43
49
 
44
50
  // Clean up the dash attributes after it finishes
45
- const total = delay + duration + (stagger ? stagger * (ctx.seriesIndex ?? 0) : 0)
51
+ const total = delay + duration + (stagger ? stagger * (lineCtx.seriesIndex ?? 0) : 0)
46
52
 
47
53
  window.setTimeout(() => {
48
- ctx.element.attr({
49
- 'stroke-dasharray': null,
50
- 'stroke-dashoffset': null,
54
+ lineCtx.element.attr({
55
+ 'stroke-dasharray': undefined,
56
+ 'stroke-dashoffset': undefined,
51
57
  })
52
58
  }, total + 30)
53
59
  }
54
60
 
55
61
  // Animation for area charts
56
62
  if (animateArea && ctx.type === 'area') {
57
- ctx.element.animate({
63
+ const areaCtx = ctx as AreaDrawEvent
64
+
65
+ areaCtx.element.animate({
58
66
  // eslint-disable-next-line id-length -- SVG path attribute
59
67
  d: {
60
68
  begin,
61
69
  dur: duration,
62
70
  easing,
63
71
  fill: 'freeze',
64
- from: ctx.path
72
+ from: areaCtx.path
65
73
  .clone()
66
74
  .scale(1, 0)
67
- .translate(0, ctx.chartRect.height())
75
+ .translate(0, areaCtx.chartRect.height())
68
76
  .stringify(),
69
- to: ctx.path.stringify(),
77
+ to: areaCtx.path.stringify(),
70
78
  },
71
79
  }, false)
72
80
  }
73
81
 
74
82
  // Animation for bar charts
75
83
  if (ctx.type === 'bar') {
76
- const horizontal = !!chart.options?.horizontalBars
84
+ const barCtx = ctx as BarDrawEvent
85
+ // Access private options property via type assertion
86
+ const chartOptions = (chart as unknown as { options?: Options & Partial<BarChartOptions> }).options
87
+ const horizontal = !!(chartOptions as BarChartOptions | undefined)?.horizontalBars
77
88
 
78
89
  // For vertical bars, y1 is baseline, y2 is top. For horizontal, x1 is baseline, x2 is end.
79
- const from = horizontal ? ctx.x1 : ctx.y1
80
- const to = horizontal ? ctx.x2 : ctx.y2
90
+ const from = horizontal ? barCtx.x1 : barCtx.y1
91
+ const to = horizontal ? barCtx.x2 : barCtx.y2
81
92
 
82
93
  // Start collapsed at baseline
83
94
  if (horizontal) {
84
- ctx.element.attr({ x2: from })
85
- ctx.element.animate({
95
+ barCtx.element.attr({ x2: from })
96
+ barCtx.element.animate({
86
97
  x2: {
87
98
  begin,
88
99
  dur: duration,
89
100
  easing,
90
101
  fill: 'freeze',
91
- from,
92
- to,
102
+ from: String(from),
103
+ to: String(to),
93
104
  },
94
105
  }, false)
95
106
  }
96
107
  else {
97
- ctx.element.attr({ y2: from })
98
- ctx.element.animate({
108
+ barCtx.element.attr({ y2: from })
109
+ barCtx.element.animate({
99
110
  y2: {
100
111
  begin,
101
112
  dur: duration,
102
113
  easing,
103
114
  fill: 'freeze',
104
- from,
105
- to,
115
+ from: String(from),
116
+ to: String(to),
106
117
  },
107
118
  }, false)
108
119
  }
@@ -46,7 +46,7 @@ export interface FieldInput {
46
46
  lowercaseOnly?: boolean
47
47
  max?: number
48
48
  min?: number
49
- modelValue?: string
49
+ modelValue: string
50
50
  placeholder?: string
51
51
  required?: boolean
52
52
  size?: FieldSize
@@ -171,7 +171,7 @@ export interface FieldTime {
171
171
  id: number | string
172
172
  label?: BaseTextText
173
173
  labelIcon?: string
174
- modelValue?: string
174
+ modelValue: string
175
175
  name?: string
176
176
  required?: boolean
177
177
  size?: FieldSize
@@ -5,7 +5,7 @@ import type * as Fields from './fields'
5
5
  declare module '@vue/runtime-core' {
6
6
  interface ComponentCustomProperties {
7
7
  vHotkey?: Record<string, (event?: KeyboardEvent | MouseEvent) => void>
8
- vTooltip?: Record<string, any> | string
8
+ vTooltip?: Record<string, unknown> | string
9
9
  }
10
10
  }
11
11
 
package/nuxt.config.ts CHANGED
@@ -25,7 +25,7 @@ export default defineNuxtConfig({
25
25
  },
26
26
  },
27
27
 
28
- // --> COMPONENTS, CSS, MODULES & PLUGINS <--
28
+ // --> COMPONENTS, CSS & MODULES <--
29
29
 
30
30
  components: [
31
31
  {
@@ -116,8 +116,8 @@ export default defineNuxtConfig({
116
116
 
117
117
  unocss: {
118
118
  nuxtLayers: true,
119
- presets: uno.presets as any,
120
- rules: uno.rules as any,
119
+ presets: uno.presets,
120
+ rules: uno.rules,
121
121
  theme: uno.theme,
122
122
  },
123
123
  })
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@saasmakers/ui",
3
3
  "type": "module",
4
- "version": "0.1.71",
4
+ "version": "0.1.73",
5
5
  "private": false,
6
6
  "description": "Reusable Nuxt UI components for SaaS Makers projects",
7
7
  "license": "MIT",
@@ -34,7 +34,6 @@
34
34
  "@nuxtjs/robots": "5.5.6",
35
35
  "@nuxtjs/sitemap": "7.4.7",
36
36
  "@pinia/nuxt": "0.11.2",
37
- "@types/chartist": "1.0.4",
38
37
  "@unocss/nuxt": "66.5.4",
39
38
  "@unocss/reset": "66.5.10",
40
39
  "@vuelidate/core": "2.0.3",
@@ -55,7 +54,7 @@
55
54
  "devDependencies": {
56
55
  "nuxt": "4.2.1",
57
56
  "typescript": "5.9.3",
58
- "@saasmakers/shared": "0.1.3"
57
+ "@saasmakers/shared": "0.1.4"
59
58
  },
60
59
  "scripts": {
61
60
  "dev": "nuxi dev",
package/uno.config.ts CHANGED
@@ -1,6 +1,7 @@
1
+ import type { Preset } from 'unocss'
1
2
  import { defineConfig, presetWind3 } from 'unocss'
2
3
 
3
- export const presets = [presetWind3()]
4
+ export const presets: Preset[] = [presetWind3()]
4
5
 
5
6
  export const rules: Array<[string, Record<string, string>]> = [
6
7
  [
@@ -185,7 +186,7 @@ export const theme = {
185
186
  }
186
187
 
187
188
  export default defineConfig({
188
- presets: [presetWind3()] as any,
189
+ presets,
189
190
  rules,
190
191
  theme,
191
192
  })