design-system-next 2.10.2 → 2.11.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.
@@ -17,7 +17,7 @@ export const useButton = (props: ButtonPropTypes, emit: SetupContext<ButtonEmitT
17
17
 
18
18
  const buttonClassses: ComputedRef<string> = computed(() => {
19
19
  const defaultClasses = classNames(
20
- 'spr-background-color spr-flex spr-items-center spr-gap-1.5 spr-w-fit spr-min-w-[24px] spr-items-center spr-justify-center spr-rounded-md spr-outline-2 spr-outline-offset-4',
20
+ 'spr-background-color spr-flex spr-items-center spr-gap-1.5 spr-w-fit spr-min-w-[24px] spr-items-center spr-justify-center spr-rounded-md spr-outline-2 spr-outline-offset-4',
21
21
  {
22
22
  'spr-w-full': fullwidth.value,
23
23
  },
@@ -55,21 +55,21 @@ export const useButton = (props: ButtonPropTypes, emit: SetupContext<ButtonEmitT
55
55
  return classNames(
56
56
  defaultClasses,
57
57
  sizeClasses,
58
- 'spr-text-color-disabled spr-background-color-disabled !spr-border-0 !spr-shadow-none !spr-cursor-not-allowed',
58
+ 'spr-text-color-disabled spr-background-color-disabled !spr-shadow-none !spr-cursor-not-allowed spr-border-none',
59
59
  );
60
60
 
61
61
  if (variant.value === 'secondary')
62
62
  return classNames(
63
63
  defaultClasses,
64
64
  sizeClasses,
65
- 'spr-text-color-disabled spr-border-solid !spr-border !spr-border-color-disabled !spr-shadow-none !spr-cursor-not-allowed',
65
+ 'spr-text-color-disabled !spr-shadow-none !spr-cursor-not-allowed spr-border spr-border-solid spr-border-color-disabled',
66
66
  );
67
67
 
68
68
  if (variant.value === 'tertiary')
69
69
  return classNames(
70
70
  defaultClasses,
71
71
  sizeClasses,
72
- 'spr-text-color-disabled !spr-border-0 !spr-shadow-none !spr-cursor-not-allowed',
72
+ 'spr-text-color-disabled !spr-shadow-none !spr-cursor-not-allowed spr-border-none',
73
73
  );
74
74
  }
75
75
 
@@ -162,19 +162,16 @@ export const useButton = (props: ButtonPropTypes, emit: SetupContext<ButtonEmitT
162
162
  // #endregion - Background Css Class
163
163
 
164
164
  const buttonBorderCssClass: ComputedRef<string> = computed(() => {
165
- if (variant.value === 'primary' || variant.value === 'tertiary') {
166
- if (focused.value) {
167
- return 'spr-border-solid !spr-border !spr-border-white-50';
165
+ return classNames(
166
+ 'spr-border spr-border-solid',
167
+ {
168
+ 'spr-border-transparent': variant.value === 'primary' || variant.value === 'tertiary',
169
+ 'spr-border-white-50': focused.value && variant.value === 'primary' || variant.value === 'tertiary',
170
+ 'spr-border-color-base': variant.value === 'secondary' && tone.value === 'neutral',
171
+ 'spr-border-color-brand-base': variant.value === 'secondary' && tone.value === 'success',
172
+ 'spr-border-color-danger-base': variant.value === 'secondary' && tone.value === 'danger',
168
173
  }
169
-
170
- return 'spr-border-solid !spr-border !spr-border-transparent';
171
- }
172
-
173
- return classNames({
174
- 'spr-border-solid !spr-border !spr-border-color-base': tone.value === 'neutral',
175
- 'spr-border-solid !spr-border !spr-border-color-brand-base': tone.value === 'success',
176
- 'spr-border-solid !spr-border !spr-border-color-danger-base': tone.value === 'danger',
177
- });
174
+ );
178
175
  });
179
176
 
180
177
  const buttonProps: ComputedRef<Record<string, unknown>> = computed(() => {
@@ -5,7 +5,7 @@ export const definePropType = <T>(val: unknown): PropType<T> => val as PropType<
5
5
 
6
6
  const GROUPED_ITEMS_BY_TYPES = ['A-Z', 'Z-A'] as const;
7
7
 
8
- const PLACEMENTS_TYPES = [
8
+ export const PLACEMENTS_TYPES = [
9
9
  'auto',
10
10
  'auto-start',
11
11
  'auto-end',
@@ -96,6 +96,10 @@ export const dropdownPropTypes = {
96
96
  removeCurrentLevelInBackLabel: {
97
97
  type: Boolean,
98
98
  default: false,
99
+ },
100
+ noCheckInList: {
101
+ type: Boolean,
102
+ default: false,
99
103
  }
100
104
  };
101
105
 
@@ -45,6 +45,7 @@
45
45
  :group-items-by="props.groupItemsBy"
46
46
  :multi-select="props.multiSelect"
47
47
  :pre-selected-items="dropdownValue"
48
+ :no-check="props.noCheckInList"
48
49
  @update:model-value="handleSelectedItem"
49
50
  />
50
51
  <spr-ladderized-list
@@ -13,6 +13,10 @@ export type MenuListType = {
13
13
  group?: string;
14
14
  disabled?: boolean;
15
15
  _originalObject?: Record<string, unknown>; // Store original object reference when mapping complex objects
16
+ icon?: string, // String value for Iconify
17
+ iconColor?: string,
18
+ textColor?: string,
19
+ onClickFn?: () => void,
16
20
  };
17
21
 
18
22
  export type GroupedMenuListType = {
@@ -60,6 +64,10 @@ export const listPropTypes = {
60
64
  type: Boolean,
61
65
  default: false,
62
66
  },
67
+ noCheck: {
68
+ type: Boolean,
69
+ default: false,
70
+ }
63
71
  };
64
72
 
65
73
  export const listEmitTypes = {
@@ -29,11 +29,14 @@
29
29
  @click="handleSelectedItem(item)"
30
30
  >
31
31
  <spr-checkbox v-if="props.multiSelect" :checked="isItemSelected(item)" />
32
- <div class="spr-flex spr-flex-auto spr-flex-col spr-justify-start">
33
- <span class="spr-text-left spr-text-xs">{{ item.text }}</span>
34
- <span v-if="item.subtext" class="spr-body-xs-regular spr-text-color-base spr-text-left">{{
35
- item.subtext
36
- }}</span>
32
+ <div :class="[item.textColor, 'spr-flex spr-flex-row spr-gap-size-spacing-3xs spr-items-center']">
33
+ <span v-if="item.icon" :class="[item.iconColor, 'spr-mt-[2px]']"><icon :icon="item.icon" width="20px" height="20px" /></span>
34
+ <div class="spr-flex spr-flex-auto spr-flex-col spr-justify-start">
35
+ <span class="spr-text-left spr-text-xs">{{ item.text }}</span>
36
+ <span v-if="item.subtext" class="spr-body-xs-regular spr-text-color-base spr-text-left">
37
+ {{ item.subtext }}
38
+ </span>
39
+ </div>
37
40
  </div>
38
41
  <Icon
39
42
  v-if="isItemSelected(item) && !props.multiSelect"
@@ -57,24 +60,27 @@
57
60
  @click="handleSelectedItem(item)"
58
61
  >
59
62
  <spr-checkbox v-if="props.multiSelect" :disabled="item.disabled" :checked="isItemSelected(item)" />
60
- <div
61
- :class="[
62
- 'spr-flex spr-flex-auto spr-flex-col spr-justify-start',
63
- { 'spr-text-color-disabled': item.disabled },
64
- ]"
65
- >
66
- <span class="spr-text-left spr-text-xs">{{ item.text }}</span>
67
- <span
68
- v-if="item.subtext"
63
+ <div :class="[item.textColor, 'spr-flex spr-flex-row spr-gap-size-spacing-3xs spr-items-center']">
64
+ <span v-if="item.icon" :class="[item.iconColor, 'spr-mt-[2px]']"><icon :icon="item.icon" width="20px" height="20px" /></span>
65
+ <div
69
66
  :class="[
70
- 'spr-body-xs-regular spr-text-color-base spr-text-left',
67
+ 'spr-flex spr-flex-auto spr-flex-col spr-justify-start',
71
68
  { 'spr-text-color-disabled': item.disabled },
72
69
  ]"
73
- >{{ item.subtext }}</span
74
70
  >
71
+ <span class="spr-text-left spr-text-xs">{{ item.text }}</span>
72
+ <span
73
+ v-if="item.subtext"
74
+ :class="[
75
+ 'spr-body-xs-regular spr-text-color-base spr-text-left',
76
+ { 'spr-text-color-disabled': item.disabled },
77
+ ]"
78
+ >{{ item.subtext }}</span
79
+ >
80
+ </div>
75
81
  </div>
76
82
  <Icon
77
- v-if="isItemSelected(item) && !props.multiSelect"
83
+ v-if="isItemSelected(item) && !props.multiSelect && !props.noCheck"
78
84
  class="spr-text-color-brand-base spr-w-[1.39em]"
79
85
  icon="ph:check"
80
86
  />
@@ -13,7 +13,7 @@ interface ListClasses {
13
13
  export const useList = (props: ListPropTypes, emit: SetupContext<ListEmitTypes>['emit']) => {
14
14
  const selectedItems = useVModel(props, 'modelValue', emit);
15
15
 
16
- const { menuList, menuLevel, groupItemsBy, multiSelect, preSelectedItems } = toRefs(props);
16
+ const { menuList, menuLevel, groupItemsBy, multiSelect, preSelectedItems, noCheck } = toRefs(props);
17
17
 
18
18
  const listClasses: ComputedRef<ListClasses> = computed(() => {
19
19
  const listItemClasses = classNames(
@@ -232,7 +232,7 @@ export const useList = (props: ListPropTypes, emit: SetupContext<ListEmitTypes>[
232
232
 
233
233
  const getListItemClasses = (item: MenuListType) => ({
234
234
  [listClasses.value.listItemClasses]: !item.disabled,
235
- 'spr-background-color-single-active': isItemSelected(item) && !item.disabled,
235
+ 'spr-background-color-single-active': isItemSelected(item) && !item.disabled && !noCheck.value,
236
236
  'hover:spr-cursor-not-allowed spr-flex spr-cursor-pointer spr-items-center spr-gap-1.5 spr-rounded-lg spr-p-2':
237
237
  item.disabled,
238
238
  });
@@ -354,6 +354,7 @@ export const useList = (props: ListPropTypes, emit: SetupContext<ListEmitTypes>[
354
354
  } else {
355
355
  // For single-select, simply replace the selection
356
356
  selectedItems.value = [item];
357
+ if (item.onClickFn) item.onClickFn();
357
358
  }
358
359
  };
359
360
  // #endregion - Helper Methods
@@ -1,9 +1,14 @@
1
1
  <template>
2
2
  <div v-if="activePanels.length > 0" :class="stackingSidepanelClasses.sidepanelStackBackdropClasses"></div>
3
- <div ref="stacking-sidepanel-base" :class="[stackingSidepanelClasses.sidepanelStackBaseClasses]" :style="stackingSidepanelBaseTransform">
4
- <transition-group
3
+ <div
4
+ ref="stacking-sidepanel-base"
5
+ :class="[stackingSidepanelClasses.sidepanelStackBaseClasses]"
6
+ :style="stackingSidepanelBaseTransform"
7
+ >
8
+ <transition-group
5
9
  :enter-active-class="stackingSidepanelClasses.sidepanelStackTransitionEnterActiveClasses"
6
10
  :leave-active-class="stackingSidepanelClasses.sidepanelStackTransitionLeaveActiveClasses"
11
+ :move-class="stackingSidepanelClasses.sidepanelStackMoveClasses"
7
12
  :enter-from-class="stackingSidepanelClasses.sidepanelStackEnterFromClasses"
8
13
  :leave-to-class="stackingSidepanelClasses.sidepanelStackLeaveToClasses"
9
14
  appear
@@ -24,13 +29,8 @@ const stackingSidepanelBase = useTemplateRef('stacking-sidepanel-base');
24
29
  const props = defineProps(stackingSidePanelProps);
25
30
  const emits = defineEmits(stackingSidePanelEmits);
26
31
 
27
- const {
28
- showPanel,
29
- hidePanel,
30
- stackingSidepanelClasses,
31
- stackingSidepanelBaseTransform,
32
- activePanels,
33
- } = useStackingSidepanel(props, emits, stackingSidepanelBase);
32
+ const { showPanel, hidePanel, stackingSidepanelClasses, stackingSidepanelBaseTransform, activePanels } =
33
+ useStackingSidepanel(props, emits, stackingSidepanelBase);
34
34
 
35
35
  defineExpose({
36
36
  showPanel,
@@ -1,9 +1,13 @@
1
1
  import classNames from 'classnames';
2
- import { computed, ref, type SetupContext, type ShallowRef } from 'vue';
2
+ import { computed, ref, watch, type SetupContext, type ShallowRef } from 'vue';
3
3
  import { useRefHistory, useResizeObserver, useVModel, watchDeep } from '@vueuse/core';
4
4
  import type { StackingSidePanelEmitTypes, StackingSidePanelPropTypes } from './stacking-sidepanel';
5
5
 
6
- export const useStackingSidepanel = (props: StackingSidePanelPropTypes, emits:SetupContext<StackingSidePanelEmitTypes>['emit'], stackingSidepanelBase: Readonly<ShallowRef<HTMLDivElement | null>>) => {
6
+ export const useStackingSidepanel = (
7
+ props: StackingSidePanelPropTypes,
8
+ emits: SetupContext<StackingSidePanelEmitTypes>['emit'],
9
+ stackingSidepanelBase: Readonly<ShallowRef<HTMLDivElement | null>>,
10
+ ) => {
7
11
  const activePanels = useVModel(props, 'stack', emits, { deep: true });
8
12
 
9
13
  // Ensure activePanels is an array
@@ -15,6 +19,8 @@ export const useStackingSidepanel = (props: StackingSidePanelPropTypes, emits:Se
15
19
  const showPanel = (name: string) => {
16
20
  if (!activePanels.value.includes(name)) {
17
21
  activePanels.value.push(name);
22
+ // Update transform immediately
23
+ updateTransform();
18
24
  }
19
25
  };
20
26
 
@@ -25,69 +31,81 @@ export const useStackingSidepanel = (props: StackingSidePanelPropTypes, emits:Se
25
31
  // Undo resize tracker two times of history
26
32
  undoResizeTracker();
27
33
  undoResizeTracker();
34
+ // Update transform immediately
35
+ updateTransform();
28
36
  }
29
37
  };
30
38
 
31
39
  // Styling for the stacking sidepanel
32
- const stackingSidepanelBaseTransform = ref("transform: translateX()");
40
+ const stackingSidepanelBaseTransform = ref('transform: translateX()');
33
41
  // Track the width of the stacking sidepanel base
34
42
  const resizeTracker = ref(0);
35
43
  const { history, undo: undoResizeTracker } = useRefHistory(resizeTracker);
36
44
 
37
45
  // Watch for changes in the active panels to update the transform
38
46
  useResizeObserver(stackingSidepanelBase, (entries) => {
39
- const entry = entries[0]
47
+ const entry = entries[0];
40
48
  const { width } = entry.contentRect;
41
49
  resizeTracker.value = resizeTracker.value !== width ? width : resizeTracker.value;
50
+ updateTransform();
51
+ });
42
52
 
53
+ // Function to update transform based on current state
54
+ const updateTransform = () => {
43
55
  // If there is only one panel, reset the transform to default
44
56
  if (activePanels.value.length <= 1) {
45
- stackingSidepanelBaseTransform.value = "transform: translateX()";
57
+ stackingSidepanelBaseTransform.value = 'transform: translateX()';
46
58
  return;
47
59
  }
48
60
 
49
61
  stackingSidepanelBaseTransform.value = `transform: translateX(${history.value[0].snapshot}px);`;
50
- })
62
+ };
63
+
64
+ // Watch for changes in active panels and update transform immediately
65
+ watch(
66
+ activePanels,
67
+ () => {
68
+ updateTransform();
69
+ },
70
+ { flush: 'post' },
71
+ );
51
72
 
52
- const stackingSidepanelClasses = computed(() =>{
53
- const sidepanelStackBackdropClasses = 'spr-fixed spr-left-0 spr-top-0 spr-z-[1010] spr-h-full spr-w-full spr-bg-mushroom-700/60';
73
+ const stackingSidepanelClasses = computed(() => {
74
+ const sidepanelStackBackdropClasses =
75
+ 'spr-fixed spr-left-0 spr-top-0 spr-z-[1010] spr-h-full spr-w-full spr-bg-mushroom-700/60';
54
76
 
55
77
  const sidepanelStackBaseClasses = classNames(
56
78
  'spr-fixed spr-right-4 spr-top-1/2 spr-z-[1015] spr-flex spr-flex-row-reverse spr-gap-size-spacing-xs spr-transition-all spr-ease-[ease-in-out] spr-duration-[300ms]',
57
79
  );
58
80
 
59
81
  const sidepanelStackTransitionEnterActiveClasses = classNames(
60
- 'spr-transition-all spr-ease-[ease-in-out] spr-duration-[300ms]'
82
+ 'spr-transition-all spr-ease-[ease-in-out] spr-duration-[150ms]',
61
83
  );
62
84
 
63
85
  const sidepanelStackTransitionLeaveActiveClasses = classNames(
64
- 'spr-transition-all spr-ease-[ease-in-out] spr-duration-[150ms]'
86
+ 'spr-transition-all spr-ease-[ease-in-out] spr-duration-[150ms]',
65
87
  );
66
-
67
88
 
68
- const sidepanelStackEnterFromClasses = classNames(
69
- 'spr-opacity-0',
70
- {
71
- 'spr-translate-x-1/2': activePanels.value.length <= 1,
72
- }
73
- );
89
+ const sidepanelStackMoveClasses = classNames('spr-transition-all spr-ease-[ease-in-out] spr-duration-[300ms]');
74
90
 
75
- const sidepanelStackLeaveToClasses = classNames(
76
- 'spr-opacity-0',
77
- {
78
- 'spr-translate-x-1/2': activePanels.value.length <= 0,
79
- '-spr-translate-x-1/2': activePanels.value.length > 0,
80
- }
81
- );
91
+ const sidepanelStackEnterFromClasses = classNames('spr-opacity-0', {
92
+ 'spr-translate-x-1/2': activePanels.value.length <= 1,
93
+ });
94
+
95
+ const sidepanelStackLeaveToClasses = classNames('spr-opacity-0', {
96
+ 'spr-translate-x-1/2': activePanels.value.length <= 0,
97
+ '-spr-translate-x-1/2': activePanels.value.length > 0,
98
+ });
82
99
 
83
100
  return {
84
101
  sidepanelStackBackdropClasses,
85
102
  sidepanelStackBaseClasses,
86
103
  sidepanelStackTransitionEnterActiveClasses,
87
104
  sidepanelStackTransitionLeaveActiveClasses,
105
+ sidepanelStackMoveClasses,
88
106
  sidepanelStackEnterFromClasses,
89
107
  sidepanelStackLeaveToClasses,
90
- }
108
+ };
91
109
  });
92
110
 
93
111
  return {
@@ -47,10 +47,10 @@ export const useSidepanel = (props: SidepanelPropTypes, emit: SetupContext<Sidep
47
47
  );
48
48
 
49
49
  const sidepanelTransitionActiveClasses = classNames(
50
- { 'spr-transition-transform spr-duration-[150ms] spr-ease-[ease-in-out]': !isStacking.value },
50
+ { 'spr-transition-all spr-duration-[150ms] spr-ease-[ease-in-out]': !isStacking.value },
51
51
  );
52
52
 
53
- const sidepanelTransitionHiddenClasses = classNames({
53
+ const sidepanelTransitionHiddenClasses = classNames('spr-opacity-0', {
54
54
  'spr-translate-x-full -spr-translate-y-2/4': !isStacking.value && position.value === 'right',
55
55
  });
56
56
 
Binary file