@usefragments/ui 1.4.0 → 1.5.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.
@@ -3843,7 +3843,7 @@
3843
3843
  ._popup_1pyvn_6[data-side=top][data-starting-style], ._popup_1pyvn_6[data-side=top][data-ending-style] {
3844
3844
  transform: none;
3845
3845
  }
3846
- }._root_npjcd_1 {
3846
+ }._root_le29r_1 {
3847
3847
  display: flex;
3848
3848
  flex-direction: column;
3849
3849
  gap: var(--fui-space-1, 0.5rem);
@@ -3851,26 +3851,26 @@
3851
3851
  font-family: var(--fui-font-sans, "Inter Variable", Inter, -apple-system, BlinkMacSystemFont, "Segoe UI", system-ui, sans-serif);
3852
3852
  }
3853
3853
 
3854
- ._header_npjcd_9 {
3854
+ ._header_le29r_9 {
3855
3855
  display: flex;
3856
3856
  align-items: center;
3857
3857
  justify-content: space-between;
3858
3858
  gap: var(--fui-space-2, 1rem);
3859
3859
  }
3860
3860
 
3861
- ._label_npjcd_16 {
3861
+ ._label_le29r_16 {
3862
3862
  font-size: var(--fui-font-size-sm, 1rem);
3863
3863
  font-weight: var(--fui-font-weight-medium, 500);
3864
3864
  color: var(--fui-text-primary, #212121);
3865
3865
  }
3866
3866
 
3867
- ._value_npjcd_22 {
3867
+ ._value_le29r_22 {
3868
3868
  font-size: var(--fui-font-size-sm, 1rem);
3869
3869
  color: var(--fui-text-secondary, rgb(84.468434358, 84.468434358, 84.468434358));
3870
3870
  font-variant-numeric: tabular-nums;
3871
3871
  }
3872
3872
 
3873
- ._track_npjcd_28 {
3873
+ ._track_le29r_28 {
3874
3874
  position: relative;
3875
3875
  width: 100%;
3876
3876
  overflow: hidden;
@@ -3878,43 +3878,47 @@
3878
3878
  border-radius: var(--fui-radius-full, 9999px);
3879
3879
  }
3880
3880
 
3881
- ._trackSm_npjcd_36 {
3881
+ ._trackSm_le29r_36 {
3882
3882
  height: calc(var(--fui-space-1, 0.5rem) / 2);
3883
3883
  }
3884
3884
 
3885
- ._trackMd_npjcd_40 {
3885
+ ._trackMd_le29r_40 {
3886
3886
  height: var(--fui-space-1, 0.5rem);
3887
3887
  }
3888
3888
 
3889
- ._trackLg_npjcd_44 {
3889
+ ._trackLg_le29r_44 {
3890
3890
  height: var(--fui-space-2, 1rem);
3891
3891
  }
3892
3892
 
3893
- ._indicator_npjcd_48 {
3893
+ ._indicator_le29r_48 {
3894
3894
  height: 100%;
3895
3895
  background-color: var(--fui-color-accent, #006b57);
3896
3896
  border-radius: var(--fui-radius-full, 9999px);
3897
3897
  transition: width var(--fui-transition-normal, 200ms cubic-bezier(0.4, 0, 0.2, 1));
3898
3898
  }
3899
3899
 
3900
- ._indicatorSuccess_npjcd_55 {
3900
+ ._indicatorNeutral_le29r_55 {
3901
+ background-color: var(--fui-text-tertiary, rgb(86.4227350852, 86.4227350852, 86.4227350852));
3902
+ }
3903
+
3904
+ ._indicatorSuccess_le29r_59 {
3901
3905
  background-color: var(--fui-color-success-text, rgb(29.9064810064, 108.5606699289, 89.7163569497));
3902
3906
  }
3903
3907
 
3904
- ._indicatorWarning_npjcd_59 {
3908
+ ._indicatorWarning_le29r_63 {
3905
3909
  background-color: var(--fui-color-warning-text, hsl(41.194706405, 139.9133245857%, 21.9712967806%));
3906
3910
  }
3907
3911
 
3908
- ._indicatorDanger_npjcd_63 {
3912
+ ._indicatorDanger_le29r_67 {
3909
3913
  background-color: var(--fui-color-danger-text, rgb(162.7774064935, 63.3790672702, 56.4827894566));
3910
3914
  }
3911
3915
 
3912
- ._indicatorIndeterminate_npjcd_67 {
3916
+ ._indicatorIndeterminate_le29r_71 {
3913
3917
  width: 50% !important;
3914
- animation: _indeterminate_npjcd_1 1.5s ease-in-out infinite;
3918
+ animation: _indeterminate_le29r_1 1.5s ease-in-out infinite;
3915
3919
  }
3916
3920
 
3917
- @keyframes _indeterminate_npjcd_1 {
3921
+ @keyframes _indeterminate_le29r_1 {
3918
3922
  0% {
3919
3923
  transform: translateX(-100%);
3920
3924
  }
@@ -3925,50 +3929,50 @@
3925
3929
  transform: translateX(-100%);
3926
3930
  }
3927
3931
  }
3928
- ._root_npjcd_1[data-complete] ._indicator_npjcd_48 {
3932
+ ._root_le29r_1[data-complete] ._indicator_le29r_48:not(._indicatorNeutral_le29r_55) {
3929
3933
  background-color: var(--fui-color-success-text, rgb(29.9064810064, 108.5606699289, 89.7163569497));
3930
3934
  }
3931
3935
 
3932
- ._circular_npjcd_87 {
3936
+ ._circular_le29r_91 {
3933
3937
  position: relative;
3934
3938
  display: inline-flex;
3935
3939
  align-items: center;
3936
3940
  justify-content: center;
3937
3941
  }
3938
3942
 
3939
- ._circularSvg_npjcd_94 {
3943
+ ._circularSvg_le29r_98 {
3940
3944
  transform: rotate(-90deg);
3941
3945
  }
3942
3946
 
3943
- ._circularTrack_npjcd_98 {
3947
+ ._circularTrack_le29r_102 {
3944
3948
  stroke: var(--fui-bg-tertiary, #f4f4f4);
3945
3949
  fill: none;
3946
3950
  }
3947
3951
 
3948
- ._circularIndicator_npjcd_103 {
3952
+ ._circularIndicator_le29r_107 {
3949
3953
  stroke: var(--fui-color-accent, #006b57);
3950
3954
  fill: none;
3951
3955
  stroke-linecap: round;
3952
3956
  transition: stroke-dashoffset var(--fui-transition-normal, 200ms cubic-bezier(0.4, 0, 0.2, 1));
3953
3957
  }
3954
3958
 
3955
- ._circularIndicatorSuccess_npjcd_110 {
3959
+ ._circularIndicatorSuccess_le29r_114 {
3956
3960
  stroke: var(--fui-color-success-text, rgb(29.9064810064, 108.5606699289, 89.7163569497));
3957
3961
  }
3958
3962
 
3959
- ._circularIndicatorWarning_npjcd_114 {
3963
+ ._circularIndicatorWarning_le29r_118 {
3960
3964
  stroke: var(--fui-color-warning-text, hsl(41.194706405, 139.9133245857%, 21.9712967806%));
3961
3965
  }
3962
3966
 
3963
- ._circularIndicatorDanger_npjcd_118 {
3967
+ ._circularIndicatorDanger_le29r_122 {
3964
3968
  stroke: var(--fui-color-danger-text, rgb(162.7774064935, 63.3790672702, 56.4827894566));
3965
3969
  }
3966
3970
 
3967
- ._circularIndicatorIndeterminate_npjcd_122 {
3968
- animation: _circularIndeterminate_npjcd_1 1.5s ease-in-out infinite;
3971
+ ._circularIndicatorIndeterminate_le29r_126 {
3972
+ animation: _circularIndeterminate_le29r_1 1.5s ease-in-out infinite;
3969
3973
  }
3970
3974
 
3971
- @keyframes _circularIndeterminate_npjcd_1 {
3975
+ @keyframes _circularIndeterminate_le29r_1 {
3972
3976
  0% {
3973
3977
  stroke-dashoffset: 280;
3974
3978
  transform: rotate(0deg);
@@ -3981,7 +3985,7 @@
3981
3985
  transform: rotate(360deg);
3982
3986
  }
3983
3987
  }
3984
- ._circularValue_npjcd_139 {
3988
+ ._circularValue_le29r_143 {
3985
3989
  position: absolute;
3986
3990
  font-size: var(--fui-font-size-sm, 1rem);
3987
3991
  font-weight: var(--fui-font-weight-medium, 500);
@@ -3989,24 +3993,24 @@
3989
3993
  font-variant-numeric: tabular-nums;
3990
3994
  }
3991
3995
 
3992
- ._circularSm_npjcd_147 {
3996
+ ._circularSm_le29r_151 {
3993
3997
  width: var(--fui-space-4, 2rem);
3994
3998
  height: var(--fui-space-4, 2rem);
3995
3999
  }
3996
- ._circularSm_npjcd_147 ._circularValue_npjcd_139 {
4000
+ ._circularSm_le29r_151 ._circularValue_le29r_143 {
3997
4001
  font-size: var(--fui-font-size-xs, 0.857rem);
3998
4002
  }
3999
4003
 
4000
- ._circularMd_npjcd_155 {
4004
+ ._circularMd_le29r_159 {
4001
4005
  width: var(--fui-space-6, 3rem);
4002
4006
  height: var(--fui-space-6, 3rem);
4003
4007
  }
4004
4008
 
4005
- ._circularLg_npjcd_160 {
4009
+ ._circularLg_le29r_164 {
4006
4010
  width: var(--fui-space-8, 4rem);
4007
4011
  height: var(--fui-space-8, 4rem);
4008
4012
  }
4009
- ._circularLg_npjcd_160 ._circularValue_npjcd_139 {
4013
+ ._circularLg_le29r_164 ._circularValue_le29r_143 {
4010
4014
  font-size: var(--fui-font-size-base, 1rem);
4011
4015
  }._wrapper_11gr0_1 {
4012
4016
  display: inline-flex;
@@ -92,9 +92,9 @@ function CardHeader({ children, divided, className, ...htmlProps }) {
92
92
  const classes = [Card_module.default.header, divided && Card_module.default.headerDivided, className].filter(Boolean).join(" ");
93
93
  return /* @__PURE__ */ jsxRuntime.jsx("div", { ...htmlProps, className: classes, children });
94
94
  }
95
- function CardTitle({ children, className, ...htmlProps }) {
95
+ function CardTitle({ children, as: Component = "h3", className, ...htmlProps }) {
96
96
  const classes = [Card_module.default.title, className].filter(Boolean).join(" ");
97
- return /* @__PURE__ */ jsxRuntime.jsx("h3", { ...htmlProps, className: classes, children });
97
+ return /* @__PURE__ */ jsxRuntime.jsx(Component, { ...htmlProps, className: classes, children });
98
98
  }
99
99
  function CardDescription({ children, className, ...htmlProps }) {
100
100
  const classes = [Card_module.default.description, className].filter(Boolean).join(" ");
@@ -32,6 +32,9 @@ export interface CardHeaderProps extends React.HTMLAttributes<HTMLDivElement> {
32
32
  }
33
33
  export interface CardTitleProps extends React.HTMLAttributes<HTMLHeadingElement> {
34
34
  children: React.ReactNode;
35
+ /** Semantic heading level.
36
+ * @default "h3" */
37
+ as?: "h2" | "h3" | "h4" | "h5" | "h6";
35
38
  }
36
39
  export interface CardDescriptionProps extends React.HTMLAttributes<HTMLParagraphElement> {
37
40
  children: React.ReactNode;
@@ -47,7 +50,7 @@ export interface CardFooterProps extends React.HTMLAttributes<HTMLDivElement> {
47
50
  }
48
51
  declare function CardRoot({ children, variant: variantProp, padding, as: Component, className, style, ...htmlProps }: CardProps): import("react/jsx-runtime").JSX.Element;
49
52
  declare function CardHeader({ children, divided, className, ...htmlProps }: CardHeaderProps): import("react/jsx-runtime").JSX.Element;
50
- declare function CardTitle({ children, className, ...htmlProps }: CardTitleProps): import("react/jsx-runtime").JSX.Element;
53
+ declare function CardTitle({ children, as: Component, className, ...htmlProps }: CardTitleProps): import("react/jsx-runtime").JSX.Element;
51
54
  declare function CardDescription({ children, className, ...htmlProps }: CardDescriptionProps): import("react/jsx-runtime").JSX.Element;
52
55
  declare function CardBody({ children, padding, className, ...htmlProps }: CardBodyProps): import("react/jsx-runtime").JSX.Element;
53
56
  declare function CardFooter({ children, className, ...htmlProps }: CardFooterProps): import("react/jsx-runtime").JSX.Element;
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/Card/index.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAO/B;;;GAGG;AACH,MAAM,WAAW,SAAU,SAAQ,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,WAAW,CAAC,EAAE,UAAU,CAAC;IACpF,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B;;;;;;;;;gEAS4D;IAC5D,OAAO,CAAC,EAAE,SAAS,GAAG,UAAU,GAAG,SAAS,GAAG,UAAU,GAAG,MAAM,GAAG,OAAO,CAAC;IAC7E;uBACmB;IACnB,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;IACtC;4BACwB;IACxB,EAAE,CAAC,EAAE,SAAS,GAAG,KAAK,GAAG,SAAS,CAAC;CACpC;AAED,MAAM,WAAW,eAAgB,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IAC3E,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B;;8DAE0D;IAC1D,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,MAAM,WAAW,cAAe,SAAQ,KAAK,CAAC,cAAc,CAAC,kBAAkB,CAAC;IAC9E,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B;AAED,MAAM,WAAW,oBAAqB,SAAQ,KAAK,CAAC,cAAc,CAAC,oBAAoB,CAAC;IACtF,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B;AAED,MAAM,WAAW,aAAc,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IACzE,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B;uDACmD;IACnD,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;CACvC;AAED,MAAM,WAAW,eAAgB,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IAC3E,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B;AAwCD,iBAAS,QAAQ,CAAC,EAChB,QAAQ,EACR,OAAO,EAAE,WAAuB,EAChC,OAAc,EACd,EAAE,EAAE,SAAqB,EACzB,SAAS,EACT,KAAK,EACL,GAAG,SAAS,EACb,EAAE,SAAS,2CA6DX;AAED,iBAAS,UAAU,CAAC,EAAE,QAAQ,EAAE,OAAO,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,eAAe,2CASlF;AAED,iBAAS,SAAS,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,cAAc,2CAOvE;AAED,iBAAS,eAAe,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,oBAAoB,2CAOnF;AAED,iBAAS,QAAQ,CAAC,EAAE,QAAQ,EAAE,OAAO,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,aAAa,2CAS9E;AAED,iBAAS,UAAU,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,eAAe,2CAOzE;AAMD,eAAO,MAAM,IAAI;;;;;;CAMf,CAAC;AAGH,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAE,SAAS,EAAE,eAAe,EAAE,QAAQ,EAAE,UAAU,EAAE,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/Card/index.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAO/B;;;GAGG;AACH,MAAM,WAAW,SAAU,SAAQ,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,WAAW,CAAC,EAAE,UAAU,CAAC;IACpF,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B;;;;;;;;;gEAS4D;IAC5D,OAAO,CAAC,EAAE,SAAS,GAAG,UAAU,GAAG,SAAS,GAAG,UAAU,GAAG,MAAM,GAAG,OAAO,CAAC;IAC7E;uBACmB;IACnB,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;IACtC;4BACwB;IACxB,EAAE,CAAC,EAAE,SAAS,GAAG,KAAK,GAAG,SAAS,CAAC;CACpC;AAED,MAAM,WAAW,eAAgB,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IAC3E,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B;;8DAE0D;IAC1D,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,MAAM,WAAW,cAAe,SAAQ,KAAK,CAAC,cAAc,CAAC,kBAAkB,CAAC;IAC9E,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B;uBACmB;IACnB,EAAE,CAAC,EAAE,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;CACvC;AAED,MAAM,WAAW,oBAAqB,SAAQ,KAAK,CAAC,cAAc,CAAC,oBAAoB,CAAC;IACtF,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B;AAED,MAAM,WAAW,aAAc,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IACzE,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B;uDACmD;IACnD,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;CACvC;AAED,MAAM,WAAW,eAAgB,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IAC3E,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;CAC3B;AAwCD,iBAAS,QAAQ,CAAC,EAChB,QAAQ,EACR,OAAO,EAAE,WAAuB,EAChC,OAAc,EACd,EAAE,EAAE,SAAqB,EACzB,SAAS,EACT,KAAK,EACL,GAAG,SAAS,EACb,EAAE,SAAS,2CA6DX;AAED,iBAAS,UAAU,CAAC,EAAE,QAAQ,EAAE,OAAO,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,eAAe,2CASlF;AAED,iBAAS,SAAS,CAAC,EAAE,QAAQ,EAAE,EAAE,EAAE,SAAgB,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,cAAc,2CAO7F;AAED,iBAAS,eAAe,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,oBAAoB,2CAOnF;AAED,iBAAS,QAAQ,CAAC,EAAE,QAAQ,EAAE,OAAO,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,aAAa,2CAS9E;AAED,iBAAS,UAAU,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,GAAG,SAAS,EAAE,EAAE,eAAe,2CAOzE;AAMD,eAAO,MAAM,IAAI;;;;;;CAMf,CAAC;AAGH,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAE,SAAS,EAAE,eAAe,EAAE,QAAQ,EAAE,UAAU,EAAE,CAAC"}
@@ -73,9 +73,9 @@ function CardHeader({ children, divided, className, ...htmlProps }) {
73
73
  const classes = [styles.header, divided && styles.headerDivided, className].filter(Boolean).join(" ");
74
74
  return /* @__PURE__ */ jsx("div", { ...htmlProps, className: classes, children });
75
75
  }
76
- function CardTitle({ children, className, ...htmlProps }) {
76
+ function CardTitle({ children, as: Component = "h3", className, ...htmlProps }) {
77
77
  const classes = [styles.title, className].filter(Boolean).join(" ");
78
- return /* @__PURE__ */ jsx("h3", { ...htmlProps, className: classes, children });
78
+ return /* @__PURE__ */ jsx(Component, { ...htmlProps, className: classes, children });
79
79
  }
80
80
  function CardDescription({ children, className, ...htmlProps }) {
81
81
  const classes = [styles.description, className].filter(Boolean).join(" ");
@@ -1,30 +1,31 @@
1
1
  "use strict";
2
2
  Object.defineProperties(exports, { __esModule: { value: true }, [Symbol.toStringTag]: { value: "Module" } });
3
- const root = "_root_npjcd_1";
4
- const header = "_header_npjcd_9";
5
- const label = "_label_npjcd_16";
6
- const value = "_value_npjcd_22";
7
- const track = "_track_npjcd_28";
8
- const trackSm = "_trackSm_npjcd_36";
9
- const trackMd = "_trackMd_npjcd_40";
10
- const trackLg = "_trackLg_npjcd_44";
11
- const indicator = "_indicator_npjcd_48";
12
- const indicatorSuccess = "_indicatorSuccess_npjcd_55";
13
- const indicatorWarning = "_indicatorWarning_npjcd_59";
14
- const indicatorDanger = "_indicatorDanger_npjcd_63";
15
- const indicatorIndeterminate = "_indicatorIndeterminate_npjcd_67";
16
- const circular = "_circular_npjcd_87";
17
- const circularSvg = "_circularSvg_npjcd_94";
18
- const circularTrack = "_circularTrack_npjcd_98";
19
- const circularIndicator = "_circularIndicator_npjcd_103";
20
- const circularIndicatorSuccess = "_circularIndicatorSuccess_npjcd_110";
21
- const circularIndicatorWarning = "_circularIndicatorWarning_npjcd_114";
22
- const circularIndicatorDanger = "_circularIndicatorDanger_npjcd_118";
23
- const circularIndicatorIndeterminate = "_circularIndicatorIndeterminate_npjcd_122";
24
- const circularValue = "_circularValue_npjcd_139";
25
- const circularSm = "_circularSm_npjcd_147";
26
- const circularMd = "_circularMd_npjcd_155";
27
- const circularLg = "_circularLg_npjcd_160";
3
+ const root = "_root_le29r_1";
4
+ const header = "_header_le29r_9";
5
+ const label = "_label_le29r_16";
6
+ const value = "_value_le29r_22";
7
+ const track = "_track_le29r_28";
8
+ const trackSm = "_trackSm_le29r_36";
9
+ const trackMd = "_trackMd_le29r_40";
10
+ const trackLg = "_trackLg_le29r_44";
11
+ const indicator = "_indicator_le29r_48";
12
+ const indicatorNeutral = "_indicatorNeutral_le29r_55";
13
+ const indicatorSuccess = "_indicatorSuccess_le29r_59";
14
+ const indicatorWarning = "_indicatorWarning_le29r_63";
15
+ const indicatorDanger = "_indicatorDanger_le29r_67";
16
+ const indicatorIndeterminate = "_indicatorIndeterminate_le29r_71";
17
+ const circular = "_circular_le29r_91";
18
+ const circularSvg = "_circularSvg_le29r_98";
19
+ const circularTrack = "_circularTrack_le29r_102";
20
+ const circularIndicator = "_circularIndicator_le29r_107";
21
+ const circularIndicatorSuccess = "_circularIndicatorSuccess_le29r_114";
22
+ const circularIndicatorWarning = "_circularIndicatorWarning_le29r_118";
23
+ const circularIndicatorDanger = "_circularIndicatorDanger_le29r_122";
24
+ const circularIndicatorIndeterminate = "_circularIndicatorIndeterminate_le29r_126";
25
+ const circularValue = "_circularValue_le29r_143";
26
+ const circularSm = "_circularSm_le29r_151";
27
+ const circularMd = "_circularMd_le29r_159";
28
+ const circularLg = "_circularLg_le29r_164";
28
29
  const styles = {
29
30
  root,
30
31
  header,
@@ -35,6 +36,7 @@ const styles = {
35
36
  trackMd,
36
37
  trackLg,
37
38
  indicator,
39
+ indicatorNeutral,
38
40
  indicatorSuccess,
39
41
  indicatorWarning,
40
42
  indicatorDanger,
@@ -69,6 +71,7 @@ exports.header = header;
69
71
  exports.indicator = indicator;
70
72
  exports.indicatorDanger = indicatorDanger;
71
73
  exports.indicatorIndeterminate = indicatorIndeterminate;
74
+ exports.indicatorNeutral = indicatorNeutral;
72
75
  exports.indicatorSuccess = indicatorSuccess;
73
76
  exports.indicatorWarning = indicatorWarning;
74
77
  exports.label = label;
@@ -1,28 +1,29 @@
1
- const root = "_root_npjcd_1";
2
- const header = "_header_npjcd_9";
3
- const label = "_label_npjcd_16";
4
- const value = "_value_npjcd_22";
5
- const track = "_track_npjcd_28";
6
- const trackSm = "_trackSm_npjcd_36";
7
- const trackMd = "_trackMd_npjcd_40";
8
- const trackLg = "_trackLg_npjcd_44";
9
- const indicator = "_indicator_npjcd_48";
10
- const indicatorSuccess = "_indicatorSuccess_npjcd_55";
11
- const indicatorWarning = "_indicatorWarning_npjcd_59";
12
- const indicatorDanger = "_indicatorDanger_npjcd_63";
13
- const indicatorIndeterminate = "_indicatorIndeterminate_npjcd_67";
14
- const circular = "_circular_npjcd_87";
15
- const circularSvg = "_circularSvg_npjcd_94";
16
- const circularTrack = "_circularTrack_npjcd_98";
17
- const circularIndicator = "_circularIndicator_npjcd_103";
18
- const circularIndicatorSuccess = "_circularIndicatorSuccess_npjcd_110";
19
- const circularIndicatorWarning = "_circularIndicatorWarning_npjcd_114";
20
- const circularIndicatorDanger = "_circularIndicatorDanger_npjcd_118";
21
- const circularIndicatorIndeterminate = "_circularIndicatorIndeterminate_npjcd_122";
22
- const circularValue = "_circularValue_npjcd_139";
23
- const circularSm = "_circularSm_npjcd_147";
24
- const circularMd = "_circularMd_npjcd_155";
25
- const circularLg = "_circularLg_npjcd_160";
1
+ const root = "_root_le29r_1";
2
+ const header = "_header_le29r_9";
3
+ const label = "_label_le29r_16";
4
+ const value = "_value_le29r_22";
5
+ const track = "_track_le29r_28";
6
+ const trackSm = "_trackSm_le29r_36";
7
+ const trackMd = "_trackMd_le29r_40";
8
+ const trackLg = "_trackLg_le29r_44";
9
+ const indicator = "_indicator_le29r_48";
10
+ const indicatorNeutral = "_indicatorNeutral_le29r_55";
11
+ const indicatorSuccess = "_indicatorSuccess_le29r_59";
12
+ const indicatorWarning = "_indicatorWarning_le29r_63";
13
+ const indicatorDanger = "_indicatorDanger_le29r_67";
14
+ const indicatorIndeterminate = "_indicatorIndeterminate_le29r_71";
15
+ const circular = "_circular_le29r_91";
16
+ const circularSvg = "_circularSvg_le29r_98";
17
+ const circularTrack = "_circularTrack_le29r_102";
18
+ const circularIndicator = "_circularIndicator_le29r_107";
19
+ const circularIndicatorSuccess = "_circularIndicatorSuccess_le29r_114";
20
+ const circularIndicatorWarning = "_circularIndicatorWarning_le29r_118";
21
+ const circularIndicatorDanger = "_circularIndicatorDanger_le29r_122";
22
+ const circularIndicatorIndeterminate = "_circularIndicatorIndeterminate_le29r_126";
23
+ const circularValue = "_circularValue_le29r_143";
24
+ const circularSm = "_circularSm_le29r_151";
25
+ const circularMd = "_circularMd_le29r_159";
26
+ const circularLg = "_circularLg_le29r_164";
26
27
  const styles = {
27
28
  root,
28
29
  header,
@@ -33,6 +34,7 @@ const styles = {
33
34
  trackMd,
34
35
  trackLg,
35
36
  indicator,
37
+ indicatorNeutral,
36
38
  indicatorSuccess,
37
39
  indicatorWarning,
38
40
  indicatorDanger,
@@ -68,6 +70,7 @@ export {
68
70
  indicator,
69
71
  indicatorDanger,
70
72
  indicatorIndeterminate,
73
+ indicatorNeutral,
71
74
  indicatorSuccess,
72
75
  indicatorWarning,
73
76
  label,
@@ -14,6 +14,7 @@ function ProgressRoot({
14
14
  showValue = false,
15
15
  formatValue,
16
16
  className,
17
+ role,
17
18
  "aria-label": ariaLabel,
18
19
  "aria-valuetext": ariaValueText,
19
20
  ...htmlProps
@@ -30,6 +31,7 @@ function ProgressRoot({
30
31
  ].filter(Boolean).join(" ");
31
32
  const indicatorClasses = [
32
33
  Progress_module.default.indicator,
34
+ variant === "neutral" && Progress_module.default.indicatorNeutral,
33
35
  variant === "success" && Progress_module.default.indicatorSuccess,
34
36
  variant === "warning" && Progress_module.default.indicatorWarning,
35
37
  variant === "danger" && Progress_module.default.indicatorDanger,
@@ -46,6 +48,7 @@ function ProgressRoot({
46
48
  min,
47
49
  max,
48
50
  className: rootClasses,
51
+ role: role ?? "progressbar",
49
52
  "aria-label": ariaLabel || (label ? void 0 : "Progress"),
50
53
  "aria-valuetext": effectiveValueText,
51
54
  "aria-busy": isIndeterminate,
@@ -1,5 +1,5 @@
1
- import * as React from 'react';
2
- export interface ProgressProps extends Omit<React.HTMLAttributes<HTMLDivElement>, 'defaultValue'> {
1
+ import * as React from "react";
2
+ export interface ProgressProps extends Omit<React.HTMLAttributes<HTMLDivElement>, "defaultValue"> {
3
3
  /** Current progress value (0-100). Null for indeterminate. */
4
4
  value?: number | null;
5
5
  /** Minimum value */
@@ -7,9 +7,9 @@ export interface ProgressProps extends Omit<React.HTMLAttributes<HTMLDivElement>
7
7
  /** Maximum value */
8
8
  max?: number;
9
9
  /** Size of the progress bar */
10
- size?: 'sm' | 'md' | 'lg';
10
+ size?: "sm" | "md" | "lg";
11
11
  /** Color variant */
12
- variant?: 'default' | 'success' | 'warning' | 'danger';
12
+ variant?: "default" | "neutral" | "success" | "warning" | "danger";
13
13
  /** Label text */
14
14
  label?: string;
15
15
  /** Show percentage value */
@@ -21,16 +21,16 @@ export interface CircularProgressProps extends React.HTMLAttributes<HTMLDivEleme
21
21
  /** Current progress value (0-100). Null for indeterminate. */
22
22
  value?: number | null;
23
23
  /** Size of the circular progress */
24
- size?: 'sm' | 'md' | 'lg';
24
+ size?: "sm" | "md" | "lg";
25
25
  /** Color variant */
26
- variant?: 'default' | 'success' | 'warning' | 'danger';
26
+ variant?: "default" | "success" | "warning" | "danger";
27
27
  /** Show percentage in center */
28
28
  showValue?: boolean;
29
29
  /** Stroke width */
30
30
  strokeWidth?: number;
31
31
  }
32
- declare function ProgressRoot({ value, min, max, size, variant, label, showValue, formatValue, className, 'aria-label': ariaLabel, 'aria-valuetext': ariaValueText, ...htmlProps }: ProgressProps): import("react/jsx-runtime").JSX.Element;
33
- declare function CircularProgressRoot({ value, size, variant, showValue, strokeWidth: customStrokeWidth, className, 'aria-label': ariaLabel, 'aria-labelledby': ariaLabelledBy, 'aria-valuetext': ariaValueText, ...htmlProps }: CircularProgressProps): import("react/jsx-runtime").JSX.Element;
32
+ declare function ProgressRoot({ value, min, max, size, variant, label, showValue, formatValue, className, role, "aria-label": ariaLabel, "aria-valuetext": ariaValueText, ...htmlProps }: ProgressProps): import("react/jsx-runtime").JSX.Element;
33
+ declare function CircularProgressRoot({ value, size, variant, showValue, strokeWidth: customStrokeWidth, className, "aria-label": ariaLabel, "aria-labelledby": ariaLabelledBy, "aria-valuetext": ariaValueText, ...htmlProps }: CircularProgressProps): import("react/jsx-runtime").JSX.Element;
34
34
  export declare const CircularProgress: typeof CircularProgressRoot;
35
35
  export declare const Progress: typeof ProgressRoot & {
36
36
  Root: typeof ProgressRoot;
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/Progress/index.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAQ/B,MAAM,WAAW,aAAc,SAAQ,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC,EAAE,cAAc,CAAC;IAC/F,8DAA8D;IAC9D,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,oBAAoB;IACpB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,oBAAoB;IACpB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,+BAA+B;IAC/B,IAAI,CAAC,EAAE,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;IAC1B,oBAAoB;IACpB,OAAO,CAAC,EAAE,SAAS,GAAG,SAAS,GAAG,SAAS,GAAG,QAAQ,CAAC;IACvD,iBAAiB;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,4BAA4B;IAC5B,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,6BAA6B;IAC7B,WAAW,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,MAAM,CAAC;CACzC;AAED,MAAM,WAAW,qBAAsB,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IACjF,8DAA8D;IAC9D,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,oCAAoC;IACpC,IAAI,CAAC,EAAE,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;IAC1B,oBAAoB;IACpB,OAAO,CAAC,EAAE,SAAS,GAAG,SAAS,GAAG,SAAS,GAAG,QAAQ,CAAC;IACvD,gCAAgC;IAChC,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,mBAAmB;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAMD,iBAAS,YAAY,CAAC,EACpB,KAAY,EACZ,GAAO,EACP,GAAS,EACT,IAAW,EACX,OAAmB,EACnB,KAAK,EACL,SAAiB,EACjB,WAAW,EACX,SAAS,EACT,YAAY,EAAE,SAAS,EACvB,gBAAgB,EAAE,aAAa,EAC/B,GAAG,SAAS,EACb,EAAE,aAAa,2CAqEf;AAYD,iBAAS,oBAAoB,CAAC,EAC5B,KAAY,EACZ,IAAW,EACX,OAAmB,EACnB,SAAiB,EACjB,WAAW,EAAE,iBAAiB,EAC9B,SAAS,EACT,YAAY,EAAE,SAAS,EACvB,iBAAiB,EAAE,cAAc,EACjC,gBAAgB,EAAE,aAAa,EAC/B,GAAG,SAAS,EACb,EAAE,qBAAqB,2CA+EvB;AAED,eAAO,MAAM,gBAAgB,6BAAuB,CAAC;AAErD,eAAO,MAAM,QAAQ;;;CAGnB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/Progress/index.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAQ/B,MAAM,WAAW,aAAc,SAAQ,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC,EAAE,cAAc,CAAC;IAC/F,8DAA8D;IAC9D,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,oBAAoB;IACpB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,oBAAoB;IACpB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,+BAA+B;IAC/B,IAAI,CAAC,EAAE,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;IAC1B,oBAAoB;IACpB,OAAO,CAAC,EAAE,SAAS,GAAG,SAAS,GAAG,SAAS,GAAG,SAAS,GAAG,QAAQ,CAAC;IACnE,iBAAiB;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,4BAA4B;IAC5B,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,6BAA6B;IAC7B,WAAW,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,MAAM,CAAC;CACzC;AAED,MAAM,WAAW,qBAAsB,SAAQ,KAAK,CAAC,cAAc,CAAC,cAAc,CAAC;IACjF,8DAA8D;IAC9D,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,oCAAoC;IACpC,IAAI,CAAC,EAAE,IAAI,GAAG,IAAI,GAAG,IAAI,CAAC;IAC1B,oBAAoB;IACpB,OAAO,CAAC,EAAE,SAAS,GAAG,SAAS,GAAG,SAAS,GAAG,QAAQ,CAAC;IACvD,gCAAgC;IAChC,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,mBAAmB;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAMD,iBAAS,YAAY,CAAC,EACpB,KAAY,EACZ,GAAO,EACP,GAAS,EACT,IAAW,EACX,OAAmB,EACnB,KAAK,EACL,SAAiB,EACjB,WAAW,EACX,SAAS,EACT,IAAI,EACJ,YAAY,EAAE,SAAS,EACvB,gBAAgB,EAAE,aAAa,EAC/B,GAAG,SAAS,EACb,EAAE,aAAa,2CA8Df;AAYD,iBAAS,oBAAoB,CAAC,EAC5B,KAAY,EACZ,IAAW,EACX,OAAmB,EACnB,SAAiB,EACjB,WAAW,EAAE,iBAAiB,EAC9B,SAAS,EACT,YAAY,EAAE,SAAS,EACvB,iBAAiB,EAAE,cAAc,EACjC,gBAAgB,EAAE,aAAa,EAC/B,GAAG,SAAS,EACb,EAAE,qBAAqB,2CA+EvB;AAED,eAAO,MAAM,gBAAgB,6BAAuB,CAAC;AAErD,eAAO,MAAM,QAAQ;;;CAGnB,CAAC"}
@@ -12,6 +12,7 @@ function ProgressRoot({
12
12
  showValue = false,
13
13
  formatValue,
14
14
  className,
15
+ role,
15
16
  "aria-label": ariaLabel,
16
17
  "aria-valuetext": ariaValueText,
17
18
  ...htmlProps
@@ -28,6 +29,7 @@ function ProgressRoot({
28
29
  ].filter(Boolean).join(" ");
29
30
  const indicatorClasses = [
30
31
  styles.indicator,
32
+ variant === "neutral" && styles.indicatorNeutral,
31
33
  variant === "success" && styles.indicatorSuccess,
32
34
  variant === "warning" && styles.indicatorWarning,
33
35
  variant === "danger" && styles.indicatorDanger,
@@ -44,6 +46,7 @@ function ProgressRoot({
44
46
  min,
45
47
  max,
46
48
  className: rootClasses,
49
+ role: role ?? "progressbar",
47
50
  "aria-label": ariaLabel || (label ? void 0 : "Progress"),
48
51
  "aria-valuetext": effectiveValueText,
49
52
  "aria-busy": isIndeterminate,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@usefragments/ui",
3
- "version": "1.4.0",
3
+ "version": "1.5.0",
4
4
  "license": "MIT",
5
5
  "description": "Customizable UI components built on Base UI headless primitives",
6
6
  "author": "Conan McNicholl",
@@ -241,7 +241,7 @@
241
241
  "vite": "^6.0.0",
242
242
  "vitest": "^2.1.8",
243
243
  "vitest-axe": "^0.1.0",
244
- "@usefragments/core": "1.7.1"
244
+ "@usefragments/core": "1.8.0"
245
245
  },
246
246
  "files": [
247
247
  "src",
@@ -77,6 +77,11 @@
77
77
  ]
78
78
  },
79
79
  "examples": [
80
+ {
81
+ "name": "Nested Heading",
82
+ "description": "Select the heading level required by the surrounding document outline",
83
+ "code": "<Card variant=\"panel\" padding=\"none\">\n <Card.Header divided>\n <Card.Title as=\"h4\">Nested panel</Card.Title>\n </Card.Header>\n <Card.Body padding=\"md\">Panel content</Card.Body>\n</Card>"
84
+ },
80
85
  {
81
86
  "name": "Default",
82
87
  "description": "Standard quiet card surface",
@@ -42,6 +42,9 @@ export interface CardHeaderProps extends React.HTMLAttributes<HTMLDivElement> {
42
42
 
43
43
  export interface CardTitleProps extends React.HTMLAttributes<HTMLHeadingElement> {
44
44
  children: React.ReactNode;
45
+ /** Semantic heading level.
46
+ * @default "h3" */
47
+ as?: "h2" | "h3" | "h4" | "h5" | "h6";
45
48
  }
46
49
 
47
50
  export interface CardDescriptionProps extends React.HTMLAttributes<HTMLParagraphElement> {
@@ -179,12 +182,12 @@ function CardHeader({ children, divided, className, ...htmlProps }: CardHeaderPr
179
182
  );
180
183
  }
181
184
 
182
- function CardTitle({ children, className, ...htmlProps }: CardTitleProps) {
185
+ function CardTitle({ children, as: Component = "h3", className, ...htmlProps }: CardTitleProps) {
183
186
  const classes = [styles.title, className].filter(Boolean).join(" ");
184
187
  return (
185
- <h3 {...htmlProps} className={classes}>
188
+ <Component {...htmlProps} className={classes}>
186
189
  {children}
187
- </h3>
190
+ </Component>
188
191
  );
189
192
  }
190
193
 
@@ -3,13 +3,7 @@
3
3
  "name": "Progress",
4
4
  "description": "Visual indicator of task completion or loading state. Available in linear and circular variants.",
5
5
  "category": "feedback",
6
- "tags": [
7
- "progress",
8
- "loading",
9
- "indicator",
10
- "percentage",
11
- "status"
12
- ],
6
+ "tags": ["progress", "loading", "indicator", "percentage", "status"],
13
7
  "status": "stable",
14
8
  "sourcePath": "src/components/Progress/index.tsx",
15
9
  "exportName": "Progress",
@@ -18,7 +12,8 @@
18
12
  "min: number (default: 0)",
19
13
  "max: number (default: 100)",
20
14
  "size: sm|md|lg (default: md)",
21
- "variant: default|success|warning|danger (default: default)",
15
+ "variant: default|neutral|success|warning|danger (default: default)",
16
+ "role: progressbar|meter (default: progressbar)",
22
17
  "label: string",
23
18
  "showValue: boolean (default: false)",
24
19
  "formatValue: function"
@@ -47,23 +42,14 @@
47
42
  "description": "Size of the progress bar",
48
43
  "default": "md",
49
44
  "required": false,
50
- "values": [
51
- "sm",
52
- "md",
53
- "lg"
54
- ]
45
+ "values": ["sm", "md", "lg"]
55
46
  },
56
47
  "variant": {
57
48
  "type": "enum",
58
49
  "description": "Color variant",
59
50
  "default": "default",
60
51
  "required": false,
61
- "values": [
62
- "default",
63
- "success",
64
- "warning",
65
- "danger"
66
- ]
52
+ "values": ["default", "neutral", "success", "warning", "danger"]
67
53
  },
68
54
  "label": {
69
55
  "type": "string",
@@ -99,10 +85,12 @@
99
85
  "Use indeterminate for unknown durations",
100
86
  "Include a label for context when the purpose isnt obvious",
101
87
  "Use appropriate color variants for success/warning/danger states",
88
+ "Use variant=\"neutral\" with role=\"meter\" for magnitude or distribution values where reaching the maximum is not a success state",
102
89
  "Determinate values are clamped to the min/max range for display"
103
90
  ],
104
91
  "accessibility": [
105
92
  "Uses role=\"progressbar\" with aria-valuenow",
93
+ "Accepts role=\"meter\" for scalar measurements within a known range",
106
94
  "Label is associated with the progress bar",
107
95
  "State changes are announced to screen readers"
108
96
  ]
@@ -155,17 +143,11 @@
155
143
  "showValue: boolean - display percentage",
156
144
  "Determinate display values are clamped (and invalid min/max ranges render as 0%)"
157
145
  ],
158
- "a11yRules": [
159
- "A11Y_PROGRESS_ROLE",
160
- "A11Y_PROGRESS_VALUE"
161
- ]
146
+ "a11yRules": ["A11Y_PROGRESS_ROLE", "A11Y_PROGRESS_VALUE"]
162
147
  },
163
148
  "ai": {
164
149
  "compositionPattern": "compound",
165
- "subComponents": [
166
- "Root",
167
- "Circular"
168
- ]
150
+ "subComponents": ["Root", "Circular"]
169
151
  },
170
152
  "provenance": {
171
153
  "source": "migrated",
@@ -63,6 +63,10 @@
63
63
  }
64
64
 
65
65
  // Color variants
66
+ .indicatorNeutral {
67
+ background-color: var(--fui-text-tertiary, $fui-text-tertiary);
68
+ }
69
+
66
70
  .indicatorSuccess {
67
71
  background-color: var(--fui-color-success-text, $fui-color-success-text);
68
72
  }
@@ -94,7 +98,7 @@
94
98
  }
95
99
 
96
100
  // Complete state
97
- .root[data-complete] .indicator {
101
+ .root[data-complete] .indicator:not(.indicatorNeutral) {
98
102
  background-color: var(--fui-color-success-text, $fui-color-success-text);
99
103
  }
100
104
 
@@ -1,14 +1,14 @@
1
- 'use client';
1
+ "use client";
2
2
 
3
- import * as React from 'react';
4
- import { Progress as BaseProgress } from '@base-ui/react/progress';
5
- import styles from './Progress.module.scss';
3
+ import * as React from "react";
4
+ import { Progress as BaseProgress } from "@base-ui/react/progress";
5
+ import styles from "./Progress.module.scss";
6
6
 
7
7
  // ============================================
8
8
  // Types
9
9
  // ============================================
10
10
 
11
- export interface ProgressProps extends Omit<React.HTMLAttributes<HTMLDivElement>, 'defaultValue'> {
11
+ export interface ProgressProps extends Omit<React.HTMLAttributes<HTMLDivElement>, "defaultValue"> {
12
12
  /** Current progress value (0-100). Null for indeterminate. */
13
13
  value?: number | null;
14
14
  /** Minimum value */
@@ -16,9 +16,9 @@ export interface ProgressProps extends Omit<React.HTMLAttributes<HTMLDivElement>
16
16
  /** Maximum value */
17
17
  max?: number;
18
18
  /** Size of the progress bar */
19
- size?: 'sm' | 'md' | 'lg';
19
+ size?: "sm" | "md" | "lg";
20
20
  /** Color variant */
21
- variant?: 'default' | 'success' | 'warning' | 'danger';
21
+ variant?: "default" | "neutral" | "success" | "warning" | "danger";
22
22
  /** Label text */
23
23
  label?: string;
24
24
  /** Show percentage value */
@@ -31,9 +31,9 @@ export interface CircularProgressProps extends React.HTMLAttributes<HTMLDivEleme
31
31
  /** Current progress value (0-100). Null for indeterminate. */
32
32
  value?: number | null;
33
33
  /** Size of the circular progress */
34
- size?: 'sm' | 'md' | 'lg';
34
+ size?: "sm" | "md" | "lg";
35
35
  /** Color variant */
36
- variant?: 'default' | 'success' | 'warning' | 'danger';
36
+ variant?: "default" | "success" | "warning" | "danger";
37
37
  /** Show percentage in center */
38
38
  showValue?: boolean;
39
39
  /** Stroke width */
@@ -48,52 +48,51 @@ function ProgressRoot({
48
48
  value = null,
49
49
  min = 0,
50
50
  max = 100,
51
- size = 'md',
52
- variant = 'default',
51
+ size = "md",
52
+ variant = "default",
53
53
  label,
54
54
  showValue = false,
55
55
  formatValue,
56
56
  className,
57
- 'aria-label': ariaLabel,
58
- 'aria-valuetext': ariaValueText,
57
+ role,
58
+ "aria-label": ariaLabel,
59
+ "aria-valuetext": ariaValueText,
59
60
  ...htmlProps
60
61
  }: ProgressProps) {
61
62
  const isIndeterminate = value === null;
62
63
  const range = max - min;
63
- const normalizedPercentage = isIndeterminate
64
- ? 0
65
- : range <= 0
66
- ? 0
67
- : ((value - min) / range) * 100;
64
+ const normalizedPercentage = isIndeterminate ? 0 : range <= 0 ? 0 : ((value - min) / range) * 100;
68
65
  const percentage = isIndeterminate
69
66
  ? 0
70
67
  : Math.round(Math.min(100, Math.max(0, normalizedPercentage)));
71
68
 
72
69
  const trackClasses = [
73
70
  styles.track,
74
- size === 'sm' && styles.trackSm,
75
- size === 'md' && styles.trackMd,
76
- size === 'lg' && styles.trackLg,
77
- ].filter(Boolean).join(' ');
71
+ size === "sm" && styles.trackSm,
72
+ size === "md" && styles.trackMd,
73
+ size === "lg" && styles.trackLg,
74
+ ]
75
+ .filter(Boolean)
76
+ .join(" ");
78
77
 
79
78
  const indicatorClasses = [
80
79
  styles.indicator,
81
- variant === 'success' && styles.indicatorSuccess,
82
- variant === 'warning' && styles.indicatorWarning,
83
- variant === 'danger' && styles.indicatorDanger,
80
+ variant === "neutral" && styles.indicatorNeutral,
81
+ variant === "success" && styles.indicatorSuccess,
82
+ variant === "warning" && styles.indicatorWarning,
83
+ variant === "danger" && styles.indicatorDanger,
84
84
  isIndeterminate && styles.indicatorIndeterminate,
85
- ].filter(Boolean).join(' ');
85
+ ]
86
+ .filter(Boolean)
87
+ .join(" ");
86
88
 
87
- const rootClasses = [styles.root, className].filter(Boolean).join(' ');
89
+ const rootClasses = [styles.root, className].filter(Boolean).join(" ");
88
90
 
89
- const displayValue = formatValue
90
- ? formatValue(percentage)
91
- : `${percentage}%`;
91
+ const displayValue = formatValue ? formatValue(percentage) : `${percentage}%`;
92
92
 
93
93
  // Default value text for screen readers
94
- const effectiveValueText = ariaValueText || (
95
- isIndeterminate ? 'Loading' : `${percentage} percent`
96
- );
94
+ const effectiveValueText =
95
+ ariaValueText || (isIndeterminate ? "Loading" : `${percentage} percent`);
97
96
 
98
97
  return (
99
98
  <BaseProgress.Root
@@ -102,20 +101,15 @@ function ProgressRoot({
102
101
  min={min}
103
102
  max={max}
104
103
  className={rootClasses}
105
- aria-label={ariaLabel || (label ? undefined : 'Progress')}
104
+ role={role ?? "progressbar"}
105
+ aria-label={ariaLabel || (label ? undefined : "Progress")}
106
106
  aria-valuetext={effectiveValueText}
107
107
  aria-busy={isIndeterminate}
108
108
  >
109
109
  {(label || showValue) && (
110
110
  <div className={styles.header}>
111
- {label && (
112
- <BaseProgress.Label className={styles.label}>
113
- {label}
114
- </BaseProgress.Label>
115
- )}
116
- {showValue && !isIndeterminate && (
117
- <span className={styles.value}>{displayValue}</span>
118
- )}
111
+ {label && <BaseProgress.Label className={styles.label}>{label}</BaseProgress.Label>}
112
+ {showValue && !isIndeterminate && <span className={styles.value}>{displayValue}</span>}
119
113
  </div>
120
114
  )}
121
115
  <BaseProgress.Track className={trackClasses}>
@@ -140,14 +134,14 @@ const CIRCLE_SIZES = {
140
134
 
141
135
  function CircularProgressRoot({
142
136
  value = null,
143
- size = 'md',
144
- variant = 'default',
137
+ size = "md",
138
+ variant = "default",
145
139
  showValue = false,
146
140
  strokeWidth: customStrokeWidth,
147
141
  className,
148
- 'aria-label': ariaLabel,
149
- 'aria-labelledby': ariaLabelledBy,
150
- 'aria-valuetext': ariaValueText,
142
+ "aria-label": ariaLabel,
143
+ "aria-labelledby": ariaLabelledBy,
144
+ "aria-valuetext": ariaValueText,
151
145
  ...htmlProps
152
146
  }: CircularProgressProps) {
153
147
  const isIndeterminate = value === null;
@@ -160,26 +154,24 @@ function CircularProgressRoot({
160
154
  const circumference = 2 * Math.PI * radius;
161
155
  const offset = circumference - (percentage / 100) * circumference;
162
156
 
163
- const sizeClass = size === 'sm' ? styles.circularSm
164
- : size === 'lg' ? styles.circularLg
165
- : styles.circularMd;
157
+ const sizeClass =
158
+ size === "sm" ? styles.circularSm : size === "lg" ? styles.circularLg : styles.circularMd;
166
159
 
167
160
  const indicatorClasses = [
168
161
  styles.circularIndicator,
169
- variant === 'success' && styles.circularIndicatorSuccess,
170
- variant === 'warning' && styles.circularIndicatorWarning,
171
- variant === 'danger' && styles.circularIndicatorDanger,
162
+ variant === "success" && styles.circularIndicatorSuccess,
163
+ variant === "warning" && styles.circularIndicatorWarning,
164
+ variant === "danger" && styles.circularIndicatorDanger,
172
165
  isIndeterminate && styles.circularIndicatorIndeterminate,
173
- ].filter(Boolean).join(' ');
174
-
175
- const rootClasses = [styles.circular, sizeClass, className]
166
+ ]
176
167
  .filter(Boolean)
177
- .join(' ');
168
+ .join(" ");
169
+
170
+ const rootClasses = [styles.circular, sizeClass, className].filter(Boolean).join(" ");
178
171
 
179
172
  // Default value text for screen readers
180
- const effectiveValueText = ariaValueText || (
181
- isIndeterminate ? 'Loading' : `${Math.round(percentage)} percent`
182
- );
173
+ const effectiveValueText =
174
+ ariaValueText || (isIndeterminate ? "Loading" : `${Math.round(percentage)} percent`);
183
175
 
184
176
  return (
185
177
  <BaseProgress.Root
@@ -220,11 +212,13 @@ function CircularProgressRoot({
220
212
  strokeWidth={strokeWidth}
221
213
  strokeDasharray={circumference}
222
214
  strokeDashoffset={isIndeterminate ? undefined : offset}
223
- style={isIndeterminate ? { transformOrigin: 'center' } : undefined}
215
+ style={isIndeterminate ? { transformOrigin: "center" } : undefined}
224
216
  />
225
217
  </svg>
226
218
  {showValue && !isIndeterminate && (
227
- <span className={styles.circularValue} aria-hidden="true">{Math.round(percentage)}%</span>
219
+ <span className={styles.circularValue} aria-hidden="true">
220
+ {Math.round(percentage)}%
221
+ </span>
228
222
  )}
229
223
  </BaseProgress.Root>
230
224
  );