@ecohouse/ui 0.1.6 → 0.1.7

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/dist/index.cjs CHANGED
@@ -114,6 +114,43 @@ var counterTypography = {
114
114
  lineHeight: 14,
115
115
  letterSpacing: 0
116
116
  };
117
+ var ratingTypography = {
118
+ fontFamily: fonts.sans,
119
+ fontSize: 32,
120
+ fontWeight: "700",
121
+ lineHeight: 35.84,
122
+ letterSpacing: 0
123
+ };
124
+ var commentCardTypography = {
125
+ name: {
126
+ fontFamily: fonts.sans,
127
+ fontSize: 16,
128
+ fontWeight: "600",
129
+ lineHeight: 18,
130
+ letterSpacing: 0
131
+ },
132
+ date: {
133
+ fontFamily: fonts.sans,
134
+ fontSize: 14,
135
+ fontWeight: "400",
136
+ lineHeight: 16,
137
+ letterSpacing: 0
138
+ },
139
+ comment: {
140
+ fontFamily: fonts.sans,
141
+ fontSize: 14,
142
+ fontWeight: "400",
143
+ lineHeight: 19,
144
+ letterSpacing: 0
145
+ },
146
+ action: {
147
+ fontFamily: fonts.sans,
148
+ fontSize: 12,
149
+ fontWeight: "700",
150
+ lineHeight: 12,
151
+ letterSpacing: 0
152
+ }
153
+ };
117
154
  var inputTypography = {
118
155
  label: {
119
156
  fontFamily: fonts.sans,
@@ -711,6 +748,47 @@ function SidebarIcon({ size = 20, color = colors.primary, strokeWidth = 2 }) {
711
748
  ) });
712
749
  }
713
750
 
751
+ // src/icons/Star/starPath.ts
752
+ var STAR_PATH = "M12.6112 2.09824C12.9186 1.47565 13.0722 1.16436 13.2808 1.0649C13.4623 0.978367 13.6732 0.978367 13.8546 1.0649C14.0632 1.16436 14.2169 1.47565 14.5242 2.09824L17.4398 8.00486C17.5305 8.18866 17.5759 8.28056 17.6422 8.35192C17.7009 8.41509 17.7713 8.46628 17.8495 8.50264C17.9378 8.54371 18.0392 8.55854 18.242 8.58818L24.7637 9.54142C25.4505 9.6418 25.7938 9.69199 25.9528 9.85973C26.091 10.0057 26.156 10.2062 26.1297 10.4055C26.0995 10.6346 25.8509 10.8767 25.3537 11.361L20.6363 15.9557C20.4893 16.0989 20.4157 16.1706 20.3683 16.2558C20.3263 16.3312 20.2993 16.4141 20.2889 16.4998C20.2772 16.5966 20.2945 16.6978 20.3292 16.9001L21.4423 23.39C21.5597 24.0745 21.6184 24.4167 21.5081 24.6198C21.4121 24.7965 21.2415 24.9205 21.0438 24.9571C20.8165 24.9992 20.5092 24.8376 19.8945 24.5144L14.0642 21.4483C13.8826 21.3527 13.7917 21.305 13.696 21.2862C13.6113 21.2696 13.5242 21.2696 13.4394 21.2862C13.3437 21.305 13.2529 21.3527 13.0713 21.4483L7.24094 24.5144C6.62626 24.8376 6.31892 24.9992 6.09167 24.9571C5.89395 24.9205 5.72334 24.7965 5.62736 24.6198C5.51704 24.4167 5.57574 24.0745 5.69314 23.39L6.80622 16.9001C6.84092 16.6978 6.85828 16.5966 6.84653 16.4998C6.83614 16.4141 6.80919 16.3312 6.76718 16.2558C6.71974 16.1706 6.64621 16.0989 6.49916 15.9557L1.78179 11.361C1.28459 10.8767 1.03599 10.6346 1.00574 10.4055C0.979423 10.2062 1.04445 10.0057 1.18271 9.85973C1.34162 9.69199 1.685 9.6418 2.37177 9.54142L8.89346 8.58818C9.09627 8.55854 9.19768 8.54371 9.286 8.50264C9.36419 8.46628 9.43459 8.41509 9.49329 8.35192C9.55958 8.28056 9.60495 8.18866 9.69567 8.00486L12.6112 2.09824Z";
753
+ function StarIcon({
754
+ active = false,
755
+ size = 28,
756
+ height,
757
+ color,
758
+ strokeWidth = 2
759
+ }) {
760
+ const resolvedColor = color ?? (active ? "#E38E5E" : colors.grey150);
761
+ return /* @__PURE__ */ jsxRuntime.jsx(Svg__default.default, { width: size, height: height ?? size * 26 / 28, viewBox: "0 0 28 26", fill: "none", children: /* @__PURE__ */ jsxRuntime.jsx(
762
+ Svg.Path,
763
+ {
764
+ d: STAR_PATH,
765
+ fill: active ? resolvedColor : "none",
766
+ stroke: resolvedColor,
767
+ strokeWidth,
768
+ strokeLinecap: "round",
769
+ strokeLinejoin: "round"
770
+ }
771
+ ) });
772
+ }
773
+ function StarFilledIcon({
774
+ size = 28,
775
+ height,
776
+ color = "#E38E5E",
777
+ strokeWidth = 2
778
+ }) {
779
+ return /* @__PURE__ */ jsxRuntime.jsx(Svg__default.default, { width: size, height: height ?? size * 26 / 28, viewBox: "0 0 28 26", fill: color, children: /* @__PURE__ */ jsxRuntime.jsx(
780
+ Svg.Path,
781
+ {
782
+ d: STAR_PATH,
783
+ fill: color,
784
+ stroke: color,
785
+ strokeWidth,
786
+ strokeLinecap: "round",
787
+ strokeLinejoin: "round"
788
+ }
789
+ ) });
790
+ }
791
+
714
792
  // src/icons/User/userPath.ts
715
793
  var USER_PATH = "M15.8334 17.5C15.8334 14.2783 13.2217 11.6667 10 11.6667C6.77836 11.6667 4.16669 14.2783 4.16669 17.5M10 9.16667C8.15907 9.16667 6.66669 7.67428 6.66669 5.83333C6.66669 3.99238 8.15907 2.5 10 2.5C11.841 2.5 13.3334 3.99238 13.3334 5.83333C13.3334 7.67428 11.841 9.16667 10 9.16667Z";
716
794
  function UserIcon({ size = 20, color = colors.primary, strokeWidth = 2 }) {
@@ -783,6 +861,8 @@ var icons = {
783
861
  settings: SettingsIcon,
784
862
  show: ShowIcon,
785
863
  sidebar: SidebarIcon,
864
+ star: StarIcon,
865
+ starFilled: StarFilledIcon,
786
866
  user: UserIcon,
787
867
  usersAlt: UsersAltIcon,
788
868
  video: VideoIcon
@@ -801,6 +881,8 @@ var iconGroups = {
801
881
  "calendar",
802
882
  "calendarOutline",
803
883
  "heart",
884
+ "star",
885
+ "starFilled",
804
886
  "minus",
805
887
  "plus"
806
888
  ],
@@ -3492,6 +3574,272 @@ var styles13 = reactNative.StyleSheet.create({
3492
3574
  color: colors.white
3493
3575
  }
3494
3576
  });
3577
+ var STAR_COUNT = 5;
3578
+ var BASE_ITEM_SIZE = 16;
3579
+ var ICON_WIDTH_RATIO = 12.57 / BASE_ITEM_SIZE;
3580
+ var ICON_HEIGHT_RATIO = 11.98 / BASE_ITEM_SIZE;
3581
+ var STAR_GAP_RATIO = 2 / BASE_ITEM_SIZE;
3582
+ function clamp2(value) {
3583
+ return Math.max(0, Math.min(value, STAR_COUNT));
3584
+ }
3585
+ var RatingInput = react.forwardRef(
3586
+ function RatingInput2({
3587
+ value,
3588
+ defaultValue = 0,
3589
+ onValueChange,
3590
+ showValue = true,
3591
+ precision = 1,
3592
+ size = 20,
3593
+ starGap,
3594
+ readOnly = false,
3595
+ disabled = false,
3596
+ style,
3597
+ valueStyle,
3598
+ className,
3599
+ hitSlop = 6,
3600
+ accessibilityLabel,
3601
+ ...rest
3602
+ }, forwardedRef) {
3603
+ const containerRef = react.useRef(null);
3604
+ const setContainerRef = react.useMemo(() => mergeRefs(containerRef, forwardedRef), [forwardedRef]);
3605
+ const isControlled = value !== void 0;
3606
+ const [uncontrolledValue, setUncontrolledValue] = react.useState(() => clamp2(defaultValue));
3607
+ const selectedValue = clamp2(isControlled ? value : uncontrolledValue);
3608
+ const selectedStarCount = Math.round(selectedValue);
3609
+ const iconWidth = size * ICON_WIDTH_RATIO;
3610
+ const iconHeight = size * ICON_HEIGHT_RATIO;
3611
+ const resolvedStarGap = starGap ?? size * STAR_GAP_RATIO;
3612
+ const resolvedAccessibilityLabel = accessibilityLabel ?? (readOnly ? `${selectedValue} out of ${STAR_COUNT} stars` : "Rating");
3613
+ useApplyWebClassName(containerRef, className);
3614
+ const selectValue = (nextValue) => {
3615
+ if (disabled || nextValue === selectedValue) return;
3616
+ if (!isControlled) setUncontrolledValue(nextValue);
3617
+ onValueChange?.(nextValue);
3618
+ };
3619
+ return /* @__PURE__ */ jsxRuntime.jsxs(
3620
+ reactNative.View,
3621
+ {
3622
+ ...rest,
3623
+ ref: setContainerRef,
3624
+ style: [styles14.root, disabled && styles14.disabled, style],
3625
+ children: [
3626
+ showValue ? /* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { numberOfLines: 1, style: [styles14.value, valueStyle], children: selectedValue.toFixed(precision) }) : null,
3627
+ /* @__PURE__ */ jsxRuntime.jsx(
3628
+ reactNative.View,
3629
+ {
3630
+ accessibilityRole: readOnly ? "image" : "radiogroup",
3631
+ accessibilityLabel: resolvedAccessibilityLabel,
3632
+ accessibilityState: { disabled },
3633
+ style: [styles14.stars, { gap: resolvedStarGap }],
3634
+ children: Array.from({ length: STAR_COUNT }, (_, index) => {
3635
+ const starValue = index + 1;
3636
+ const isSelected = starValue <= selectedStarCount;
3637
+ const icon = isSelected ? /* @__PURE__ */ jsxRuntime.jsx(StarFilledIcon, { size: iconWidth, height: iconHeight }) : /* @__PURE__ */ jsxRuntime.jsx(StarIcon, { size: iconWidth, height: iconHeight });
3638
+ const itemStyle = [styles14.starItem, { width: size, height: size }];
3639
+ if (readOnly) {
3640
+ return /* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: itemStyle, children: icon }, starValue);
3641
+ }
3642
+ return /* @__PURE__ */ jsxRuntime.jsx(
3643
+ reactNative.Pressable,
3644
+ {
3645
+ disabled,
3646
+ hitSlop,
3647
+ onPress: () => selectValue(starValue),
3648
+ accessibilityRole: "radio",
3649
+ accessibilityLabel: `${starValue} star${starValue === 1 ? "" : "s"}`,
3650
+ accessibilityState: { checked: isSelected, disabled },
3651
+ style: itemStyle,
3652
+ children: icon
3653
+ },
3654
+ starValue
3655
+ );
3656
+ })
3657
+ }
3658
+ )
3659
+ ]
3660
+ }
3661
+ );
3662
+ }
3663
+ );
3664
+ var styles14 = reactNative.StyleSheet.create({
3665
+ root: {
3666
+ flexDirection: "row",
3667
+ alignItems: "center",
3668
+ flexWrap: "nowrap",
3669
+ alignSelf: "flex-start",
3670
+ gap: 16
3671
+ },
3672
+ stars: {
3673
+ flexDirection: "row",
3674
+ alignItems: "center"
3675
+ },
3676
+ starItem: {
3677
+ alignItems: "center",
3678
+ justifyContent: "center"
3679
+ },
3680
+ value: {
3681
+ ...ratingTypography,
3682
+ color: colors.white
3683
+ },
3684
+ disabled: {
3685
+ opacity: 0.5
3686
+ }
3687
+ });
3688
+ var CARD_WIDTH = 370;
3689
+ var CARD_MIN_HEIGHT = 173;
3690
+ var AVATAR_SIZE = 44;
3691
+ var CommentCard = react.forwardRef(
3692
+ function CommentCard2({
3693
+ userName,
3694
+ date,
3695
+ commentText,
3696
+ rating,
3697
+ imageUrl,
3698
+ maxCommentLines = 3,
3699
+ maxCommentLength = 111,
3700
+ readMoreLabel = "\u0534\u056B\u057F\u0565\u056C \u0561\u057E\u0565\u056C\u056B\u0576",
3701
+ readLessLabel = "\u0553\u0561\u056F\u0565\u056C",
3702
+ onExpandedChange,
3703
+ style,
3704
+ commentStyle,
3705
+ className,
3706
+ ...rest
3707
+ }, forwardedRef) {
3708
+ const containerRef = react.useRef(null);
3709
+ const setContainerRef = react.useMemo(() => mergeRefs(containerRef, forwardedRef), [forwardedRef]);
3710
+ const [imageFailed, setImageFailed] = react.useState(false);
3711
+ const [expanded, setExpanded] = react.useState(false);
3712
+ const [actionHovered, setActionHovered] = react.useState(false);
3713
+ const hasImage = Boolean(imageUrl) && !imageFailed;
3714
+ const shouldShowAction = Array.from(commentText).length >= maxCommentLength;
3715
+ useApplyWebClassName(containerRef, className);
3716
+ react.useEffect(() => {
3717
+ setImageFailed(false);
3718
+ }, [imageUrl]);
3719
+ react.useEffect(() => {
3720
+ setExpanded(false);
3721
+ setActionHovered(false);
3722
+ }, [commentText, maxCommentLength, maxCommentLines]);
3723
+ const toggleExpanded = () => {
3724
+ const next = !expanded;
3725
+ setExpanded(next);
3726
+ onExpandedChange?.(next);
3727
+ };
3728
+ return /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { ...rest, ref: setContainerRef, style: [styles15.root, style], children: [
3729
+ /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: styles15.header, children: [
3730
+ /* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles15.avatar, children: hasImage ? /* @__PURE__ */ jsxRuntime.jsx(
3731
+ reactNative.Image,
3732
+ {
3733
+ source: { uri: imageUrl ?? void 0 },
3734
+ style: styles15.avatarImage,
3735
+ onError: () => setImageFailed(true)
3736
+ }
3737
+ ) : /* @__PURE__ */ jsxRuntime.jsx(UserIcon, { size: 20, color: colors.primary }) }),
3738
+ /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: styles15.identity, children: [
3739
+ /* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { numberOfLines: 1, style: styles15.name, children: userName }),
3740
+ /* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { numberOfLines: 1, style: styles15.date, children: date })
3741
+ ] }),
3742
+ /* @__PURE__ */ jsxRuntime.jsx(RatingInput, { value: rating, readOnly: true, showValue: false, size: 16 })
3743
+ ] }),
3744
+ /* @__PURE__ */ jsxRuntime.jsx(
3745
+ reactNative.Text,
3746
+ {
3747
+ numberOfLines: expanded ? void 0 : maxCommentLines,
3748
+ style: [styles15.comment, commentStyle],
3749
+ children: commentText
3750
+ }
3751
+ ),
3752
+ shouldShowAction ? /* @__PURE__ */ jsxRuntime.jsx(
3753
+ reactNative.Pressable,
3754
+ {
3755
+ onPress: toggleExpanded,
3756
+ accessibilityRole: "button",
3757
+ accessibilityState: { expanded },
3758
+ hitSlop: 6,
3759
+ onHoverIn: () => setActionHovered(true),
3760
+ onHoverOut: () => setActionHovered(false),
3761
+ style: styles15.action,
3762
+ children: /* @__PURE__ */ jsxRuntime.jsx(
3763
+ reactNative.Text,
3764
+ {
3765
+ style: [
3766
+ styles15.actionText,
3767
+ expanded && styles15.closeActionText,
3768
+ actionHovered && (expanded ? styles15.closeActionTextHovered : styles15.openActionTextHovered)
3769
+ ],
3770
+ children: expanded ? readLessLabel : readMoreLabel
3771
+ }
3772
+ )
3773
+ }
3774
+ ) : null
3775
+ ] });
3776
+ }
3777
+ );
3778
+ var styles15 = reactNative.StyleSheet.create({
3779
+ root: {
3780
+ width: CARD_WIDTH,
3781
+ minHeight: CARD_MIN_HEIGHT,
3782
+ padding: 16,
3783
+ gap: 12,
3784
+ borderRadius: 12,
3785
+ backgroundColor: colors.grey750
3786
+ },
3787
+ header: {
3788
+ flexDirection: "row",
3789
+ alignItems: "center",
3790
+ gap: 8
3791
+ },
3792
+ avatar: {
3793
+ width: AVATAR_SIZE,
3794
+ height: AVATAR_SIZE,
3795
+ flexShrink: 0,
3796
+ alignItems: "center",
3797
+ justifyContent: "center",
3798
+ overflow: "hidden",
3799
+ borderRadius: AVATAR_SIZE / 2,
3800
+ backgroundColor: colors.grey600
3801
+ },
3802
+ avatarImage: {
3803
+ width: AVATAR_SIZE,
3804
+ height: AVATAR_SIZE
3805
+ },
3806
+ identity: {
3807
+ minWidth: 0,
3808
+ flex: 1,
3809
+ gap: 4
3810
+ },
3811
+ name: {
3812
+ ...commentCardTypography.name,
3813
+ color: colors.white
3814
+ },
3815
+ date: {
3816
+ ...commentCardTypography.date,
3817
+ color: colors.grey0
3818
+ },
3819
+ comment: {
3820
+ ...commentCardTypography.comment,
3821
+ color: colors.white
3822
+ },
3823
+ action: {
3824
+ alignSelf: "flex-start",
3825
+ marginTop: "auto",
3826
+ minHeight: 16,
3827
+ justifyContent: "center"
3828
+ },
3829
+ actionText: {
3830
+ ...commentCardTypography.action,
3831
+ color: colors.white
3832
+ },
3833
+ closeActionText: {
3834
+ color: colors.primary
3835
+ },
3836
+ openActionTextHovered: {
3837
+ color: colors.primary
3838
+ },
3839
+ closeActionTextHovered: {
3840
+ color: colors.white
3841
+ }
3842
+ });
3495
3843
 
3496
3844
  exports.ArrowRightIcon = ArrowRightIcon;
3497
3845
  exports.Avatar = Avatar;
@@ -3509,6 +3857,7 @@ exports.Checkbox = Checkbox;
3509
3857
  exports.ChevronDownIcon = ChevronDownIcon;
3510
3858
  exports.ChevronLeftIcon = ChevronLeftIcon;
3511
3859
  exports.ClockIcon = ClockIcon;
3860
+ exports.CommentCard = CommentCard;
3512
3861
  exports.Counter = Counter;
3513
3862
  exports.DatePicker = DatePicker;
3514
3863
  exports.FacebookIcon = FacebookIcon;
@@ -3528,12 +3877,15 @@ exports.MinusIcon = MinusIcon;
3528
3877
  exports.NavigateIcon = NavigateIcon;
3529
3878
  exports.PhoneIcon = PhoneIcon;
3530
3879
  exports.PlusIcon = PlusIcon;
3880
+ exports.RatingInput = RatingInput;
3531
3881
  exports.SearchIcon = SearchIcon;
3532
3882
  exports.SegmentedToggle = SegmentedToggle;
3533
3883
  exports.Select = Select;
3534
3884
  exports.SettingsIcon = SettingsIcon;
3535
3885
  exports.ShowIcon = ShowIcon;
3536
3886
  exports.SidebarIcon = SidebarIcon;
3887
+ exports.StarFilledIcon = StarFilledIcon;
3888
+ exports.StarIcon = StarIcon;
3537
3889
  exports.StatCard = StatCard;
3538
3890
  exports.Textarea = Textarea;
3539
3891
  exports.Toggle = Toggle;
@@ -3544,6 +3896,7 @@ exports.avatarTypography = avatarTypography;
3544
3896
  exports.badgeTypography = badgeTypography;
3545
3897
  exports.buttonTypography = buttonTypography;
3546
3898
  exports.colors = colors;
3899
+ exports.commentCardTypography = commentCardTypography;
3547
3900
  exports.counterTypography = counterTypography;
3548
3901
  exports.datePickerTypography = datePickerTypography;
3549
3902
  exports.fonts = fonts;
@@ -3554,6 +3907,7 @@ exports.iconGroups = iconGroups;
3554
3907
  exports.iconNames = iconNames;
3555
3908
  exports.icons = icons;
3556
3909
  exports.inputTypography = inputTypography;
3910
+ exports.ratingTypography = ratingTypography;
3557
3911
  exports.segmentedToggleTypography = segmentedToggleTypography;
3558
3912
  exports.selectTypography = selectTypography;
3559
3913
  exports.statCardTypography = statCardTypography;