@teammodlr/ui-kit 3.0.0-beta.7 → 3.0.0
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.
- package/lib/components/checkbox/Checkbox.vue.d.ts +4 -4
- package/lib/components/clearbutton/ClearButton.vue.d.ts +7 -0
- package/lib/components/clearbutton/style/ClearButton.css.d.ts +2 -0
- package/lib/components/clearbutton/style/index.d.ts +1 -0
- package/lib/components/colorpicker/ColorPicker.vue.d.ts +0 -1
- package/lib/components/colorpicker/style/ColorPicker.css.d.ts +1 -0
- package/lib/components/dialog/style/Dialog.css.d.ts +2 -0
- package/lib/components/drawer/Drawer.vue.d.ts +142 -0
- package/lib/components/drawer/style/Drawer.css.d.ts +33 -0
- package/lib/components/drawer/style/index.d.ts +1 -0
- package/lib/components/hovercard/HoverCard.vue.d.ts +122 -0
- package/lib/components/hovercard/style/HoverCard.css.d.ts +3 -0
- package/lib/components/hovercard/style/index.d.ts +1 -0
- package/lib/components/index.d.ts +4 -0
- package/lib/components/input/Input.vue.d.ts +20 -5
- package/lib/components/input/style/Input.css.d.ts +4 -0
- package/lib/components/paneldialog/PanelDialog.vue.d.ts +167 -0
- package/lib/components/paneldialog/style/PanelDialog.css.d.ts +8 -0
- package/lib/components/paneldialog/style/index.d.ts +1 -0
- package/lib/components/popover/Popover.vue.d.ts +113 -0
- package/lib/components/popover/style/Popover.css.d.ts +4 -0
- package/lib/components/popover/style/index.d.ts +1 -0
- package/lib/components/radio/Radio.vue.d.ts +5 -5
- package/lib/components/radiobutton/RadioButton.vue.d.ts +4 -4
- package/lib/components/select/Select.vue.d.ts +72 -91
- package/lib/components/select/style/Select.css.d.ts +9 -1
- package/lib/components/switch/Switch.vue.d.ts +4 -4
- package/lib/components/textarea/Textarea.vue.d.ts +16 -5
- package/lib/components/textarea/style/Textarea.css.d.ts +2 -0
- package/lib/composables/useInput.d.ts +9 -2
- package/lib/index.cjs.js +3 -3
- package/lib/index.es.js +11870 -9642
- package/lib/style.css +1 -1
- package/lib/tsconfig.app.tsbuildinfo +1 -0
- package/package.json +7 -4
- package/src/components/cardcontextmenu/style/Dropdown.css.ts +7 -0
- package/src/components/clearbutton/ClearButton.vue +39 -0
- package/src/components/clearbutton/style/ClearButton.css.ts +37 -0
- package/src/components/clearbutton/style/index.ts +1 -0
- package/src/components/colorpicker/ColorPicker.vue +8 -11
- package/src/components/colorpicker/examples/basic.vue +8 -17
- package/src/components/colorpicker/style/ColorPicker.css.ts +6 -1
- package/src/components/dialog/Dialog.vue +2 -5
- package/src/components/dialog/style/Dialog.css.ts +30 -0
- package/src/components/drawer/Drawer.vue +276 -0
- package/src/components/drawer/examples/basic.vue +15 -0
- package/src/components/drawer/examples/custom-title.vue +21 -0
- package/src/components/drawer/examples/index.stories.ts +24 -0
- package/src/components/drawer/examples/index.ts +7 -0
- package/src/components/drawer/examples/no-mask.vue +15 -0
- package/src/components/drawer/examples/no-outside-close.vue +15 -0
- package/src/components/drawer/examples/placements.vue +28 -0
- package/src/components/drawer/examples/with-footer.vue +21 -0
- package/src/components/drawer/examples/with-trigger.vue +13 -0
- package/src/components/drawer/style/Drawer.css.ts +208 -0
- package/src/components/drawer/style/index.ts +1 -0
- package/src/components/dropdown/Dropdown.vue +1 -1
- package/src/components/hovercard/HoverCard.vue +163 -0
- package/src/components/hovercard/style/HoverCard.css.ts +175 -0
- package/src/components/hovercard/style/index.ts +1 -0
- package/src/components/index.ts +4 -0
- package/src/components/input/Input.vue +52 -4
- package/src/components/input/examples/clearable.vue +18 -0
- package/src/components/input/examples/index.stories.ts +3 -1
- package/src/components/input/examples/index.ts +1 -0
- package/src/components/input/style/Input.css.ts +19 -0
- package/src/components/messageprovider/MessageProvider.vue +33 -7
- package/src/components/paneldialog/PanelDialog.vue +500 -0
- package/src/components/paneldialog/examples/basic.vue +36 -0
- package/src/components/paneldialog/examples/index.stories.ts +22 -0
- package/src/components/paneldialog/examples/index.ts +2 -0
- package/src/components/paneldialog/examples/modal.vue +31 -0
- package/src/components/paneldialog/style/PanelDialog.css.ts +90 -0
- package/src/components/paneldialog/style/index.ts +1 -0
- package/src/components/popover/Popover.vue +155 -0
- package/src/components/popover/examples/arrow.vue +47 -0
- package/src/components/popover/examples/basic.vue +15 -0
- package/src/components/popover/examples/index.stories.ts +19 -0
- package/src/components/popover/examples/index.ts +4 -0
- package/src/components/popover/examples/placement.vue +59 -0
- package/src/components/popover/examples/variant.vue +30 -0
- package/src/components/popover/style/Popover.css.ts +203 -0
- package/src/components/popover/style/index.ts +1 -0
- package/src/components/select/Select.vue +122 -42
- package/src/components/select/examples/clearable.vue +18 -0
- package/src/components/select/examples/fill.vue +52 -0
- package/src/components/select/examples/index.stories.ts +3 -1
- package/src/components/select/examples/index.ts +2 -0
- package/src/components/select/style/Select.css.ts +140 -24
- package/src/components/tab/Tab.vue +1 -1
- package/src/components/tab/style/Tab.css.ts +6 -0
- package/src/components/textarea/Textarea.vue +40 -4
- package/src/components/textarea/examples/clearable.vue +16 -0
- package/src/components/textarea/examples/index.stories.ts +2 -1
- package/src/components/textarea/examples/index.ts +1 -0
- package/src/components/textarea/style/Textarea.css.ts +10 -0
- package/src/composables/useInput.ts +10 -2
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './Popover.css';
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
<template>
|
|
2
2
|
<PopoverRoot :open="isOpen" @update:open="handleOpenChange">
|
|
3
|
-
<div ref="selectRef" tabindex="-1">
|
|
3
|
+
<div ref="selectRef" tabindex="-1" :class="fillRootClass">
|
|
4
4
|
<label v-if="label" :for="id" :class="style.label" :id="`${id}-label`">
|
|
5
5
|
{{ label }}
|
|
6
6
|
</label>
|
|
@@ -16,7 +16,7 @@
|
|
|
16
16
|
<div :class="selectComputedClasses">
|
|
17
17
|
<template v-if="multiple && Array.isArray(selected) && selected.length > 0">
|
|
18
18
|
<MTag v-for="value in selectedMax" :key="value" :closeable="true"
|
|
19
|
-
@close="
|
|
19
|
+
@close="() => removeSelected(value)" :size="size">
|
|
20
20
|
{{ getSelectedLabel(value) }}
|
|
21
21
|
</MTag>
|
|
22
22
|
<template v-if="selectedCountNotShown > 0">
|
|
@@ -26,15 +26,16 @@
|
|
|
26
26
|
</template>
|
|
27
27
|
</template>
|
|
28
28
|
<template v-else-if="!multiple && selected">
|
|
29
|
-
{{ getSelectedLabel(selected) }}
|
|
29
|
+
<span :class="fillLabelClass">{{ getSelectedLabel(selected) }}</span>
|
|
30
30
|
</template>
|
|
31
31
|
<template v-else>
|
|
32
|
-
<div :class="style.placeholder">{{ placeholder }}</div>
|
|
32
|
+
<div :class="[style.placeholder, fillLabelClass]">{{ placeholder }}</div>
|
|
33
33
|
</template>
|
|
34
34
|
<span :class="selectComputedArrowClasses">
|
|
35
35
|
<svg xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="lucide lucide-chevron-down-icon lucide-chevron-down"><path d="m6 9 6 6 6-6"/></svg>
|
|
36
36
|
</span>
|
|
37
37
|
</div>
|
|
38
|
+
<MClearButton v-if="showClear" :class="style.clear" @clear="clearSelected" />
|
|
38
39
|
</div>
|
|
39
40
|
</PopoverTrigger>
|
|
40
41
|
|
|
@@ -71,24 +72,30 @@
|
|
|
71
72
|
<input v-if="searchable" type="text" ref="searchRef" v-model="search" placeholder="Search"
|
|
72
73
|
:class="style.searchInput" :data-input="`select-menu-search-${id}`" />
|
|
73
74
|
</div>
|
|
74
|
-
<div :class="style.
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
75
|
+
<div v-if="computedOptions.length === 0" :class="style.noResults">No results</div>
|
|
76
|
+
<VList
|
|
77
|
+
v-else
|
|
78
|
+
ref="virtualListRef"
|
|
79
|
+
:data="computedOptions"
|
|
80
|
+
:item-size="optionItemHeight"
|
|
81
|
+
:style="{ height: optionsHeight + 'px', padding: '4px' }"
|
|
82
|
+
>
|
|
83
|
+
<template #default="{ item, index }">
|
|
84
|
+
<div :class="[optionSizeClass, {
|
|
85
|
+
[style.option]: true,
|
|
86
|
+
[style.optionSelected]: item.active,
|
|
87
|
+
[style.optionFocused]: selectedIndex === index
|
|
88
|
+
}]" @click.prevent="item.onClick" @mouseenter="selectedIndex = index"
|
|
89
|
+
:data-element="`select-menu-option-${id}-${item.value}`">
|
|
90
|
+
<span :class="style.optionIcon">
|
|
91
|
+
<svg v-if="item.active" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20" fill="currentColor" aria-hidden="true">
|
|
92
|
+
<path fill-rule="evenodd" d="M16.704 4.153a.75.75 0 01.143 1.052l-8 10.5a.75.75 0 01-1.127.075l-4.5-4.5a.75.75 0 011.06-1.06l3.894 3.893 7.48-9.817a.75.75 0 011.05-.143z" clip-rule="evenodd"></path>
|
|
93
|
+
</svg>
|
|
94
|
+
</span>
|
|
95
|
+
<span :class="style.optionLabel">{{ item.label }}</span>
|
|
96
|
+
</div>
|
|
90
97
|
</template>
|
|
91
|
-
</
|
|
98
|
+
</VList>
|
|
92
99
|
</PopoverContent>
|
|
93
100
|
</Transition>
|
|
94
101
|
</PopoverPortal>
|
|
@@ -101,7 +108,7 @@
|
|
|
101
108
|
</template>
|
|
102
109
|
|
|
103
110
|
<script lang="ts">
|
|
104
|
-
import { useInput } from '../../composables/useInput';
|
|
111
|
+
import { useInput, type InputEmitsMap } from '../../composables/useInput';
|
|
105
112
|
import type { MaybeArray, Size } from '../../types/props';
|
|
106
113
|
import { PopoverContent, PopoverPortal, PopoverRoot, PopoverTrigger } from 'reka-ui';
|
|
107
114
|
import { useEventListener } from '@vueuse/core';
|
|
@@ -115,7 +122,13 @@ import {
|
|
|
115
122
|
type PropType
|
|
116
123
|
} from 'vue';
|
|
117
124
|
import MTag from '../tag/Tag.vue';
|
|
125
|
+
import MClearButton from '../clearbutton/ClearButton.vue';
|
|
126
|
+
import { VList } from 'virtua/vue';
|
|
118
127
|
import * as style from './style';
|
|
128
|
+
|
|
129
|
+
interface VListHandle {
|
|
130
|
+
scrollToIndex(index: number, opts?: { align?: 'start' | 'center' | 'end' | 'nearest' }): void;
|
|
131
|
+
}
|
|
119
132
|
import { fade } from '../../styles/transitions.css';
|
|
120
133
|
import { useInteractive } from '../../composables/useInteractive';
|
|
121
134
|
import type { OnUpdateValue, OnUpdateValueImpl } from './types';
|
|
@@ -127,7 +140,10 @@ let shouldOpenNextFocusedSelect = false;
|
|
|
127
140
|
export default defineComponent({
|
|
128
141
|
name: 'MSelect',
|
|
129
142
|
emits: {
|
|
130
|
-
...useInput.emits()
|
|
143
|
+
...(useInput.emits() as unknown as InputEmitsMap),
|
|
144
|
+
'on-open': () => true,
|
|
145
|
+
'on-close': () => true,
|
|
146
|
+
clear: () => true
|
|
131
147
|
},
|
|
132
148
|
props: {
|
|
133
149
|
...useInput.props(),
|
|
@@ -184,7 +200,7 @@ export default defineComponent({
|
|
|
184
200
|
default: false
|
|
185
201
|
},
|
|
186
202
|
error: {
|
|
187
|
-
type: String
|
|
203
|
+
type: String as PropType<string | null>
|
|
188
204
|
},
|
|
189
205
|
allowBlank: {
|
|
190
206
|
type: Boolean,
|
|
@@ -202,9 +218,26 @@ export default defineComponent({
|
|
|
202
218
|
type: Boolean,
|
|
203
219
|
default: false
|
|
204
220
|
},
|
|
221
|
+
fill: {
|
|
222
|
+
type: Boolean,
|
|
223
|
+
default: false
|
|
224
|
+
},
|
|
225
|
+
noBorder: {
|
|
226
|
+
type: Boolean,
|
|
227
|
+
default: false
|
|
228
|
+
},
|
|
205
229
|
zIndex: {
|
|
206
230
|
type: Number
|
|
207
231
|
},
|
|
232
|
+
clearable: {
|
|
233
|
+
type: Boolean,
|
|
234
|
+
default: false
|
|
235
|
+
},
|
|
236
|
+
// Value a single select resets to when cleared (e.g. a "Don't restrict" option)
|
|
237
|
+
clearValue: {
|
|
238
|
+
type: [String, Number, Boolean, Object] as PropType<string | number | boolean | object | null>,
|
|
239
|
+
default: undefined
|
|
240
|
+
},
|
|
208
241
|
showDataOptions: {
|
|
209
242
|
type: Boolean,
|
|
210
243
|
default: true
|
|
@@ -214,6 +247,8 @@ export default defineComponent({
|
|
|
214
247
|
},
|
|
215
248
|
components: {
|
|
216
249
|
MTag,
|
|
250
|
+
MClearButton,
|
|
251
|
+
VList,
|
|
217
252
|
PopoverContent,
|
|
218
253
|
PopoverPortal,
|
|
219
254
|
PopoverRoot,
|
|
@@ -221,7 +256,7 @@ export default defineComponent({
|
|
|
221
256
|
},
|
|
222
257
|
setup(props, { emit, expose }) {
|
|
223
258
|
const container = ref<HTMLElement | null>(null);
|
|
224
|
-
const
|
|
259
|
+
const virtualListRef = ref<VListHandle | null>(null);
|
|
225
260
|
const searchRef = ref<HTMLInputElement>();
|
|
226
261
|
const selectRef = ref<HTMLElement>();
|
|
227
262
|
const popper = ref<HTMLElement>();
|
|
@@ -593,9 +628,34 @@ export default defineComponent({
|
|
|
593
628
|
}
|
|
594
629
|
}
|
|
595
630
|
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
631
|
+
const hasValue = computed(() => {
|
|
632
|
+
if (props.multiple) {
|
|
633
|
+
return Array.isArray(selected.value) && selected.value.length > 0;
|
|
634
|
+
}
|
|
635
|
+
|
|
636
|
+
if (props.clearValue !== undefined && selected.value === props.clearValue) {
|
|
637
|
+
return false;
|
|
638
|
+
}
|
|
639
|
+
|
|
640
|
+
return !!selected.value;
|
|
641
|
+
});
|
|
642
|
+
|
|
643
|
+
const showClear = computed(() => {
|
|
644
|
+
return props.clearable
|
|
645
|
+
&& hasValue.value
|
|
646
|
+
&& !disabled.value
|
|
647
|
+
&& !loading.value;
|
|
648
|
+
});
|
|
649
|
+
|
|
650
|
+
function clearSelected() {
|
|
651
|
+
selected.value = props.multiple
|
|
652
|
+
? []
|
|
653
|
+
: (props.clearValue !== undefined ? props.clearValue : '');
|
|
654
|
+
emit('clear');
|
|
655
|
+
container.value?.focus();
|
|
656
|
+
}
|
|
657
|
+
|
|
658
|
+
function removeSelected(value: string | number) {
|
|
599
659
|
if (!props.multiple) {
|
|
600
660
|
return;
|
|
601
661
|
}
|
|
@@ -741,20 +801,36 @@ export default defineComponent({
|
|
|
741
801
|
]
|
|
742
802
|
})
|
|
743
803
|
|
|
804
|
+
const optionItemHeightMap: Record<string, number> = { xs: 30, sm: 32, md: 38, lg: 42, xl: 46 };
|
|
805
|
+
const optionItemHeight = computed(() => optionItemHeightMap[props.size] ?? 38);
|
|
806
|
+
const optionsHeight = computed(() => {
|
|
807
|
+
const total = computedOptions.value.length * optionItemHeight.value + 8; // 8px = paddingTop+paddingBottom
|
|
808
|
+
return Math.min(total, 222);
|
|
809
|
+
});
|
|
810
|
+
const optionSizeClass = computed(() => style.optionSizes[props.size]);
|
|
811
|
+
const fillRootClass = computed(() => props.fill ? style.fillRoot : undefined);
|
|
812
|
+
const fillLabelClass = computed(() => props.fill ? style.fillLabel : undefined);
|
|
813
|
+
|
|
744
814
|
const computedWrapperClasses = computed(() => {
|
|
745
|
-
return [
|
|
815
|
+
return [
|
|
816
|
+
style.wrapper,
|
|
817
|
+
{ [style.fill]: props.fill }
|
|
818
|
+
];
|
|
746
819
|
});
|
|
747
820
|
|
|
748
821
|
const selectComputedClasses = computed(() => {
|
|
749
822
|
return [
|
|
750
823
|
style.base,
|
|
824
|
+
style.sizes[props.size],
|
|
751
825
|
{
|
|
826
|
+
[style.hasClear]: showClear.value,
|
|
752
827
|
[style.selectedTags]:
|
|
753
828
|
props.multiple &&
|
|
754
829
|
Array.isArray(selected.value) &&
|
|
755
830
|
selected.value.length > 0,
|
|
756
|
-
[style.focused]: open.value || focused.value,
|
|
757
|
-
|
|
831
|
+
[style.focused]: !props.noBorder && (open.value || focused.value),
|
|
832
|
+
[style.fillBase]: props.fill,
|
|
833
|
+
[style.noBorder]: props.noBorder,
|
|
758
834
|
'm-select--disabled': disabled.value || loading.value,
|
|
759
835
|
'm-select--focused': open.value || focused.value,
|
|
760
836
|
'm-select--multiple': props.multiple,
|
|
@@ -784,21 +860,20 @@ export default defineComponent({
|
|
|
784
860
|
if (!keyboardNavigation.value) {
|
|
785
861
|
return;
|
|
786
862
|
}
|
|
787
|
-
if (typeof index !== 'undefined'
|
|
788
|
-
|
|
789
|
-
block: 'nearest',
|
|
790
|
-
inline: 'nearest'
|
|
791
|
-
});
|
|
863
|
+
if (typeof index !== 'undefined') {
|
|
864
|
+
virtualListRef.value?.scrollToIndex(index, { align: 'nearest' });
|
|
792
865
|
}
|
|
793
866
|
});
|
|
794
867
|
|
|
795
868
|
watch(open, (value: boolean) => {
|
|
796
869
|
nextTick(() => {
|
|
797
870
|
if (!value) {
|
|
871
|
+
emit('on-close');
|
|
798
872
|
search.value = '';
|
|
799
873
|
}
|
|
800
874
|
|
|
801
875
|
if (value) {
|
|
876
|
+
emit('on-open');
|
|
802
877
|
zIndex.value = nextZIndex();
|
|
803
878
|
}
|
|
804
879
|
|
|
@@ -816,7 +891,7 @@ export default defineComponent({
|
|
|
816
891
|
});
|
|
817
892
|
}
|
|
818
893
|
|
|
819
|
-
if (value
|
|
894
|
+
if (value) {
|
|
820
895
|
const selectedValue = Array.isArray(selected.value)
|
|
821
896
|
? selected.value[0]
|
|
822
897
|
: selected.value;
|
|
@@ -824,9 +899,7 @@ export default defineComponent({
|
|
|
824
899
|
i => i.value === selectedValue
|
|
825
900
|
);
|
|
826
901
|
if (index !== -1) {
|
|
827
|
-
|
|
828
|
-
block: 'nearest'
|
|
829
|
-
});
|
|
902
|
+
nextTick(() => virtualListRef.value?.scrollToIndex(index, { align: 'nearest' }));
|
|
830
903
|
selectedIndex.value = index;
|
|
831
904
|
} else if (computedOptions.value.length > 0) {
|
|
832
905
|
selectedIndex.value = 0;
|
|
@@ -894,7 +967,7 @@ export default defineComponent({
|
|
|
894
967
|
|
|
895
968
|
return {
|
|
896
969
|
container,
|
|
897
|
-
|
|
970
|
+
virtualListRef,
|
|
898
971
|
searchRef,
|
|
899
972
|
selectRef,
|
|
900
973
|
popper,
|
|
@@ -922,13 +995,20 @@ export default defineComponent({
|
|
|
922
995
|
getSelectedLabel,
|
|
923
996
|
openSelect,
|
|
924
997
|
removeSelected,
|
|
998
|
+
showClear,
|
|
999
|
+
clearSelected,
|
|
925
1000
|
inputError,
|
|
926
1001
|
transitionName,
|
|
927
1002
|
inputListeners,
|
|
928
1003
|
style,
|
|
929
1004
|
focused,
|
|
930
1005
|
fade,
|
|
931
|
-
toggleAllItems
|
|
1006
|
+
toggleAllItems,
|
|
1007
|
+
optionItemHeight,
|
|
1008
|
+
optionsHeight,
|
|
1009
|
+
optionSizeClass,
|
|
1010
|
+
fillRootClass,
|
|
1011
|
+
fillLabelClass
|
|
932
1012
|
};
|
|
933
1013
|
}
|
|
934
1014
|
});
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<div style="display: flex; flex-direction: column; gap: 12px; max-width: 320px;">
|
|
3
|
+
<MSelect v-model="single" :options="options" clearable />
|
|
4
|
+
<MSelect v-model="multiple" :options="options" multiple clearable />
|
|
5
|
+
</div>
|
|
6
|
+
</template>
|
|
7
|
+
|
|
8
|
+
<script lang="ts" setup>
|
|
9
|
+
import { ref } from 'vue';
|
|
10
|
+
|
|
11
|
+
const options = Array.from({ length: 10 }, (_, i) => ({
|
|
12
|
+
value: i + 1,
|
|
13
|
+
label: `Option ${i + 1}`
|
|
14
|
+
}));
|
|
15
|
+
|
|
16
|
+
const single = ref(2);
|
|
17
|
+
const multiple = ref([1, 2]);
|
|
18
|
+
</script>
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
<template>
|
|
2
|
+
<div style="display: grid; grid-template-columns: 120px 1fr 1fr; border: 1px solid #e5e7eb;">
|
|
3
|
+
<div style="padding: 6px 8px; font-size: 13px; border-right: 1px solid #e5e7eb; border-bottom: 1px solid #e5e7eb; background: #f9fafb; font-weight: 500;">Row 1</div>
|
|
4
|
+
<div style="height: 36px; border-right: 1px solid #e5e7eb; border-bottom: 1px solid #e5e7eb;">
|
|
5
|
+
<MSelect size="xs" v-model="row1Status" :options="statusOptions" fill no-border />
|
|
6
|
+
</div>
|
|
7
|
+
<div style="height: 36px; border-bottom: 1px solid #e5e7eb;">
|
|
8
|
+
<MSelect size="xs" v-model="row1Priority" :options="priorityOptions" fill no-border />
|
|
9
|
+
</div>
|
|
10
|
+
|
|
11
|
+
<div style="padding: 6px 8px; font-size: 13px; border-right: 1px solid #e5e7eb; border-bottom: 1px solid #e5e7eb; background: #f9fafb; font-weight: 500;">Row 2</div>
|
|
12
|
+
<div style="height: 36px; border-right: 1px solid #e5e7eb; border-bottom: 1px solid #e5e7eb;">
|
|
13
|
+
<MSelect size="xs" v-model="row2Status" :options="statusOptions" fill no-border />
|
|
14
|
+
</div>
|
|
15
|
+
<div style="height: 36px; border-bottom: 1px solid #e5e7eb;">
|
|
16
|
+
<MSelect size="xs" v-model="row2Priority" :options="priorityOptions" fill no-border />
|
|
17
|
+
</div>
|
|
18
|
+
|
|
19
|
+
<div style="padding: 6px 8px; font-size: 13px; border-right: 1px solid #e5e7eb; background: #f9fafb; font-weight: 500;">Row 3</div>
|
|
20
|
+
<div style="height: 36px; border-right: 1px solid #e5e7eb;">
|
|
21
|
+
<MSelect size="xs" v-model="row3Status" :options="statusOptions" fill no-border />
|
|
22
|
+
</div>
|
|
23
|
+
<div style="height: 36px;">
|
|
24
|
+
<MSelect size="xs" v-model="row3Priority" :options="priorityOptions" fill no-border />
|
|
25
|
+
</div>
|
|
26
|
+
</div>
|
|
27
|
+
</template>
|
|
28
|
+
|
|
29
|
+
<script lang="ts" setup>
|
|
30
|
+
import { ref } from 'vue';
|
|
31
|
+
|
|
32
|
+
const statusOptions = [
|
|
33
|
+
{ value: 'todo', label: 'To Do' },
|
|
34
|
+
{ value: 'in_progress', label: 'In Progress' },
|
|
35
|
+
{ value: 'in_review', label: 'In Review' },
|
|
36
|
+
{ value: 'done', label: 'Done' }
|
|
37
|
+
];
|
|
38
|
+
|
|
39
|
+
const priorityOptions = [
|
|
40
|
+
{ value: 'low', label: 'Low' },
|
|
41
|
+
{ value: 'medium', label: 'Medium' },
|
|
42
|
+
{ value: 'high', label: 'High' },
|
|
43
|
+
{ value: 'critical', label: 'Critical' }
|
|
44
|
+
];
|
|
45
|
+
|
|
46
|
+
const row1Status = ref('in_progress');
|
|
47
|
+
const row1Priority = ref('high');
|
|
48
|
+
const row2Status = ref('todo');
|
|
49
|
+
const row2Priority = ref('medium');
|
|
50
|
+
const row3Status = ref('done');
|
|
51
|
+
const row3Priority = ref('low');
|
|
52
|
+
</script>
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import MSelect from '../Select.vue';
|
|
2
|
-
import { MSelectBasic, MSelectSearchable, MSelectMultiple } from './index';
|
|
2
|
+
import { MSelectBasic, MSelectSearchable, MSelectMultiple, MSelectFill, MSelectClearable } from './index';
|
|
3
3
|
|
|
4
4
|
import { createStory, sizeArgType } from '../../../__storybook__';
|
|
5
5
|
|
|
@@ -14,3 +14,5 @@ export default {
|
|
|
14
14
|
export const Basic = createStory(MSelectBasic);
|
|
15
15
|
export const Searchable = createStory(MSelectSearchable);
|
|
16
16
|
export const Multiple = createStory(MSelectMultiple);
|
|
17
|
+
export const Fill = createStory(MSelectFill);
|
|
18
|
+
export const Clearable = createStory(MSelectClearable);
|
|
@@ -1,3 +1,5 @@
|
|
|
1
1
|
export { default as MSelectBasic } from './basic.vue';
|
|
2
2
|
export { default as MSelectSearchable } from './searchable.vue';
|
|
3
3
|
export { default as MSelectMultiple } from './multiple.vue';
|
|
4
|
+
export { default as MSelectFill } from './fill.vue';
|
|
5
|
+
export { default as MSelectClearable } from './clearable.vue';
|
|
@@ -6,7 +6,7 @@ import {
|
|
|
6
6
|
} from '@vanilla-extract/css';
|
|
7
7
|
import { themeVars } from '../../../styles/theme.css';
|
|
8
8
|
|
|
9
|
-
const
|
|
9
|
+
const heights = {
|
|
10
10
|
xs: '26px',
|
|
11
11
|
sm: '30px',
|
|
12
12
|
md: '38px',
|
|
@@ -42,7 +42,7 @@ export const wrapper = style({
|
|
|
42
42
|
|
|
43
43
|
export const base = style({
|
|
44
44
|
vars: {
|
|
45
|
-
[vars.height]:
|
|
45
|
+
[vars.height]: heights.md,
|
|
46
46
|
[vars.radius]: borderRadiuses.md,
|
|
47
47
|
[vars.paddingX]: themeVars.space[2],
|
|
48
48
|
[vars.paddingY]: themeVars.space[0],
|
|
@@ -189,8 +189,7 @@ export const menu = style({
|
|
|
189
189
|
borderRadius: '4px',
|
|
190
190
|
border: `1px solid ${themeVars.color.gray[200]}`,
|
|
191
191
|
boxShadow: themeVars.shadow.md,
|
|
192
|
-
|
|
193
|
-
overflowY: 'auto'
|
|
192
|
+
overflow: 'hidden'
|
|
194
193
|
});
|
|
195
194
|
|
|
196
195
|
export const placeholder = style({
|
|
@@ -199,11 +198,7 @@ export const placeholder = style({
|
|
|
199
198
|
});
|
|
200
199
|
|
|
201
200
|
export const search = style({
|
|
202
|
-
// padding: `${themeVars.space[1]} ${themeVars.space[1]} 0`,
|
|
203
201
|
backgroundColor: '#FFFFFF',
|
|
204
|
-
position: 'sticky',
|
|
205
|
-
top: 0,
|
|
206
|
-
zIndex: 1,
|
|
207
202
|
borderBottom: `1px solid ${themeVars.color.gray[200]}`,
|
|
208
203
|
display: 'flex'
|
|
209
204
|
});
|
|
@@ -219,10 +214,7 @@ export const searchInput = style({
|
|
|
219
214
|
});
|
|
220
215
|
|
|
221
216
|
export const options = style({
|
|
222
|
-
|
|
223
|
-
display: 'flex',
|
|
224
|
-
flexDirection: 'column',
|
|
225
|
-
gap: themeVars.space[0.5]
|
|
217
|
+
overflow: 'hidden'
|
|
226
218
|
});
|
|
227
219
|
|
|
228
220
|
export const option = style({
|
|
@@ -234,10 +226,7 @@ export const option = style({
|
|
|
234
226
|
display: 'flex',
|
|
235
227
|
alignItems: 'center',
|
|
236
228
|
cursor: 'pointer',
|
|
237
|
-
|
|
238
|
-
fontSize: themeVars.fontSize.base,
|
|
239
|
-
paddingBlock: themeVars.space['1.5'],
|
|
240
|
-
paddingInline: themeVars.space['3'],
|
|
229
|
+
marginBottom: '2px',
|
|
241
230
|
gap: themeVars.space[2],
|
|
242
231
|
color: vars.optionColor,
|
|
243
232
|
transition: 'background-color 0.05s ease-in-out',
|
|
@@ -280,6 +269,39 @@ export const optionSelected = style({
|
|
|
280
269
|
|
|
281
270
|
export const optionLabel = style({});
|
|
282
271
|
|
|
272
|
+
export const optionSizes = styleVariants({
|
|
273
|
+
xs: {
|
|
274
|
+
minHeight: '28px',
|
|
275
|
+
fontSize: themeVars.fontSize.small,
|
|
276
|
+
paddingBlock: themeVars.space['1'],
|
|
277
|
+
paddingInline: themeVars.space['2']
|
|
278
|
+
},
|
|
279
|
+
sm: {
|
|
280
|
+
minHeight: '30px',
|
|
281
|
+
fontSize: themeVars.fontSize.base,
|
|
282
|
+
paddingBlock: themeVars.space['1'],
|
|
283
|
+
paddingInline: themeVars.space['2.5']
|
|
284
|
+
},
|
|
285
|
+
md: {
|
|
286
|
+
minHeight: '36px',
|
|
287
|
+
fontSize: themeVars.fontSize.base,
|
|
288
|
+
paddingBlock: themeVars.space['1.5'],
|
|
289
|
+
paddingInline: themeVars.space['3']
|
|
290
|
+
},
|
|
291
|
+
lg: {
|
|
292
|
+
minHeight: '40px',
|
|
293
|
+
fontSize: themeVars.fontSize.large,
|
|
294
|
+
paddingBlock: themeVars.space['2'],
|
|
295
|
+
paddingInline: themeVars.space['3']
|
|
296
|
+
},
|
|
297
|
+
xl: {
|
|
298
|
+
minHeight: '44px',
|
|
299
|
+
fontSize: themeVars.fontSize.large,
|
|
300
|
+
paddingBlock: themeVars.space['2.5'],
|
|
301
|
+
paddingInline: themeVars.space['3']
|
|
302
|
+
}
|
|
303
|
+
});
|
|
304
|
+
|
|
283
305
|
export const checkAll = style({
|
|
284
306
|
display: 'flex',
|
|
285
307
|
alignItems: 'center',
|
|
@@ -357,13 +379,15 @@ export const noResults = style({
|
|
|
357
379
|
fontSize: themeVars.fontSize.small
|
|
358
380
|
});
|
|
359
381
|
|
|
360
|
-
export const
|
|
361
|
-
width: themeVars.space[4],
|
|
362
|
-
height: themeVars.space[4],
|
|
382
|
+
export const clear = style({
|
|
363
383
|
position: 'absolute',
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
384
|
+
top: '50%',
|
|
385
|
+
right: '2.25rem',
|
|
386
|
+
transform: 'translateY(-50%)'
|
|
387
|
+
});
|
|
388
|
+
|
|
389
|
+
export const hasClear = style({
|
|
390
|
+
paddingRight: '3.75rem'
|
|
367
391
|
});
|
|
368
392
|
|
|
369
393
|
export const arrow = style({
|
|
@@ -371,12 +395,104 @@ export const arrow = style({
|
|
|
371
395
|
height: themeVars.space[4],
|
|
372
396
|
position: 'absolute',
|
|
373
397
|
right: themeVars.space[3],
|
|
374
|
-
top:
|
|
398
|
+
top: '50%',
|
|
399
|
+
transform: 'translateY(-50%)',
|
|
375
400
|
display: 'flex',
|
|
376
401
|
color: themeVars.color.gray[500],
|
|
377
402
|
transition: 'transform 0.3s ease',
|
|
378
403
|
});
|
|
379
404
|
|
|
380
405
|
export const arrowOpen = style({
|
|
381
|
-
transform: 'rotate(180deg)',
|
|
406
|
+
transform: 'translateY(-50%) rotate(180deg)',
|
|
382
407
|
})
|
|
408
|
+
|
|
409
|
+
export const fillRoot = style({
|
|
410
|
+
display: 'flex',
|
|
411
|
+
flexDirection: 'column',
|
|
412
|
+
height: '100%',
|
|
413
|
+
width: '100%'
|
|
414
|
+
});
|
|
415
|
+
|
|
416
|
+
export const fill = style({
|
|
417
|
+
flexGrow: 1,
|
|
418
|
+
width: '100%',
|
|
419
|
+
minHeight: 0
|
|
420
|
+
});
|
|
421
|
+
|
|
422
|
+
export const sizes = styleVariants({
|
|
423
|
+
xs: {
|
|
424
|
+
vars: {
|
|
425
|
+
[vars.height]: heights.xs,
|
|
426
|
+
[vars.radius]: borderRadiuses.xs,
|
|
427
|
+
[vars.paddingX]: themeVars.space[1]
|
|
428
|
+
},
|
|
429
|
+
fontSize: themeVars.fontSize.small
|
|
430
|
+
},
|
|
431
|
+
sm: {
|
|
432
|
+
vars: {
|
|
433
|
+
[vars.height]: heights.sm,
|
|
434
|
+
[vars.radius]: borderRadiuses.sm,
|
|
435
|
+
[vars.paddingX]: themeVars.space[1.5]
|
|
436
|
+
},
|
|
437
|
+
fontSize: themeVars.fontSize.small
|
|
438
|
+
},
|
|
439
|
+
md: {
|
|
440
|
+
vars: {
|
|
441
|
+
[vars.height]: heights.md,
|
|
442
|
+
[vars.radius]: borderRadiuses.md
|
|
443
|
+
}
|
|
444
|
+
},
|
|
445
|
+
lg: {
|
|
446
|
+
vars: {
|
|
447
|
+
[vars.height]: heights.lg,
|
|
448
|
+
[vars.radius]: borderRadiuses.lg,
|
|
449
|
+
[vars.paddingX]: themeVars.space[2.5]
|
|
450
|
+
},
|
|
451
|
+
fontSize: themeVars.fontSize.large
|
|
452
|
+
},
|
|
453
|
+
xl: {
|
|
454
|
+
vars: {
|
|
455
|
+
[vars.height]: heights.xl,
|
|
456
|
+
[vars.radius]: borderRadiuses.xl,
|
|
457
|
+
[vars.paddingX]: themeVars.space[3]
|
|
458
|
+
},
|
|
459
|
+
fontSize: themeVars.fontSize.large
|
|
460
|
+
}
|
|
461
|
+
});
|
|
462
|
+
|
|
463
|
+
export const fillBase = style({
|
|
464
|
+
minHeight: 'unset',
|
|
465
|
+
height: '100%',
|
|
466
|
+
lineHeight: 'normal',
|
|
467
|
+
display: 'flex',
|
|
468
|
+
alignItems: 'center',
|
|
469
|
+
overflow: 'hidden',
|
|
470
|
+
paddingRight: '2rem'
|
|
471
|
+
});
|
|
472
|
+
|
|
473
|
+
export const fillLabel = style({
|
|
474
|
+
overflow: 'hidden',
|
|
475
|
+
whiteSpace: 'nowrap',
|
|
476
|
+
textOverflow: 'ellipsis',
|
|
477
|
+
flex: 1,
|
|
478
|
+
minWidth: 0
|
|
479
|
+
});
|
|
480
|
+
|
|
481
|
+
export const noBorder = style({
|
|
482
|
+
vars: {
|
|
483
|
+
[vars.borderColor]: 'transparent'
|
|
484
|
+
},
|
|
485
|
+
borderRadius: 0,
|
|
486
|
+
boxShadow: 'none',
|
|
487
|
+
':hover': {
|
|
488
|
+
vars: {
|
|
489
|
+
[vars.borderColor]: 'transparent'
|
|
490
|
+
}
|
|
491
|
+
},
|
|
492
|
+
':focus': {
|
|
493
|
+
vars: {
|
|
494
|
+
[vars.borderColor]: 'transparent'
|
|
495
|
+
},
|
|
496
|
+
boxShadow: 'none'
|
|
497
|
+
}
|
|
498
|
+
});
|