savor-ui 0.28.0 → 0.30.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/CHANGELOG.md CHANGED
@@ -2,6 +2,28 @@
2
2
 
3
3
 
4
4
 
5
+ # [0.30.0](https://gitee.com/mach552/savor-ui/compare/v0.29.0...v0.30.0) (2026-08-31)
6
+
7
+
8
+ ### Bug Fixes
9
+
10
+ * **datetime-picker:** 修复禁用样式无效问题 ([19a295b](https://gitee.com/mach552/savor-ui/commits/19a295b6475dc97eb8456a0803c22791a7f299a8))
11
+ * **input-tag:** 修复错误状态样式无效问题 ([1c219ef](https://gitee.com/mach552/savor-ui/commits/1c219efbc6f4211bc02f3f77fa9d2b076f53f6e0))
12
+ * **textarea:** 修复错误状态样式无效问题 ([595dee9](https://gitee.com/mach552/savor-ui/commits/595dee93be93033a7adf058710012d72c7f982ab))
13
+ * **textarea:** 修复禁用样式无效问题 ([86ae468](https://gitee.com/mach552/savor-ui/commits/86ae4689e9a43ad72fbc0d42093f5d89382c3f6f))
14
+
15
+
16
+ ### Features
17
+
18
+ * **form:** 新增额外内容属性和插槽 ([bd9534d](https://gitee.com/mach552/savor-ui/commits/bd9534d1ba5d70501c3bd1467fe23b8b3bdfe0d2))
19
+
20
+ # [0.29.0](https://gitee.com/mach552/savor-ui/compare/v0.28.0...v0.29.0) (2026-08-30)
21
+
22
+
23
+ ### Features
24
+
25
+ * **steps:** 新增`arrow`属性开启箭头模式 ([707c65d](https://gitee.com/mach552/savor-ui/commits/707c65db08fa6a996ef2be37ab92d90fe32a1009))
26
+
5
27
  # [0.28.0](https://gitee.com/mach552/savor-ui/compare/v0.27.0...v0.28.0) (2026-08-29)
6
28
 
7
29
 
@@ -251,7 +251,7 @@ var k = /*@__PURE__*/ m({
251
251
  t.is("range", W.value),
252
252
  t.is("error", T(j)),
253
253
  t.is("filled", xe.value)
254
- ]), C(r, Me.value), S(r, "clearable", m.clearable), S(r, "placeholder", Pe.value), S(r, "disabled", n), b(r, [t.e("input")]);
254
+ ]), C(r, Me.value), S(r, "clearable", m.clearable), S(r, "placeholder", Pe.value), S(r, "disabled", n), b(r, [t.e("inner")]);
255
255
  }), x(e, null, 1), f(() => M.value && !!A.value && m.clearable, () => {
256
256
  let e = ge();
257
257
  return y(() => b(e, [T(k).e("close")])), x(e, null, 0), d(T(n)), _(e, "click", E(De, ["stop"])), e;
@@ -264,7 +264,7 @@ var k = /*@__PURE__*/ m({
264
264
  r.$evtinput = p(Ue), _(r, "blur", We), _(r, "click", E(U, ["stop"]));
265
265
  let o = se(i);
266
266
  return a.$evtinput = p(Ge), _(a, "blur", Ke), _(a, "click", E(U, ["stop"])), y(() => {
267
- let t = T(k), n = m.disabled, i = Ne.value, s = m.clearable, c = Fe.value, l = [t.e("input")];
267
+ let t = T(k), n = m.disabled, i = Ne.value, s = m.clearable, c = Fe.value, l = [t.e("inner")];
268
268
  b(e, [
269
269
  t.e("wrapper"),
270
270
  t.is("disabled", n),
@@ -1,4 +1,4 @@
1
- import { FormItemExpose, FormItemProps } from './types';
1
+ import { FormItemExpose, FormItemProps, FormItemSlots } from './types';
2
2
  import { PublicProps, ShallowUnwrapRef, VNode } from 'vue';
3
3
  declare const __VLS_export: (__VLS_props: NonNullable<Awaited<typeof __VLS_setup>>["props"], __VLS_ctx?: __VLS_PrettifyLocal<Pick<NonNullable<Awaited<typeof __VLS_setup>>, "attrs" | "emit" | "slots">>, __VLS_exposed?: NonNullable<Awaited<typeof __VLS_setup>>["expose"], __VLS_setup?: Promise<{
4
4
  props: PublicProps & __VLS_PrettifyLocal<FormItemProps> & (typeof globalThis extends {
@@ -6,19 +6,7 @@ declare const __VLS_export: (__VLS_props: NonNullable<Awaited<typeof __VLS_setup
6
6
  } ? P : {});
7
7
  expose: (exposed: ShallowUnwrapRef<FormItemExpose>) => void;
8
8
  attrs: any;
9
- slots: {
10
- label?: (props: {
11
- label: string | undefined;
12
- }) => any;
13
- } & {
14
- label?: (props: {
15
- label: string | undefined;
16
- }) => any;
17
- } & {
18
- default?: (props: {
19
- validate: (trigger?: string) => Promise<true | void>;
20
- }) => any;
21
- };
9
+ slots: FormItemSlots;
22
10
  emit: {};
23
11
  }>) => VNode & {
24
12
  __ctx?: Awaited<typeof __VLS_setup>;
@@ -4,12 +4,12 @@ import { useNamespace as t } from "../../../hooks/src/use-namespace.mjs";
4
4
  import "../../../hooks/index.mjs";
5
5
  import { AsteriskLine as n } from "../../../icons/src/svg/editor/index.mjs";
6
6
  import { QuestionLine as r } from "../../../icons/src/svg/system/index.mjs";
7
- import { formContextKey as i, formItemContextKey as a, formItemStatusContextKey as o } from "./types.mjs";
8
- import { STooltip as s } from "../tooltip/index.mjs";
9
- import { child as c, computed as l, createComponent as u, createIf as d, createSlot as f, defineVaporComponent as p, inject as m, onMounted as h, onUnmounted as g, provide as _, ref as v, renderEffect as y, setClass as b, setInsertionState as x, setStyle as S, setText as C, template as w, toDisplayString as T, txt as E, unref as D } from "vue";
10
- import O from "async-validator";
7
+ import { formContextKey as i, formItemContextKey as a, formItemStatusContextKey as ee } from "./types.mjs";
8
+ import { STooltip as o } from "../tooltip/index.mjs";
9
+ import { child as s, computed as c, createComponent as l, createIf as u, createSlot as d, defineVaporComponent as f, inject as p, onMounted as m, onUnmounted as h, provide as g, ref as te, renderEffect as _, setClass as v, setInsertionState as y, setStyle as ne, setText as b, template as x, toDisplayString as S, txt as C, unref as w } from "vue";
10
+ import T from "async-validator";
11
11
  //#region ../components/src/form/form-item.vue?vue&type=script&setup=true&vapor=true&lang.ts
12
- var k = w("<span>"), A = w(" "), j = w("<div><label>"), M = w("<div> "), N = w("<div><div><div></div>", 1), P = /*@__PURE__*/ p({
12
+ var E = x("<span>"), D = x(" "), O = x("<div><label>"), k = x("<div>"), A = x("<div> "), j = x("<div><div><div></div>", 1), M = /*@__PURE__*/ f({
13
13
  name: "SFormItem",
14
14
  __name: "form-item",
15
15
  props: {
@@ -24,27 +24,28 @@ var k = w("<span>"), A = w(" "), j = w("<div><label>"), M = w("<div> "), N = w("
24
24
  type: Boolean,
25
25
  default: !0
26
26
  },
27
- requiredAlign: {}
27
+ requiredAlign: {},
28
+ extra: {}
28
29
  },
29
- setup(p, { expose: w }) {
30
- let P = p, F = t("form-item"), I = m(i), L = l(() => P.labelPosition ? P.labelPosition : I?.labelPosition?.value ? I?.labelPosition?.value : "left"), ee = l(() => I?.labelPosition?.value === "top" ? "" : P.labelWidth || I?.labelWidth?.value), R = l(() => P.labelAlign ? P.labelAlign : I?.labelAlign?.value ? I?.labelAlign?.value : I?.labelPosition?.value === "top" ? "left" : "right"), z = null, B = l(() => {
31
- let e = I?.model?.value;
32
- return e && P.field && e[P.field] !== void 0 ? e[P.field] : null;
33
- }), V = l(() => {
34
- let e = I?.rules?.value;
35
- return e && P.field && e[P.field] ? e[P.field] : P.rules && P.rules.length > 0 ? P.rules : [];
36
- }), H = v({
30
+ setup(f, { expose: x, slots: M }) {
31
+ let N = f, P = t("form-item"), F = p(i), I = c(() => N.labelPosition ? N.labelPosition : F?.labelPosition?.value ? F?.labelPosition?.value : "left"), L = c(() => F?.labelPosition?.value === "top" ? "" : N.labelWidth || F?.labelWidth?.value), R = c(() => N.labelAlign ? N.labelAlign : F?.labelAlign?.value ? F?.labelAlign?.value : F?.labelPosition?.value === "top" ? "left" : "right"), z = null, B = c(() => {
32
+ let e = F?.model?.value;
33
+ return e && N.field && e[N.field] !== void 0 ? e[N.field] : null;
34
+ }), V = c(() => {
35
+ let e = F?.rules?.value;
36
+ return e && N.field && e[N.field] ? e[N.field] : N.rules && N.rules.length > 0 ? N.rules : [];
37
+ }), H = te({
37
38
  state: "init",
38
39
  errorMsg: "",
39
40
  loading: !1
40
- }), U = (e) => V.value ? V.value.filter((t) => !t.trigger || !e ? !0 : t.trigger && t.trigger === e) : [], W = l(() => V.value.some((e) => e.required) && (P.showRequired || I?.showRequired?.value)), G = l(() => P.requiredAlign ? P.requiredAlign : I?.requiredAlign?.value ? I?.requiredAlign?.value : "left"), K = async (e) => {
41
- let t = P.field, n = U(e);
41
+ }), U = (e) => V.value ? V.value.filter((t) => !t.trigger || !e ? !0 : t.trigger && t.trigger === e) : [], W = c(() => V.value.some((e) => e.required) && (N.showRequired || F?.showRequired?.value)), G = c(() => N.requiredAlign ? N.requiredAlign : F?.requiredAlign?.value ? F?.requiredAlign?.value : "left"), K = async (e) => {
42
+ let t = N.field, n = U(e);
42
43
  if (n.length === 0) return !0;
43
44
  if (t) {
44
45
  let e = B.value, r = Array.isArray(e) ? "array" : e != null && typeof e != "string" ? typeof e : void 0, i = r ? n.map((e) => e.type ? e : {
45
46
  ...e,
46
47
  type: r
47
- }) : n, a = new O({ [t]: i });
48
+ }) : n, a = new T({ [t]: i });
48
49
  return H.value.loading = !0, a.validate({ [t]: e }).then(() => {
49
50
  H.value.state = "success", H.value.errorMsg = "";
50
51
  }).catch((e) => {
@@ -58,72 +59,78 @@ var k = w("<span>"), A = w(" "), j = w("<div><label>"), M = w("<div> "), N = w("
58
59
  H.value.state = "init", H.value.errorMsg = "", H.value.loading = !1;
59
60
  }, J = () => {
60
61
  q();
61
- let e = I?.model?.value;
62
- e && P.field && (e[P.field] = z);
63
- }, Y = l(() => H.value.state === "error"), X = {
62
+ let e = F?.model?.value;
63
+ e && N.field && (e[N.field] = z);
64
+ }, Y = c(() => H.value.state === "error"), X = {
64
65
  validate: K,
65
- field: P.field,
66
+ field: N.field,
66
67
  resetField: J,
67
68
  clearValidate: q
68
69
  };
69
- _(a, X), _(o, {
70
- size: I?.size,
70
+ g(a, X), g(ee, {
71
+ size: F?.size,
71
72
  error: Y
73
+ }), m(() => {
74
+ N.field && (F?.addField(X), z = F?.model?.value?.[N.field]);
72
75
  }), h(() => {
73
- P.field && (I?.addField(X), z = I?.model?.value?.[P.field]);
74
- }), g(() => {
75
- P.field && I?.removeField(X);
76
- }), w({
76
+ N.field && F?.removeField(X);
77
+ }), x({
77
78
  validate: K,
78
79
  resetField: J,
79
80
  clearValidate: q,
80
81
  validateStatus: H
81
82
  });
82
- let Z = N(), Q = c(Z, 1), $ = c(Q);
83
- return y(() => {
84
- let e = D(F), t = H.value, n = t.state;
85
- b(Z, [
83
+ let Z = j(), Q = s(Z, 1), $ = s(Q);
84
+ return _(() => {
85
+ let e = w(P), t = H.value, n = t.state;
86
+ v(Z, [
86
87
  e.b(),
87
88
  e.is("error", n === "error"),
88
89
  e.is("success", n === "success"),
89
90
  e.is("loading", t.loading),
90
- e.is("top", L.value === "top"),
91
- e.m(D(I)?.size?.value)
91
+ e.is("top", I.value === "top"),
92
+ e.m(w(F)?.size?.value)
92
93
  ]);
93
- }), x(Z, 0, 0), d(() => W.value || p.label || p.tooltip, () => {
94
- let t = j(), i = c(t);
95
- return y(() => {
96
- let n = D(F);
97
- b(t, [n.e("label-wrapper")]), b(i, [n.e("label"), n.m("align-" + R.value)]), S(i, { width: D(e)(ee.value) });
98
- }), x(i, null, 0), d(() => G.value === "left", () => [d(() => W.value, () => {
99
- let e = k();
100
- return y(() => b(e, [D(F).e("required")])), x(e, null, 0), u(D(n)), e;
101
- }), f("label", { label: () => p.label }, () => {
102
- let e = A();
103
- return y(() => C(e, T(p.label))), e;
104
- })], () => d(() => G.value === "right", () => [f("label", { label: () => p.label }, () => {
105
- let e = A();
106
- return y(() => C(e, T(p.label))), e;
107
- }), d(() => W.value, () => {
108
- let e = k();
109
- return y(() => b(e, [D(F).e("required")])), x(e, null, 0), u(D(n)), e;
110
- })], null, 2), 518), x(i, null, 1), d(() => p.tooltip, () => u(D(s), {
111
- content: () => p.tooltip,
94
+ }), y(Z, 0, 0), u(() => W.value || f.label || f.tooltip, () => {
95
+ let t = O(), i = s(t);
96
+ return _(() => {
97
+ let n = w(P);
98
+ v(t, [n.e("label-wrapper")]), v(i, [n.e("label"), n.m("align-" + R.value)]), ne(i, { width: w(e)(L.value) });
99
+ }), y(i, null, 0), u(() => G.value === "left", () => [u(() => W.value, () => {
100
+ let e = E();
101
+ return _(() => v(e, [w(P).e("required")])), y(e, null, 0), l(w(n)), e;
102
+ }), d("label", { label: () => f.label }, () => {
103
+ let e = D();
104
+ return _(() => b(e, S(f.label))), e;
105
+ })], () => u(() => G.value === "right", () => [d("label", { label: () => f.label }, () => {
106
+ let e = D();
107
+ return _(() => b(e, S(f.label))), e;
108
+ }), u(() => W.value, () => {
109
+ let e = E();
110
+ return _(() => v(e, [w(P).e("required")])), y(e, null, 0), l(w(n)), e;
111
+ })], null, 2), 518), y(i, null, 1), u(() => f.tooltip, () => l(w(o), {
112
+ content: () => f.tooltip,
112
113
  mini: ""
113
114
  }, () => {
114
- let e = k();
115
- return y(() => b(e, [D(F).e("tooltip")])), x(e, null, 0), u(D(r)), e;
115
+ let e = E();
116
+ return _(() => v(e, [w(P).e("tooltip")])), y(e, null, 0), l(w(r)), e;
116
117
  })), t;
117
- }), y(() => {
118
- let e = D(F);
119
- b(Q, [e.e("content-wrapper")]), b($, [e.e("content")]);
120
- }), x($, null, 0), f("default", { validate: () => K }), x(Q, null, 1), d(() => H.value.state === "error", () => {
121
- let e = M(), t = E(e);
122
- return y(() => {
123
- b(e, [D(F).e("error-msg")]), C(t, T(H.value.errorMsg));
118
+ }), _(() => {
119
+ let e = w(P);
120
+ v(Q, [e.e("content-wrapper")]), v($, [e.e("content")]);
121
+ }), y($, null, 0), d("default", { validate: () => K }), y(Q, null, 1), u(() => M.extra || f.extra, () => {
122
+ let e = k();
123
+ return _(() => v(e, [w(P).e("extra")])), y(e, null, 0), d("extra", null, () => {
124
+ let e = D();
125
+ return _(() => b(e, S(f.extra))), e;
126
+ }), e;
127
+ }), y(Q, null, 2), u(() => H.value.state === "error", () => {
128
+ let e = A(), t = C(e);
129
+ return _(() => {
130
+ v(e, [w(P).e("error-msg")]), b(t, S(H.value.errorMsg));
124
131
  }), e;
125
132
  }), Z;
126
133
  }
127
134
  });
128
135
  //#endregion
129
- export { P as default };
136
+ export { M as default };
@@ -1,5 +1,5 @@
1
1
  import { PublicProps, ShallowUnwrapRef, VNode, Plugin } from 'vue';
2
- import { FormItemRule, FormExpose, FormItemExpose } from './types';
2
+ import { FormItemRule, FormExpose, FormItemSlots, FormItemExpose } from './types';
3
3
  export declare const SForm: ((__VLS_props: NonNullable<Awaited<typeof __VLS_setup>>["props"], __VLS_ctx?: {
4
4
  attrs: any;
5
5
  slots: {
@@ -31,19 +31,7 @@ export declare const SForm: ((__VLS_props: NonNullable<Awaited<typeof __VLS_setu
31
31
  }) & Plugin;
32
32
  export declare const SFormItem: ((__VLS_props: NonNullable<Awaited<typeof __VLS_setup>>["props"], __VLS_ctx?: {
33
33
  attrs: any;
34
- slots: {
35
- label?: (props: {
36
- label: string | undefined;
37
- }) => any;
38
- } & {
39
- label?: (props: {
40
- label: string | undefined;
41
- }) => any;
42
- } & {
43
- default?: (props: {
44
- validate: (trigger?: string) => Promise<true | void>;
45
- }) => any;
46
- };
34
+ slots: FormItemSlots;
47
35
  emit: {};
48
36
  }, __VLS_exposed?: NonNullable<Awaited<typeof __VLS_setup>>["expose"], __VLS_setup?: Promise<{
49
37
  props: PublicProps & {
@@ -56,24 +44,13 @@ export declare const SFormItem: ((__VLS_props: NonNullable<Awaited<typeof __VLS_
56
44
  labelAlign?: "left" | "right" | undefined;
57
45
  showRequired?: boolean | undefined;
58
46
  requiredAlign?: "left" | "right" | undefined;
47
+ extra?: string | undefined;
59
48
  } & (typeof globalThis extends {
60
49
  __VLS_PROPS_FALLBACK: infer P;
61
50
  } ? P : {});
62
51
  expose: (exposed: ShallowUnwrapRef<FormItemExpose>) => void;
63
52
  attrs: any;
64
- slots: {
65
- label?: (props: {
66
- label: string | undefined;
67
- }) => any;
68
- } & {
69
- label?: (props: {
70
- label: string | undefined;
71
- }) => any;
72
- } & {
73
- default?: (props: {
74
- validate: (trigger?: string) => Promise<true | void>;
75
- }) => any;
76
- };
53
+ slots: FormItemSlots;
77
54
  emit: {};
78
55
  }>) => VNode & {
79
56
  __ctx?: Awaited<typeof __VLS_setup>;
@@ -53,6 +53,16 @@ export interface FormItemProps {
53
53
  showRequired?: boolean;
54
54
  /** 必填标识对齐方式 */
55
55
  requiredAlign?: "left" | "right";
56
+ /** 表单项额外内容 */
57
+ extra?: string;
58
+ }
59
+ export interface FormItemSlots {
60
+ /** 内容 */
61
+ default: () => any;
62
+ /** 标签 */
63
+ label: () => any;
64
+ /** 额外内容 */
65
+ extra: () => any;
56
66
  }
57
67
  export interface FormContext {
58
68
  /** 表单模型 */
@@ -9,12 +9,13 @@ export declare const SSteps: ((__VLS_props: NonNullable<Awaited<typeof __VLS_set
9
9
  items: StepsItemProps[];
10
10
  current?: number | undefined;
11
11
  vertical?: boolean | undefined;
12
- size?: "small" | "medium" | undefined;
12
+ size?: "mini" | "small" | "medium" | "large" | "larger" | undefined;
13
13
  alignCenter?: boolean | undefined;
14
14
  status?: "wait" | "loading" | "done" | "error" | "process" | undefined;
15
15
  changeable?: boolean | undefined;
16
16
  dot?: boolean | undefined;
17
17
  simple?: boolean | undefined;
18
+ arrow?: boolean | undefined;
18
19
  onChange?: ((index: number) => any) | undefined;
19
20
  "onUpdate:current"?: ((value: number) => any) | undefined;
20
21
  } & (typeof globalThis extends {
@@ -1,44 +1,41 @@
1
- import { useNamespace as e } from "../../../hooks/src/use-namespace.mjs";
1
+ import { useElementSize as e } from "../../../hooks/src/use-element-size.mjs";
2
+ import { useNamespace as t } from "../../../hooks/src/use-namespace.mjs";
2
3
  import "../../../hooks/index.mjs";
3
- import { RightLine as t } from "../../../icons/src/svg/arrow/index.mjs";
4
- import { CheckLine as n } from "../../../icons/src/svg/system/index.mjs";
5
- import { SIcon as r } from "../icon/index.mjs";
6
- import { child as i, createComponent as a, createFor as o, createIf as s, createInvoker as c, defineVaporComponent as l, delegateEvents as u, mergeModels as d, next as f, renderEffect as p, setClass as m, setInsertionState as h, setStyle as g, setText as _, template as v, toDisplayString as y, txt as b, unref as x, useModel as S, watch as C } from "vue";
4
+ import { RightLine as n } from "../../../icons/src/svg/arrow/index.mjs";
5
+ import { CheckLine as r } from "../../../icons/src/svg/system/index.mjs";
6
+ import { SIcon as i } from "../icon/index.mjs";
7
+ import { child as a, createComponent as o, createFor as s, createIf as c, createInvoker as l, defineVaporComponent as u, delegateEvents as d, mergeModels as f, renderEffect as p, setClass as m, setInsertionState as h, setStaticTemplateRef as g, setStyle as _, setText as v, template as y, toDisplayString as b, txt as x, unref as S, useModel as C, useTemplateRef as w, watch as T } from "vue";
7
8
  //#region ../components/src/steps/steps.vue?vue&type=script&setup=true&vapor=true&lang.ts
8
- var w = v("<div>"), T = v("<span> "), E = v("<div> "), D = v("<div><div></div><div><div> </div></div>"), O = v("<div>", 1);
9
- u("click");
10
- var k = /*@__PURE__*/ l({
9
+ var E = y("<div>"), D = y("<span> "), O = y("<div> "), k = y("<div><div><div> </div></div>"), A = y("<div>", 1);
10
+ d("click");
11
+ var j = /*@__PURE__*/ u({
11
12
  name: "SSteps",
12
13
  __name: "steps",
13
- props: /*@__PURE__*/ d({
14
+ props: /*@__PURE__*/ f({
14
15
  items: { default: () => [] },
15
16
  current: {},
16
- vertical: {
17
- type: Boolean,
18
- default: !1
19
- },
17
+ vertical: { type: Boolean },
20
18
  size: { default: "medium" },
21
19
  alignCenter: { type: Boolean },
22
20
  status: { default: "process" },
23
- changeable: {
24
- type: Boolean,
25
- default: !1
26
- },
27
- dot: {
28
- type: Boolean,
29
- default: !1
30
- },
31
- simple: { type: Boolean }
21
+ changeable: { type: Boolean },
22
+ dot: { type: Boolean },
23
+ simple: { type: Boolean },
24
+ arrow: { type: Boolean }
32
25
  }, {
33
26
  current: { default: 0 },
34
27
  currentModifiers: {}
35
28
  }),
36
- emits: /*@__PURE__*/ d(["change"], ["update:current"]),
37
- setup(l, { emit: u }) {
38
- let d = l, v = u, k = e("steps"), A = S(l, "current"), j = (e) => e > A.value ? "wait" : e < A.value ? "done" : e === A.value ? d.status : "", M = (e) => {
29
+ emits: /*@__PURE__*/ f(["change"], ["update:current"]),
30
+ setup(u, { emit: d }) {
31
+ let f = u, y = d, j = t("steps"), M = C(u, "current"), N = w("stepsRef"), { height: P } = e(N);
32
+ T(P, (e) => {
33
+ N.value?.style.setProperty("--s-steps-height", e + "px");
34
+ }, { immediate: !0 });
35
+ let F = (e) => e > M.value ? "wait" : e < M.value ? "done" : e === M.value ? f.status : "", I = (e) => {
39
36
  let t = { backgroundColor: "" }, n = e + 1;
40
- if (n >= d.items.length) return t.backgroundColor = "var(--s-color-fill-3)", t;
41
- switch (j(n)) {
37
+ if (n >= f.items.length) return t.backgroundColor = "var(--s-color-fill-3)", t;
38
+ switch (F(n)) {
42
39
  case "done":
43
40
  t.backgroundColor = "var(--s-color-success-6)";
44
41
  break;
@@ -51,62 +48,66 @@ var k = /*@__PURE__*/ l({
51
48
  default: t.backgroundColor = "var(--s-color-fill-3)";
52
49
  }
53
50
  return t;
54
- }, N = (e) => {
55
- d.changeable && (d.items[e]?.disabled || (A.value = e));
51
+ }, L = (e) => f.arrow ? "0%" : e < f.items.length - 1 && !f.alignCenter ? 100 / (f.items.length - 1) + "%" : 100 / f.items.length + "%", R = (e) => {
52
+ f.changeable && (f.items[e]?.disabled || (M.value = e));
56
53
  };
57
- C(A, (e) => {
58
- v("change", e);
54
+ T(M, (e) => {
55
+ y("change", e);
59
56
  });
60
- let P = O();
57
+ let z = A();
61
58
  return p(() => {
62
- let e = x(k);
63
- m(P, [
59
+ let e = S(j);
60
+ m(z, [
64
61
  e.b(),
65
- e.m(l.size),
66
- e.is("vertical", l.vertical),
67
- e.is("dot", l.dot),
68
- e.is("simple", l.simple)
62
+ e.m(u.size),
63
+ e.is("vertical", u.vertical),
64
+ e.is("dot", u.dot),
65
+ e.is("simple", u.simple),
66
+ e.is("arrow", u.arrow)
69
67
  ]);
70
- }), h(P, null, 0), o(() => l.items, (e, o) => {
71
- let u = D(), d = i(u), v = f(d, 1), S = i(v);
68
+ }), h(z, null, 0), s(() => u.items, (e, t) => {
69
+ let s = k(), d = a(s, 1), f = a(d);
72
70
  p(() => {
73
- let e = x(k), t = o.value, n = l.alignCenter, r = l.items.length;
74
- m(u, [
71
+ let e = S(j), n = t.value;
72
+ m(s, [
75
73
  e.e("step"),
76
- e.m(j(t)),
77
- e.is("center", n),
78
- e.is("changeable", l.changeable)
79
- ]), g(u, { flexBasis: t < r - 1 && !n ? 100 / (r - 1) + "%" : 100 / r + "%" }), m(d, [e.e("head")]);
80
- }), h(d, null, 0), s(() => o.value < l.items.length - 1 && !l.simple, () => {
81
- let e = w();
82
- return p(() => {
83
- m(e, [x(k).e("line")]), g(e, M(o.value));
84
- }), e;
85
- }), h(d, null, 1), s(() => l.dot, () => {
86
- let e = w();
87
- return p(() => m(e, [x(k).e("dot")])), e;
88
- }, () => {
89
- let e = w();
90
- return p(() => m(e, [x(k).e("icon")])), h(e, null, 0), s(() => j(o.value) === "loading", () => a(x(r), { loading: "" })), h(e, null, 1), s(() => j(o.value) === "done", () => a(x(n)), () => {
91
- let e = T(), t = b(e);
92
- return p(() => _(t, y(o.value + 1))), e;
93
- }, 1029), e;
94
- }, 517);
95
- let C = b(S);
74
+ e.m(F(n)),
75
+ e.is("center", u.alignCenter),
76
+ e.is("changeable", u.changeable)
77
+ ]), _(s, { flexBasis: L(n) });
78
+ }), h(s, 0, 0), c(() => !u.arrow, () => {
79
+ let e = E();
80
+ return p(() => m(e, [S(j).e("head")])), h(e, null, 0), c(() => t.value < u.items.length - 1 && !u.simple, () => {
81
+ let e = E();
82
+ return p(() => {
83
+ m(e, [S(j).e("line")]), _(e, I(t.value));
84
+ }), e;
85
+ }), h(e, null, 1), c(() => u.dot, () => {
86
+ let e = E();
87
+ return p(() => m(e, [S(j).e("dot")])), e;
88
+ }, () => {
89
+ let e = E();
90
+ return p(() => m(e, [S(j).e("icon")])), h(e, null, 0), c(() => F(t.value) === "loading", () => o(S(i), { loading: "" })), h(e, null, 1), c(() => F(t.value) === "done", () => o(S(r)), () => {
91
+ let e = D(), n = x(e);
92
+ return p(() => v(n, b(t.value + 1))), e;
93
+ }, 1029), e;
94
+ }, 517), e;
95
+ });
96
+ let g = x(f);
96
97
  return p(() => {
97
- let t = x(k);
98
- m(v, [t.e("content")]), m(S, [t.e("title")]), _(C, y(e.value.title));
99
- }), h(v, null, 1), s(() => !l.simple, () => {
100
- let t = E(), n = b(t);
98
+ let t = S(j);
99
+ m(d, [t.e("content")]), m(f, [t.e("title")]), v(g, b(e.value.title));
100
+ }), h(d, null, 1), c(() => !u.simple && !u.arrow || u.arrow && e.value.description, () => {
101
+ let t = O(), n = x(t);
101
102
  return p(() => {
102
- m(t, [x(k).e("description")]), _(n, y(e.value.description));
103
+ m(t, [S(j).e("description")]), v(n, b(e.value.description));
103
104
  }), t;
104
- }), h(u, null, 2), s(() => o.value < l.items.length - 1 && l.simple, () => {
105
- let e = w();
106
- return p(() => m(e, [x(k).e("arrow")])), h(e, null, 0), a(x(t)), e;
107
- }), u.$evtclick = c(() => N(o.value)), u;
108
- }, (e, t) => t, 9), P;
105
+ }), h(s, null, 2), c(() => t.value < u.items.length - 1 && u.simple, () => {
106
+ let e = E();
107
+ return p(() => m(e, [S(j).e("arrow")])), h(e, null, 0), o(S(n)), e;
108
+ }), s.$evtclick = l(() => R(t.value)), s;
109
+ }, (e, t) => t, 9), g(z, N, null, "stepsRef"), z;
109
110
  }
110
111
  });
111
112
  //#endregion
112
- export { k as default };
113
+ export { j as default };
@@ -6,7 +6,7 @@ export interface StepsProps {
6
6
  /** 是否垂直布局 */
7
7
  vertical?: boolean;
8
8
  /** 步骤项大小 */
9
- size?: "small" | "medium";
9
+ size?: "mini" | "small" | "medium" | "large" | "larger";
10
10
  /** 节点标题布局方向 */
11
11
  alignCenter?: boolean;
12
12
  /** 当前步骤项状态 */
@@ -17,6 +17,8 @@ export interface StepsProps {
17
17
  dot?: boolean;
18
18
  /** 是否显示为简单步骤 */
19
19
  simple?: boolean;
20
+ /** 是否使用箭头形步骤条 */
21
+ arrow?: boolean;
20
22
  }
21
23
  export interface StepsItemProps {
22
24
  /** 标题 */
@@ -1,10 +1,41 @@
1
- import "vue";
1
+ import { onMounted as e, onUnmounted as t, ref as n, watch as r } from "vue";
2
2
  //#region ../hooks/src/use-element-size.ts
3
- var e = /* @__PURE__ */ new WeakMap();
4
- new ResizeObserver((t) => {
5
- for (let n of t) {
6
- let t = e.get(n.target);
7
- t && (t.width.value = n.contentRect.width, t.height.value = n.contentRect.height);
3
+ var i = /* @__PURE__ */ new WeakMap(), a = /* @__PURE__ */ new Set(), o = new ResizeObserver((e) => {
4
+ for (let t of e) {
5
+ let e = i.get(t.target);
6
+ e && (e.width.value = t.contentRect.width, e.height.value = t.contentRect.height);
8
7
  }
9
- });
8
+ }), s = (s) => {
9
+ let c = n(0), l = n(0), u = () => {
10
+ c.value = window.innerWidth, l.value = window.innerHeight;
11
+ }, d = (e) => {
12
+ i.set(e, {
13
+ width: c,
14
+ height: l
15
+ }), o.observe(e);
16
+ let t = e.getBoundingClientRect();
17
+ c.value = t.width, l.value = t.height;
18
+ }, f = (e) => {
19
+ o.unobserve(e), i.delete(e);
20
+ }, p = () => {
21
+ c.value = window.innerWidth, l.value = window.innerHeight, window.addEventListener("resize", u), a.add(u);
22
+ }, m = () => {
23
+ window.removeEventListener("resize", u), a.delete(u);
24
+ }, h = (e) => {
25
+ e && (e === window ? p() : e instanceof Element && d(e));
26
+ }, g = (e) => {
27
+ e && (e === window ? m() : e instanceof Element && f(e));
28
+ };
29
+ return e(() => {
30
+ h(s === window ? window : s.value);
31
+ }), t(() => {
32
+ g(s === window ? window : s.value);
33
+ }), s !== window && r(() => s.value, (e, t) => {
34
+ t && g(t), e && h(e);
35
+ }, { immediate: !1 }), {
36
+ width: c,
37
+ height: l
38
+ };
39
+ };
10
40
  //#endregion
41
+ export { s as useElementSize };
@@ -21,7 +21,7 @@
21
21
  }
22
22
  @include when(range) {
23
23
  &:focus-within {
24
- @include be(datetime-picker, input) {
24
+ @include be(datetime-picker, inner) {
25
25
  &:focus {
26
26
  background-color: getCssVar("color", "fill-2");
27
27
  }
@@ -109,13 +109,13 @@
109
109
  padding: 4px 8px 4px 4px;
110
110
  }
111
111
  }
112
- @include be(datetime-picker, input) {
112
+ @include be(datetime-picker, inner) {
113
113
  font-size: getCssVar("font-size", $size);
114
114
  }
115
115
  }
116
116
  }
117
117
 
118
- @include e(input) {
118
+ @include e(inner) {
119
119
  height: 100%;
120
120
  width: 100%;
121
121
  padding: 0 8px 0 8px;
@@ -78,6 +78,12 @@
78
78
  justify-content: flex-start;
79
79
  }
80
80
 
81
+ @include e(extra) {
82
+ margin-top: 4px;
83
+ color: getCssVar("color", "text-3");
84
+ font-size: getCssVar("font-size", "mini");
85
+ }
86
+
81
87
  @include e(error-msg) {
82
88
  height: 20px;
83
89
  font-size: getCssVar("font-size", "small");
@@ -53,14 +53,14 @@
53
53
  border-color: getCssVar("color", "danger-6");
54
54
  }
55
55
  @include when(filled) {
56
- background-color: getCssVar("color", "error-1");
57
- border-color: getCssVar("color", "error-1");
56
+ background-color: getCssVar("color", "danger-1");
57
+ border-color: getCssVar("color", "danger-1");
58
58
  &:hover {
59
- background-color: getCssVar("color", "error-2");
59
+ background-color: getCssVar("color", "danger-2");
60
60
  }
61
61
  &:focus-within {
62
62
  background-color: getCssVar("color", "bg-2");
63
- border-color: getCssVar("color", "error-5");
63
+ border-color: getCssVar("color", "danger-5");
64
64
  }
65
65
  }
66
66
  }
@@ -1,10 +1,46 @@
1
1
  @use "../mixins/function.scss" as *;
2
2
  @use "../mixins/mixins.scss" as *;
3
+ @use "../common/var.scss" as *;
3
4
 
4
5
  @include b(steps) {
5
6
  display: flex;
6
7
  width: 100%;
7
8
 
9
+ @each $size in $size-list {
10
+ @include m(#{$size}) {
11
+ @include this-is(simple) {
12
+ min-height: getCssVar("size", $size);
13
+ }
14
+ @include this-is(arrow) {
15
+ border-radius: getCssVar("radius", $size);
16
+ @include child-be(steps, step) {
17
+ min-height: getCssVar("size", $size);
18
+ }
19
+ }
20
+ @include be(steps, icon) {
21
+ height: calc(getCssVar("size", $size) - 12px);
22
+ width: calc(getCssVar("size", $size) - 12px);
23
+ font-size: getCssVar("font-size", $size);
24
+ }
25
+ @include be(steps, title) {
26
+ font-size: getCssVar("font-size", $size);
27
+ line-height: getCssVar("line-height", $size);
28
+ }
29
+ @include be(steps, description) {
30
+ font-size: getCssVar("font-size", $size);
31
+ line-height: getCssVar("line-height", $size);
32
+ }
33
+ @include be(steps, line) {
34
+ top: calc((getCssVar("size", $size) - 12px) / 2);
35
+ }
36
+ @include this-is(vertical) {
37
+ @include be(steps, line) {
38
+ left: calc((getCssVar("size", $size) - 12px) / 2);
39
+ }
40
+ }
41
+ }
42
+ }
43
+
8
44
  @include when(vertical) {
9
45
  height: 100%;
10
46
  flex-direction: column;
@@ -19,7 +55,6 @@
19
55
  width: 2px;
20
56
  top: 0;
21
57
  bottom: 0;
22
- left: 11px;
23
58
  height: 100%;
24
59
  }
25
60
  @include be(steps, content) {
@@ -40,8 +75,8 @@
40
75
  }
41
76
 
42
77
  @include when(simple) {
43
- padding: 12px 8%;
44
- background-color: getCssVar("color", "fill-3");
78
+ padding: 4px 8%;
79
+ background-color: getCssVar("color", "fill-2");
45
80
  flex-direction: row;
46
81
  border-radius: getCssVar("radius", "medium");
47
82
  @include be(steps, step) {
@@ -136,38 +171,6 @@
136
171
  }
137
172
  }
138
173
 
139
- @include m(small) {
140
- @include be(steps, icon) {
141
- width: 20px;
142
- height: 20px;
143
- font-size: 12px;
144
- }
145
- @include be(steps, title) {
146
- font-size: getCssVar("font-size", "medium");
147
- line-height: getCssVar("line-height", "large");
148
- }
149
- @include be(steps, description) {
150
- font-size: getCssVar("font-size", "small");
151
- line-height: getCssVar("line-height", "small");
152
- }
153
- }
154
-
155
- @include m(medium) {
156
- @include be(steps, icon) {
157
- width: 24px;
158
- height: 24px;
159
- font-size: 14px;
160
- }
161
- @include be(steps, title) {
162
- font-size: getCssVar("font-size", "large");
163
- line-height: getCssVar("line-height", "larger");
164
- }
165
- @include be(steps, description) {
166
- font-size: getCssVar("font-size", "medium");
167
- line-height: getCssVar("line-height", "medium");
168
- }
169
- }
170
-
171
174
  @include e(step) {
172
175
  @include when(changeable) {
173
176
  cursor: pointer;
@@ -197,7 +200,6 @@
197
200
  @include e(line) {
198
201
  position: absolute;
199
202
  height: 2px;
200
- top: 11px;
201
203
  left: 0;
202
204
  right: 0;
203
205
  }
@@ -234,4 +236,124 @@
234
236
  line-height: getCssVar("line-height", "medium");
235
237
  color: getCssVar("color", "text-3");
236
238
  }
239
+
240
+ @include when(arrow) {
241
+ flex-wrap: nowrap;
242
+ align-items: stretch;
243
+ overflow: hidden;
244
+
245
+ @include be(steps, step) {
246
+ position: relative;
247
+ flex: 1 1 0;
248
+ min-width: 0;
249
+ display: flex;
250
+ align-items: center;
251
+ padding: 4px 16px;
252
+ color: #fff;
253
+ overflow: visible;
254
+
255
+ &:not(:first-child) {
256
+ padding-left: var(--s-steps-height);
257
+ }
258
+
259
+ &:not(:last-child) {
260
+ margin-right: 4px;
261
+ }
262
+
263
+ &:not(:first-child)::before {
264
+ content: "";
265
+ position: absolute;
266
+ top: 0;
267
+ left: 0;
268
+ z-index: 1;
269
+ width: 0;
270
+ height: 0;
271
+
272
+ border-top: calc(var(--s-steps-height) / 2) solid transparent;
273
+ border-bottom: calc(var(--s-steps-height) / 2) solid transparent;
274
+ border-left: calc(var(--s-steps-height) / 2) solid getCssVar("color", "bg-2");
275
+ }
276
+
277
+ &:not(:last-child)::after {
278
+ content: "";
279
+ position: absolute;
280
+ top: 0;
281
+ z-index: 2;
282
+ width: 0;
283
+ height: 0;
284
+ right: calc(var(--s-steps-height) / 2 * -1);
285
+ border-top: calc(var(--s-steps-height) / 2) solid transparent;
286
+ border-bottom: calc(var(--s-steps-height) / 2) solid transparent;
287
+ border-left: calc(var(--s-steps-height) / 2) solid getCssVar("color", "fill-2");
288
+ }
289
+
290
+ @include when(changeable) {
291
+ cursor: pointer;
292
+ }
293
+
294
+ @include this-bm(steps, wait) {
295
+ background-color: getCssVar("color", "fill-2");
296
+
297
+ &:not(:last-child)::after {
298
+ border-left-color: getCssVar("color", "fill-2");
299
+ }
300
+
301
+ @include be(steps, title) {
302
+ color: getCssVar("color", "text-1");
303
+ }
304
+ @include be(steps, description) {
305
+ color: getCssVar("color", "text-3");
306
+ opacity: 1;
307
+ }
308
+ }
309
+
310
+ @include this-bm(steps, process) {
311
+ background-color: getCssVar("color", "primary-6");
312
+
313
+ &:not(:last-child)::after {
314
+ border-left-color: getCssVar("color", "primary-6");
315
+ }
316
+ }
317
+
318
+ @include this-bm(steps, done) {
319
+ background-color: getCssVar("color", "success-6");
320
+
321
+ &:not(:last-child)::after {
322
+ border-left-color: getCssVar("color", "success-6");
323
+ }
324
+ }
325
+
326
+ @include this-bm(steps, error) {
327
+ background-color: getCssVar("color", "danger-6");
328
+
329
+ &:not(:last-child)::after {
330
+ border-left-color: getCssVar("color", "danger-6");
331
+ }
332
+ }
333
+ }
334
+
335
+ @include be(steps, content) {
336
+ margin-top: 0;
337
+ overflow: hidden;
338
+ display: flex;
339
+ flex-direction: column;
340
+ gap: 4px;
341
+ }
342
+
343
+ @include be(steps, title) {
344
+ color: inherit;
345
+ font-weight: 500;
346
+ white-space: nowrap;
347
+ overflow: hidden;
348
+ text-overflow: ellipsis;
349
+ }
350
+
351
+ @include be(steps, description) {
352
+ color: inherit;
353
+ opacity: 0.85;
354
+ white-space: nowrap;
355
+ overflow: hidden;
356
+ text-overflow: ellipsis;
357
+ }
358
+ }
237
359
  }
@@ -29,10 +29,10 @@
29
29
  }
30
30
  @include when(disabled) {
31
31
  cursor: not-allowed;
32
- @include be(input, inner) {
32
+ @include be(textarea, inner) {
33
33
  color: getCssVar("color", "text-3");
34
34
  }
35
- @include this-be(input, wrapper) {
35
+ @include this-be(textarea, wrapper) {
36
36
  background-color: getCssVar("color", "bg-2");
37
37
  border: 1px solid getCssVar("color", "fill-3");
38
38
  &:hover {
@@ -58,14 +58,14 @@
58
58
  border-color: getCssVar("color", "danger-6");
59
59
  }
60
60
  @include when(filled) {
61
- background-color: getCssVar("color", "error-1");
62
- border-color: getCssVar("color", "error-1");
61
+ background-color: getCssVar("color", "danger-1");
62
+ border-color: getCssVar("color", "danger-1");
63
63
  &:hover {
64
- background-color: getCssVar("color", "error-2");
64
+ background-color: getCssVar("color", "danger-2");
65
65
  }
66
66
  &:focus-within {
67
67
  background-color: getCssVar("color", "bg-2");
68
- border-color: getCssVar("color", "error-5");
68
+ border-color: getCssVar("color", "danger-5");
69
69
  }
70
70
  }
71
71
  }
@@ -78,7 +78,7 @@
78
78
  }
79
79
  &:focus-within {
80
80
  background-color: getCssVar("color", "bg-2");
81
- border-color: getCssVar("color", "primary-6");
81
+ border-color: getCssVar("color", "primary-5");
82
82
  }
83
83
  }
84
84
  }
@@ -878,6 +878,10 @@
878
878
  "s-form-item/requiredAlign": {
879
879
  "description": "必填标识对齐方式"
880
880
  },
881
+ "s-form-item/extra": {
882
+ "description": "表单项额外内容",
883
+ "type": "string"
884
+ },
881
885
  "s-galleria/modelValue": {
882
886
  "description": "当前选中项索引(v-model)",
883
887
  "type": "number"
@@ -2286,6 +2290,10 @@
2286
2290
  "description": "是否显示为简单步骤",
2287
2291
  "type": "boolean"
2288
2292
  },
2293
+ "s-steps/arrow": {
2294
+ "description": "是否使用箭头形步骤条",
2295
+ "type": "boolean"
2296
+ },
2289
2297
  "s-steps-item/title": {
2290
2298
  "description": "标题",
2291
2299
  "type": "string"
@@ -381,7 +381,8 @@
381
381
  "labelPosition",
382
382
  "labelAlign",
383
383
  "showRequired",
384
- "requiredAlign"
384
+ "requiredAlign",
385
+ "extra"
385
386
  ]
386
387
  },
387
388
  "s-galleria": {
@@ -948,7 +949,8 @@
948
949
  "status",
949
950
  "changeable",
950
951
  "dot",
951
- "simple"
952
+ "simple",
953
+ "arrow"
952
954
  ]
953
955
  },
954
956
  "s-steps-item": {
@@ -2,7 +2,7 @@
2
2
  "$schema": "https://raw.githubusercontent.com/JetBrains/web-types/master/schema/web-types.json",
3
3
  "framework": "vue",
4
4
  "name": "savor-ui",
5
- "version": "0.27.0",
5
+ "version": "0.29.0",
6
6
  "contributions": {
7
7
  "html": {
8
8
  "types-syntax": "typescript",
@@ -2340,10 +2340,31 @@
2340
2340
  "type": "left | right",
2341
2341
  "kind": "expression"
2342
2342
  }
2343
+ },
2344
+ {
2345
+ "name": "extra",
2346
+ "description": "表单项额外内容",
2347
+ "value": {
2348
+ "type": "string",
2349
+ "kind": "expression"
2350
+ }
2343
2351
  }
2344
2352
  ],
2345
2353
  "events": [],
2346
- "slots": []
2354
+ "slots": [
2355
+ {
2356
+ "name": "default",
2357
+ "description": "内容"
2358
+ },
2359
+ {
2360
+ "name": "label",
2361
+ "description": "标签"
2362
+ },
2363
+ {
2364
+ "name": "extra",
2365
+ "description": "额外内容"
2366
+ }
2367
+ ]
2347
2368
  },
2348
2369
  {
2349
2370
  "name": "s-galleria",
@@ -5868,7 +5889,7 @@
5868
5889
  "name": "size",
5869
5890
  "description": "步骤项大小",
5870
5891
  "value": {
5871
- "type": "small | medium",
5892
+ "type": "mini | small | medium | large | larger",
5872
5893
  "kind": "expression"
5873
5894
  }
5874
5895
  },
@@ -5911,6 +5932,14 @@
5911
5932
  "type": "boolean",
5912
5933
  "kind": "expression"
5913
5934
  }
5935
+ },
5936
+ {
5937
+ "name": "arrow",
5938
+ "description": "是否使用箭头形步骤条",
5939
+ "value": {
5940
+ "type": "boolean",
5941
+ "kind": "expression"
5942
+ }
5914
5943
  }
5915
5944
  ],
5916
5945
  "events": [
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "savor-ui",
3
- "version": "0.28.0",
3
+ "version": "0.30.0",
4
4
  "description": "A Vue3 Components Library",
5
5
  "keywords": [
6
6
  "component library",