sprintify-ui 0.6.34 → 0.6.36

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.
Files changed (57) hide show
  1. package/dist/sprintify-ui.es.js +15345 -15302
  2. package/dist/style.css +1 -1
  3. package/dist/tailwindcss/button.js +2 -2
  4. package/dist/tailwindcss/theme.js +14 -7
  5. package/dist/types/src/components/BaseButtonGroup.vue.d.ts +9 -0
  6. package/dist/types/src/components/BaseDataIterator.vue.d.ts +3 -3
  7. package/dist/types/src/components/BaseDataIteratorSectionButton.vue.d.ts +2 -2
  8. package/dist/types/src/components/BaseDataIteratorSectionColumns.vue.d.ts +8 -8
  9. package/dist/types/src/components/BaseDataTable.vue.d.ts +3 -3
  10. package/dist/types/src/components/BaseDataTableRowAction.vue.d.ts +4 -3
  11. package/dist/types/src/components/BaseDatePicker.vue.d.ts +10 -0
  12. package/dist/types/src/components/BaseDateSelect.vue.d.ts +9 -0
  13. package/dist/types/src/components/BaseRichText.vue.d.ts +9 -0
  14. package/dist/types/src/components/BaseTable.vue.d.ts +3 -3
  15. package/dist/types/src/components/BaseTagAutocomplete.vue.d.ts +11 -2
  16. package/dist/types/src/components/BaseTextareaAutoresize.vue.d.ts +3 -2
  17. package/dist/types/src/components/BaseTimeline.vue.d.ts +1 -1
  18. package/dist/types/src/components/BaseTimelineItem.vue.d.ts +1 -1
  19. package/dist/types/src/stories/PageInputSizes.vue.d.ts +2 -0
  20. package/dist/types/src/types/TimelineItem.d.ts +0 -9
  21. package/dist/types/src/types/index.d.ts +9 -0
  22. package/dist/types/src/utils/slots.d.ts +1 -0
  23. package/package.json +1 -1
  24. package/src/assets/base-rich-text.css +148 -26
  25. package/src/components/BaseButton.vue +3 -2
  26. package/src/components/BaseButtonGroup.vue +37 -9
  27. package/src/components/BaseColor.vue +29 -31
  28. package/src/components/BaseDataIterator.stories.js +8 -1
  29. package/src/components/BaseDataIterator.vue +36 -76
  30. package/src/components/BaseDataIteratorSectionButton.vue +8 -19
  31. package/src/components/BaseDataTable.vue +23 -16
  32. package/src/components/BaseDataTableRowAction.vue +2 -1
  33. package/src/components/BaseDatePicker.stories.js +23 -0
  34. package/src/components/BaseDatePicker.vue +65 -8
  35. package/src/components/BaseDateSelect.stories.js +25 -1
  36. package/src/components/BaseDateSelect.vue +80 -101
  37. package/src/components/BaseDropdownAutocomplete.stories.js +30 -15
  38. package/src/components/BaseHasMany.stories.js +22 -1
  39. package/src/components/BaseInput.stories.js +1 -1
  40. package/src/components/BaseInput.vue +4 -3
  41. package/src/components/BaseMediaPicturesItem.vue +2 -2
  42. package/src/components/BaseRichText.stories.js +6 -0
  43. package/src/components/BaseRichText.vue +12 -2
  44. package/src/components/BaseSelect.vue +5 -0
  45. package/src/components/BaseTable.vue +2 -1
  46. package/src/components/BaseTagAutocomplete.stories.js +1 -1
  47. package/src/components/BaseTagAutocomplete.vue +143 -88
  48. package/src/components/BaseTagAutocompleteFetch.stories.js +22 -1
  49. package/src/components/BaseTextareaAutoresize.vue +7 -7
  50. package/src/components/BaseTimeline.vue +1 -1
  51. package/src/components/BaseTimelineItem.vue +1 -1
  52. package/src/composables/inputSize.ts +5 -1
  53. package/src/stories/InputSizes.stories.js +22 -0
  54. package/src/stories/PageInputSizes.vue +205 -0
  55. package/src/types/TimelineItem.ts +0 -9
  56. package/src/types/index.ts +11 -1
  57. package/src/utils/slots.ts +13 -0
@@ -1,63 +1,44 @@
1
1
  <template>
2
2
  <div ref="autocomplete">
3
- <div
4
- class="relative z-[1] rounded border bg-white p-1"
5
- :class="[
6
- hasErrorInternal ? 'border-red-600' : 'border-slate-300',
7
- wrapperClass,
8
- ]"
9
- >
10
- <div :class="twMerge('-m-0.5 flex flex-wrap', twContainer)">
11
- <slot
12
- name="items"
13
- :items="normalizedModelValue"
14
- :remove-option="removeOption"
15
- :disabled="disabled"
3
+ <div :class="wrapperClass">
4
+ <slot
5
+ name="items"
6
+ :items="normalizedModelValue"
7
+ :remove-option="removeOption"
8
+ :disabled="disabled"
9
+ >
10
+ <div
11
+ v-for="selection in normalizedModelValue"
12
+ :key="selection.value ? selection.value : 'null'"
13
+ :class="selectionClass(selection)"
16
14
  >
17
- <div
18
- v-for="selection in normalizedModelValue"
19
- :key="selection.value ? selection.value : 'null'"
20
- class="p-0.5"
21
- >
22
- <div
23
- class="flex items-stretch rounded border"
24
- :class="[
25
- disabled ? 'cursor-not-allowed opacity-60' : '',
26
- selectionClass(selection),
27
- ]"
28
- >
29
- <div :class="[selectionLabelClass]">
30
- {{ selection.label }}
31
- </div>
32
-
33
- <button
34
- v-if="!disabled"
35
- type="button"
36
- class="flex shrink-0 appearance-none items-center justify-center border-0 bg-transparent pl-1 pr-3 text-xs outline-none"
37
- @click="removeOption(selection)"
38
- >
39
-
40
- </button>
41
- </div>
15
+ <div>
16
+ {{ selection.label }}
42
17
  </div>
43
- </slot>
44
-
45
- <div class="grow p-0.5">
46
- <input
47
- ref="inputElement"
48
- :value="keywords"
49
- type="text"
50
- :placeholder="placeholder ? placeholder : t('sui.select_an_item')"
51
- class="w-full min-w-[50px] border-none p-0 pl-1 shadow-none outline-none focus:border-none focus:shadow-none focus:outline-none focus:ring-0 disabled:cursor-not-allowed"
52
- :class="[inputClass]"
53
- autocomplete="off"
54
- :disabled="disabled"
55
- @click="open"
56
- @input="onTextInput"
57
- @keydown="onTextKeydown"
18
+
19
+ <button
20
+ type="button"
21
+ tabindex="-1"
22
+ :class="selectionDeleteClasses"
23
+ @click="removeOption(selection)"
58
24
  >
25
+
26
+ </button>
59
27
  </div>
60
- </div>
28
+ </slot>
29
+
30
+ <input
31
+ ref="inputElement"
32
+ :value="keywords"
33
+ type="text"
34
+ :placeholder="placeholder ? placeholder : t('sui.select_an_item')"
35
+ :class="inputClasses"
36
+ autocomplete="off"
37
+ :disabled="disabled"
38
+ @focus="open"
39
+ @input="onTextInput"
40
+ @keydown="onTextKeydown"
41
+ >
61
42
  </div>
62
43
 
63
44
  <div class="relative">
@@ -116,7 +97,7 @@ import { useNotificationsStore } from '@/stores/notifications';
116
97
  import BaseAutocompleteDrawer from './BaseAutocompleteDrawer.vue';
117
98
  import { twMerge } from 'tailwind-merge';
118
99
  import { t } from '@/i18n';
119
- import { Size } from '@/utils/sizes';
100
+ import { Size, sizes } from '@/utils/sizes';
120
101
 
121
102
  const notifications = useNotificationsStore();
122
103
 
@@ -141,6 +122,7 @@ const props = defineProps({
141
122
  default: undefined,
142
123
  type: String,
143
124
  },
125
+
144
126
  placeholder: {
145
127
  default: undefined,
146
128
  type: String,
@@ -178,7 +160,7 @@ const props = defineProps({
178
160
  type: Boolean,
179
161
  },
180
162
  size: {
181
- default: 'md',
163
+ default: undefined,
182
164
  type: String as PropType<Size>,
183
165
  },
184
166
  dropdownShow: {
@@ -193,6 +175,10 @@ const props = defineProps({
193
175
  default: '',
194
176
  type: [String, Array] as PropType<string | string[]>,
195
177
  },
178
+ visibleFocus: {
179
+ default: true,
180
+ type: Boolean,
181
+ },
196
182
  });
197
183
 
198
184
  const emit = defineEmits([
@@ -203,9 +189,10 @@ const emit = defineEmits([
203
189
  'scrollBottom',
204
190
  ]);
205
191
 
206
- const { hasErrorInternal, emitUpdate } = useField({
192
+ const { hasErrorInternal, emitUpdate, sizeInternal } = useField({
207
193
  name: computed(() => props.name),
208
194
  required: computed(() => props.required),
195
+ size: computed(() => props.size),
209
196
  hasError: computed(() => props.hasError),
210
197
  emit: emit,
211
198
  });
@@ -218,6 +205,31 @@ const hasOptions = useHasOptions(
218
205
  computed(() => true)
219
206
  );
220
207
 
208
+ onMounted(() => {
209
+ window.addEventListener('keydown', onWindowKeydown);
210
+ });
211
+
212
+ onBeforeUnmount(() => {
213
+ window.removeEventListener('keydown', onWindowKeydown);
214
+ });
215
+
216
+ function onWindowKeydown(event: KeyboardEvent) {
217
+
218
+ if (!opened.value) {
219
+ return;
220
+ }
221
+
222
+ const key = event.key;
223
+
224
+ if (key === 'Tab') {
225
+ close();
226
+ }
227
+
228
+ if (key === 'Escape') {
229
+ close();
230
+ }
231
+ }
232
+
221
233
  let openOfFocusTimeout = 0;
222
234
 
223
235
  onMounted(() => {
@@ -283,6 +295,7 @@ function open() {
283
295
  function close() {
284
296
  shouldFilter.value = false;
285
297
  opened.value = false;
298
+ selectionToDelete.value = null;
286
299
  blur();
287
300
  emit('close');
288
301
  }
@@ -392,6 +405,11 @@ const attemptRemoveLastSelection = () => {
392
405
  };
393
406
 
394
407
  const removeOption = (option: NormalizedOption) => {
408
+
409
+ if (props.disabled) {
410
+ return;
411
+ }
412
+
395
413
  focus();
396
414
  let newModelValue = cloneDeep(normalizedModelValue.value);
397
415
  newModelValue = newModelValue.filter((v) => v.value != option.value);
@@ -401,49 +419,86 @@ const removeOption = (option: NormalizedOption) => {
401
419
  // Element Classes
402
420
 
403
421
  const wrapperClass = computed(() => {
404
- if (props.size == 'xs') {
405
- return 'min-h-[34px]';
406
- }
407
- if (props.size == 'sm') {
408
- return 'min-h-[38px]';
409
- }
410
- return 'min-h-[42px]';
422
+ const base = 'relative z-[1] input-rounded border bg-white flex flex-wrap';
423
+ const error = hasErrorInternal.value ? 'border-red-600' : 'border-slate-300'
424
+ const height = {
425
+ 'xs': 'min-h-control-xs gap-0.5 p-0.5',
426
+ 'sm': 'min-h-control-sm gap-0.5 p-0.5',
427
+ 'md': 'min-h-control-md gap-1 p-1',
428
+ }[sizeInternal.value];
429
+
430
+ const focus = opened.value ? 'input-focus border-blue-300' : '';
431
+
432
+ return twMerge(base, error, height, focus, props.twContainer);
411
433
  });
412
434
 
413
- const inputClass = computed(() => {
414
- const base = 'h-[32px] text-base';
415
- if (props.size == 'xs') {
416
- return base + ' xs:text-xs xs:h-[22px]';
417
- }
418
- if (props.size == 'sm') {
419
- return base + ' xs:text-sm xs:h-[28px]';
420
- }
421
- return base;
435
+ const innerHeight = computed(() => {
436
+ const height = {
437
+ 'xs': 'h-[calc(theme(spacing.control-xs)_-_theme(spacing[0.5])_-_theme(spacing[0.5])_-_2px)]',
438
+ 'sm': 'h-[calc(theme(spacing.control-sm)_-_theme(spacing[0.5])_-_theme(spacing[0.5])_-_2px)]',
439
+ 'md': 'h-[calc(theme(spacing.control-md)_-_theme(spacing.1)_-_theme(spacing.1)_-_2px)]',
440
+ }[sizeInternal.value];
441
+
442
+ return height;
443
+ });
444
+
445
+ const inputClasses = computed(() => {
446
+ const base = 'grow min-w-[50px] py-0 border-none shadow-none outline-none bg-transparent';
447
+ const focus = 'focus:border-none focus:shadow-none focus:outline-none focus:ring-0';
448
+ const disabled = 'disabled:cursor-not-allowed';
449
+ const sizeConfig = sizes[sizeInternal.value];
450
+
451
+ const padding = {
452
+ 'xs': 'pl-1.5',
453
+ 'sm': 'pl-2',
454
+ 'md': 'pl-2.5',
455
+ }[sizeInternal.value];
456
+
457
+ return [base, padding, innerHeight.value, focus, disabled, sizeConfig.fontSize];
422
458
  });
423
459
 
424
460
  const selectionClass = (selection: NormalizedOption): string => {
461
+
462
+ const base = 'flex items-center rounded border';
463
+
464
+ const fontSize = {
465
+ 'xs': 'text-xs',
466
+ 'sm': 'text-xs',
467
+ 'md': 'text-sm',
468
+ }[sizeInternal.value];
469
+
470
+ const padding = {
471
+ 'xs': 'pl-2',
472
+ 'sm': 'pl-2',
473
+ 'md': 'pl-3',
474
+ }[sizeInternal.value];
475
+
476
+ let color = 'bg-slate-200 border-slate-300';
477
+
425
478
  if (
426
479
  selectionToDelete.value &&
427
480
  selectionToDelete.value.value == selection.value
428
481
  ) {
429
- return 'bg-red-200 border-red-300 text-red-800';
482
+ color = 'bg-red-200 border-red-300 text-red-800';
430
483
  }
431
- return 'bg-slate-200 border-slate-300';
484
+
485
+ const disabled = props.disabled ? 'cursor-not-allowed opacity-60' : '';
486
+
487
+ return twMerge(base, innerHeight.value, padding, color, disabled, fontSize);
432
488
  };
433
489
 
434
- const selectionLabelClass = computed((): string => {
435
- let base = 'py-[5px] pl-[0.75em] text-sm';
436
- props.disabled ? (base += ' pr-[0.75em]') : (base += ' pr-1');
437
- if (props.size == 'xs') {
438
- const classes = base + ' xs:py-[3px] xs:pl-2 xs:text-xs';
439
- return classes;
440
- }
441
- if (props.size == 'sm') {
442
- const classes = base + ' xs:py-[3px] xs:pl-2 xs:text-sm';
443
- return classes;
444
- }
445
- const classes = base;
446
- return classes;
490
+ const selectionDeleteClasses = computed(() => {
491
+ const base = 'flex shrink-0 appearance-none items-center justify-center border-0 bg-transparent outline-none';
492
+
493
+ const padding = {
494
+ 'xs': 'pl-1 pr-2',
495
+ 'sm': 'pl-1 pr-2',
496
+ 'md': 'pl-1 pr-3',
497
+ }[sizeInternal.value];
498
+
499
+ const disabled = props.disabled ? 'cursor-not-allowed opacity-60' : '';
500
+
501
+ return twMerge(base, padding, disabled);
447
502
  });
448
503
 
449
504
  defineExpose({
@@ -3,10 +3,17 @@ import ShowValue from '@/../.storybook/components/ShowValue.vue';
3
3
  import { createFieldStory } from '../../.storybook/utils';
4
4
  import BaseAppNotifications from './BaseAppNotifications.vue';
5
5
 
6
+ const sizes = ['xs', 'sm', 'md'];
7
+
6
8
  export default {
7
9
  title: 'Form/BaseTagAutocompleteFetch',
8
10
  component: BaseTagAutocompleteFetch,
9
- argTypes: {},
11
+ argTypes: {
12
+ size: {
13
+ control: { type: 'select' },
14
+ options: sizes,
15
+ },
16
+ },
10
17
  args: {
11
18
  url: 'https://effettandem.com/api/content/articles',
12
19
  labelKey: 'title',
@@ -56,6 +63,20 @@ Maximum.args = {
56
63
  max: 3,
57
64
  };
58
65
 
66
+ export const Sizes = (args) => ({
67
+ components: { BaseTagAutocompleteFetch },
68
+ setup() {
69
+ const value = ref([]);
70
+ return { args, sizes, value };
71
+ },
72
+ template: `
73
+ <div v-for="size in sizes" class="mb-1">
74
+ <p class="text-xs text-slate-600 leading-tight">{{ size }}</p>
75
+ <BaseTagAutocompleteFetch v-model="value" v-bind="args" :size="size"></BaseTagAutocompleteFetch>
76
+ </div>
77
+ `,
78
+ });
79
+
59
80
  export const SlotOption = (args) => {
60
81
  return {
61
82
  components: { BaseTagAutocompleteFetch },
@@ -55,7 +55,7 @@ const props = defineProps({
55
55
  type: String,
56
56
  },
57
57
  name: {
58
- required: true,
58
+ default: undefined,
59
59
  type: String,
60
60
  },
61
61
  required: {
@@ -145,17 +145,17 @@ function onFocus(event: FocusEvent) {
145
145
  }
146
146
 
147
147
  const textareaClasses = computed(() => {
148
- const base = 'py-2 px-3 input-rounded leading-normal tracking-normal border transition-colors duration-200';
148
+ const base = 'input-rounded leading-normal tracking-normal border transition-colors duration-200';
149
149
  const disabled = 'disabled:cursor-not-allowed disabled:text-slate-300';
150
150
  const focus = 'focus:input-focus';
151
151
  const error = hasErrorInternal.value ? 'border-red-500 focus:input-focus-error' : 'border-slate-300';
152
152
  const placeholder = 'placeholder:text-slate-400 placeholder:font-light';
153
153
  const sizeConfig = sizes[sizeInternal.value];
154
154
 
155
- const padding = {
156
- xs: 'px-2',
157
- sm: 'px-2.5',
158
- md: 'px-3',
155
+ const sizeClasses = {
156
+ xs: 'px-2 py-[0.26rem] min-h-control-xs',
157
+ sm: 'px-2.5 py-[0.31rem] min-h-control-sm',
158
+ md: 'px-3 py-[0.43rem] min-h-control-md',
159
159
  }[sizeInternal.value];
160
160
 
161
161
  return twMerge(
@@ -165,7 +165,7 @@ const textareaClasses = computed(() => {
165
165
  placeholder,
166
166
  focus,
167
167
  sizeConfig.fontSize,
168
- padding,
168
+ sizeClasses,
169
169
  props.twTextarea
170
170
  );
171
171
  });
@@ -25,7 +25,7 @@
25
25
  </template>
26
26
 
27
27
  <script lang="ts" setup>
28
- import { TimelineItem } from '../types/TimelineItem';
28
+ import { TimelineItem } from '../types';
29
29
  import { PropType } from 'vue';
30
30
  import BaseTimelineItem from './BaseTimelineItem.vue';
31
31
 
@@ -60,7 +60,7 @@
60
60
  </template>
61
61
 
62
62
  <script lang="ts" setup>
63
- import { TimelineItem } from '../types/TimelineItem';
63
+ import { TimelineItem } from '../types';
64
64
  import { PropType } from 'vue';
65
65
  import { Icon as BaseIcon } from '@iconify/vue';
66
66
  import { getColorConfig } from '@/utils/colors';
@@ -1,5 +1,5 @@
1
1
  import { useBreakpoints } from "./breakpoints";
2
- import { Size } from "@/utils/sizes";
2
+ import { Size, sizes } from "@/utils/sizes";
3
3
  import { MaybeRef } from "vue";
4
4
 
5
5
  function useInputSize(size: MaybeRef<Size | '' | undefined | null>) {
@@ -18,6 +18,10 @@ function useInputSize(size: MaybeRef<Size | '' | undefined | null>) {
18
18
  s = 'md';
19
19
  }
20
20
 
21
+ if (!Object.keys(sizes).includes(s)) {
22
+ s = 'md';
23
+ }
24
+
21
25
  return s;
22
26
  });
23
27
 
@@ -0,0 +1,22 @@
1
+ import InputSizes from './PageInputSizes.vue';
2
+
3
+ export default {
4
+ title: 'Pages/InputSize',
5
+ component: InputSizes,
6
+ parameters: {
7
+ layout: 'fullscreen',
8
+ },
9
+ };
10
+
11
+
12
+ const Template = (args) => ({
13
+ components: {
14
+ InputSizes
15
+ },
16
+ template: `<InputSizes></InputSizes>`,
17
+ setup() {
18
+ return { args };
19
+ },
20
+ });
21
+
22
+ export const Demo = Template.bind({});
@@ -0,0 +1,205 @@
1
+ <template>
2
+ <div class="p-5 flex flex-col gap-4 overflow-x-scroll overflow-y-visible pb-[400px]">
3
+ <div
4
+ v-for="size in sizes"
5
+ :key="size"
6
+ >
7
+ <div class="flex gap-1">
8
+ <BaseField :size="size">
9
+ <BaseInput
10
+ v-model="text"
11
+ placeholder="Name"
12
+ icon-left="heroicons:calendar"
13
+ />
14
+ </BaseField>
15
+ <BaseField :size="size">
16
+ <BaseSelect
17
+ v-model="valueId"
18
+ placeholder="Name"
19
+ label-key="label"
20
+ value-key="value"
21
+ :options="options"
22
+ />
23
+ </BaseField>
24
+ <BaseField
25
+ :size="size"
26
+ class="min-w-[200px]"
27
+ >
28
+ <BaseDatePicker v-model="date" />
29
+ </BaseField>
30
+ <BaseField
31
+ :size="size"
32
+ >
33
+ <BaseDateSelect v-model="date" />
34
+ </BaseField>
35
+ <BaseField :size="size">
36
+ <BaseAutocomplete
37
+ v-model="valueObject"
38
+ label-key="label"
39
+ value-key="value"
40
+ :options="options"
41
+ />
42
+ </BaseField>
43
+ <BaseField
44
+ v-if="false"
45
+ :size="size"
46
+ >
47
+ <BaseAutocompleteFetch
48
+ v-model="valueObjectFetch"
49
+ label-key="name"
50
+ value-key="id"
51
+ url="https://jsonplaceholder.typicode.com/users"
52
+ />
53
+ </BaseField>
54
+ <BaseField
55
+ v-if="false"
56
+ :size="size"
57
+ >
58
+ <BaseBelongsTo
59
+ v-model="valueId"
60
+ field="label"
61
+ primary-key="value"
62
+ :options="options"
63
+ />
64
+ </BaseField>
65
+ <BaseField
66
+ v-if="false"
67
+ :size="size"
68
+ >
69
+ <BaseBelongsToFetch
70
+ v-model="valueIdFetch"
71
+ field="name"
72
+ primary-key="id"
73
+ url="https://jsonplaceholder.typicode.com/users"
74
+ />
75
+ </BaseField>
76
+ <BaseField :size="size">
77
+ <BaseTagAutocomplete
78
+ v-model="valueArrayOfObjects"
79
+ label-key="label"
80
+ value-key="value"
81
+ :options="options"
82
+ />
83
+ </BaseField>
84
+ <BaseField
85
+ v-if="false"
86
+ :size="size"
87
+ >
88
+ <BaseTagAutocompleteFetch
89
+ v-model="valueArrayOfObjectFetch"
90
+ label-key="name"
91
+ value-key="id"
92
+ url="https://jsonplaceholder.typicode.com/users"
93
+ />
94
+ </BaseField>
95
+ <BaseField :size="size">
96
+ <BasePassword
97
+ v-model="text"
98
+ placeholder="Password"
99
+ />
100
+ </BaseField>
101
+ <BaseField :size="size">
102
+ <BaseInputPercent
103
+ v-model="number"
104
+ placeholder="Enter a value"
105
+ />
106
+ </BaseField>
107
+ <BaseField
108
+ :size="size"
109
+ class="min-w-[200px]"
110
+ >
111
+ <BaseTextareaAutoresize
112
+ v-model="text"
113
+ placeholder="Tell me a story"
114
+ />
115
+ </BaseField>
116
+ <BaseField :size="size">
117
+ <BaseButtonGroup
118
+ v-model="valueArrayOfObjects"
119
+ label-key="label"
120
+ value-key="value"
121
+ spacing="none"
122
+ :options="options.slice(0, 3)"
123
+ />
124
+ </BaseField>
125
+ <BaseField :size="size">
126
+ <BaseColor
127
+ v-model="colors"
128
+ class="flex-nowrap"
129
+ />
130
+ </BaseField>
131
+ </div>
132
+ </div>
133
+
134
+ <div
135
+ v-for="size in sizes"
136
+ :key="size"
137
+ class="flex flex-col gap-3"
138
+ >
139
+ <BaseInput
140
+ v-model="text"
141
+ :size="size"
142
+ placeholder="Name"
143
+ icon-left="heroicons:calendar"
144
+ />
145
+ <BaseDatePicker
146
+ v-model="date"
147
+ :size="size"
148
+ />
149
+ </div>
150
+ </div>
151
+ </template>
152
+
153
+ <script lang="ts" setup>
154
+ import { Size } from '@/utils/sizes';
155
+ import BaseField from '@/components/BaseField.vue';
156
+ import BaseSelect from '@/components/BaseSelect.vue';
157
+ import BaseAutocomplete from '@/components/BaseAutocomplete.vue';
158
+ import BaseInput from '@/components/BaseInput.vue';
159
+ import BaseAutocompleteFetch from '@/components/BaseAutocompleteFetch.vue';
160
+ import BaseBelongsTo from '@/components/BaseBelongsTo.vue';
161
+ import BaseBelongsToFetch from '@/components/BaseBelongsToFetch.vue';
162
+ import BaseTagAutocomplete from '@/components/BaseTagAutocomplete.vue';
163
+ import BaseTagAutocompleteFetch from '@/components/BaseTagAutocompleteFetch.vue';
164
+ import BaseButtonGroup from '@/components/BaseButtonGroup.vue';
165
+ import BaseColor from '@/components/BaseColor.vue';
166
+ import BasePassword from '@/components/BasePassword.vue';
167
+ import BaseInputPercent from '@/components/BaseInputPercent.vue';
168
+ import BaseTextareaAutoresize from '@/components/BaseTextareaAutoresize.vue';
169
+ import BaseDatePicker from '@/components/BaseDatePicker.vue';
170
+ import BaseDateSelect from '@/components/BaseDateSelect.vue';
171
+
172
+ const sizes = ref<Size[]>(['xs', 'sm', 'md']);
173
+
174
+ const text = ref('');
175
+ const number = ref('');
176
+
177
+ const valueObject = ref(null);
178
+ const valueObjectFetch = ref(null);
179
+
180
+ const valueId = ref(null);
181
+ const valueIdFetch = ref(null);
182
+
183
+ const valueArrayOfObjects = ref([]);
184
+ const valueArrayOfObjectFetch = ref([]);
185
+
186
+ const colors = ref([]);
187
+
188
+ const date = ref(null);
189
+
190
+ const options = [
191
+ { label: 'Dark Vader', value: 'dark_vader', type: 'sith' },
192
+ { label: 'Darth Maul', value: 'darth_maul', type: 'sith' },
193
+ { label: 'Dark Sidious', value: 'dark_sidious', type: 'sith' },
194
+ { label: 'Obi Wan Kenobi', value: 'obiwan', type: 'jedi' },
195
+ { label: 'Anakin Skywalker', value: 'anakin', type: 'jedi' },
196
+ { label: 'Mace Windu', value: 'windu', type: 'jedi' },
197
+ { label: 'Padme Amidala', value: 'padme', type: 'jedi' },
198
+ { label: 'Princesse Leila', value: 'leila', type: 'jedi' },
199
+ { label: 'Qui Gon Gin', value: 'quigon', type: 'jedi' },
200
+ { label: 'Chewbaca', value: 'chewbaca', type: 'jedi' },
201
+ { label: 'C3P0', value: 'c3p0', type: 'jedi' },
202
+ { label: 'R2D2', value: 'r2d2', type: 'jedi' },
203
+ ];
204
+
205
+ </script>
@@ -1,9 +0,0 @@
1
- export interface TimelineItem {
2
- title: string;
3
- icon: string;
4
- description?: null | string;
5
- date?: string | null;
6
- color?: string | null;
7
- onEdit?: () => void | Promise<void>;
8
- onDelete?: () => void | Promise<void>;
9
- }
@@ -255,4 +255,14 @@ export interface BaseCropperConfig {
255
255
  preset?: CropperPreset;
256
256
  presetOptions?: Record<string, any>;
257
257
  saveOptions?: ResultOptions;
258
- }
258
+ }
259
+
260
+ export interface TimelineItem {
261
+ title: string;
262
+ icon: string;
263
+ description?: null | string;
264
+ date?: string | null;
265
+ color?: string | null;
266
+ onEdit?: () => void | Promise<void>;
267
+ onDelete?: () => void | Promise<void>;
268
+ }