Skip to content

Conversation

@lqr131115
Copy link
Contributor

@lqr131115 lqr131115 commented Oct 23, 2025

First of all, thank you for your contribution! :-)

Please makes sure that these checkboxes are checked before submitting your PR, thank you!

  • Make sure that you follow antd's code convention.
  • Run npm run lint and fix those errors before submitting in order to keep consistent code style.
  • Rebase before creating a PR to keep commit history clear.
  • Add some descriptions and refer relative issues for you PR.

Extra checklist:

if isBugFix :

  • Make sure that you add at least one unit test for the bug which you had fixed.

elif isNewFeature :

  • Update API docs for the component.
  • Update/Add demo to demonstrate new feature.
  • Update TypeScript definition for the component.
  • Add unit tests for the feature.

Summary by CodeRabbit

  • 新功能

    • 新增完整评分组件,支持全星/半星、滑动交互、清除、只读、自定义图标与颜色及动画效果。
    • 提供可配置的图标动画与视觉样式。
  • 文档

    • 添加中英文文档与示例页面,展示多种使用场景与 API 说明。
  • 示例与演示

    • 新增演示示例并加入演示列表,便于在示例应用中查看交互。
  • 测试

    • 新增基础演示测试套件。

@gemini-code-assist
Copy link
Contributor

Summary of Changes

Hello @lqr131115, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request adds a new Rate component to the library, enabling users to implement interactive star rating functionalities. The component is highly customizable, supporting features like half-star selection, swiping gestures, read-only states, and animated feedback, making it versatile for various rating display and input needs.

Highlights

  • New Rate Component: Introduces a new Rate component for graphical rating scales, supporting various configurations.
  • Interactive Features: The Rate component supports basic rating, half-star selection, swiping for rating, read-only mode, and clear functionality.
  • Customization and Animation: Allows customization of icons (name, type, size, color) and includes an optional animation configuration for interactive feedback.
  • Comprehensive API and Documentation: Provides a detailed API with properties for value control, appearance, behavior, and callbacks, along with English and Chinese documentation and a demo.
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

@coderabbitai
Copy link

coderabbitai bot commented Oct 23, 2025

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Note

Other AI code review bot(s) detected

CodeRabbit has detected other AI code review bot(s) in this pull request and will avoid duplicating their findings in the review comments. This may lead to a less comprehensive review.

📝 Walkthrough

概览

在 React Native 项目中新增完整的 Rate(评分)组件,包括核心实现、类型定义、样式、动画支持、工具函数、文档、演示与测试,并在 components/index.tsx 中对外导出该组件。

变更

功能模块 / 文件 变更摘要
核心组件
components/rate/index.tsx
新增默认导出 Rate 组件,包含手势(PanResponder)、RTL 支持、半星/全星逻辑、清除、只读、动画集成与外部受控/非受控同步
组件导出
components/index.tsx
新增对 ./rate/index 的 re-export(公开导出 Rate
类型定义
components/rate/PropsType.tsx, components/types.ts
新增 RatePropsRateIconPropsAnimationConfigAnimatedIconProps 等类型,并在 components/types.ts 导出 RateProps
图标与动画子组件
components/rate/AnimatedIcon.tsx, components/rate/RateIcon.tsx
新增 AnimatedIcon(缩放动画)与 RateIcon(full/half/empty 三态渲染)
样式与常量
components/rate/style/index.tsx, components/rate/constants.ts
新增样式工厂 RateStyle 与默认动画配置 defaultAnimationConfig(Easing.elastic、300ms、scale 1.2)
工具函数
components/rate/utils.ts
新增 getStars(rating, maxStars),返回每格为 full/half/empty 的数组
演示与测试
components/rate/demo/basic.{md,tsx}, components/rate/__tests__/demo.test.js, rn-kitchen-sink/demoList.js
新增演示文档与示例组件 RateExample,添加 demo 注册项并增加简单 demo 测试调用
文档
components/rate/index.en-US.md, components/rate/index.zh-CN.md
新增英文与中文文档,列出 API、用法与示例

序列图

sequenceDiagram
    participant User
    participant Rate as Rate 组件
    participant Pan as PanResponder
    participant State as 内部状态
    participant Anim as AnimatedIcon

    User->>Rate: 点击或滑动评分区域
    Rate->>Pan: 接收手势事件(start/move/end)
    Pan->>State: 计算并更新 internalValue(含半星与 RTL 处理)
    Rate->>Rate: 使用 getStars 生成星态数组
    Rate->>Anim: 对被激活星位触发动画(active=true)
    Anim->>Anim: 执行缩放动画(1 → scale)
    Rate->>User: 渲染更新后的星图标
    Note over Rate: 释放手势后触发 onChange/onRatingEnd;若 allowClear 并重复点击同一值则清除
Loading

代码审查工作量

🎯 3 (中等复杂度) | ⏱️ ~25 分钟

🐰 星光轻敲屏幕,
半颗闪烁又完整,
手势滑过评分行,
弹性动画悄然生,
新的 Rate 在枝头笑。

Pre-merge checks and finishing touches

✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed 标题"feat: 评分 rate"清晰地表明了Pull Request的主要变化——添加一个新的评分(Rate)组件功能。使用了conventional commit格式(feat:)标识新特性,并通过中英文双语描述了功能的本质。从raw_summary可以看出,整个changeset围绕Rate组件的完整实现展开,包括核心组件、类型定义、样式、工具函数、文档和演示代码,标题准确地捕捉了这一主要变化的要点。标题简洁但不模糊,足够具体让同事快速理解PR的核心目的。
Docstring Coverage ✅ Passed No functions found in the changes. Docstring coverage check skipped.

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces a new Rate component, which is a great addition. The implementation is comprehensive, covering features like half-star rating, swiping, clearing, and animations. The code is well-structured with separate files for props, styles, and utility functions.

I've left a few comments with suggestions for improvement, mainly focusing on performance optimization in PanResponder usage, improving type safety, removing a magic number, and addressing some minor code duplication and inconsistencies. Overall, this is a solid contribution.

@lqr131115 lqr131115 mentioned this pull request Oct 23, 2025
1 task
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🧹 Nitpick comments (11)
components/rate/utils.ts (1)

1-9: 函数逻辑正确,可以考虑添加更具体的返回类型。

getStars 函数的逻辑正确处理了满星、半星和空星的状态。

可以考虑为返回值添加更具体的类型注解以提高类型安全性:

-export function getStars(rating: number, maxStars: number) {
+export function getStars(rating: number, maxStars: number): ('full' | 'half' | 'empty')[] {
   return [...Array(maxStars)].map((_, i) => {
components/rate/index.zh-CN.md (1)

28-29: 建议简化默认值描述。

默认值列中的描述信息有些冗余。默认值应该简洁明了。

-| iconName        | 图标名称                                                | `string`                                                                                              | `star`, 默认星星 |
-| iconType        | 图标类型                                                | `fill | outline`                                                                                     | `fill`, 实底风格 |
+| iconName        | 图标名称                                                | `string`                                                                                              | `star` |
+| iconType        | 图标类型                                                | `fill | outline`                                                                                     | `fill` |
components/rate/demo/basic.md (1)

14-15: 示例中 Item 来源错误,应为 List.Item
当前写成 Popover.Item 且未导入 Popover,复制运行会报错。建议更正:

-const Item = Popover.Item
+const Item = List.Item
components/rate/RateIcon.tsx (2)

6-22: 避免向底层 Icon 透传未知属性并收紧类型。
emptyColor 不应再透传到 IconFill/IconOutline;同时移除 any

-const Icon = ({
-  size,
-  name,
-  color,
-  emptyColor,
-  isFill,
-}: Omit<RateIconProps, 'type'>) => {
-  const IconComponent: any = isFill ? IconFill : IconOutline
-  return (
-    <IconComponent
-      size={size}
-      color={color}
-      name={name}
-      emptyColor={emptyColor}
-    />
-  )
-}
+const Icon = ({
+  size,
+  name,
+  color,
+  isFill,
+}: Omit<RateIconProps, 'type' | 'emptyColor'>) => {
+  const IconComponent: typeof IconFill | typeof IconOutline = isFill
+    ? IconFill
+    : IconOutline
+  return <IconComponent size={size} color={color} name={name} />
+}

46-82: 请验证 RTL 下半星裁剪是否正确且无缝。
容器在 RTL 时整体 rotateY(180deg),第二半区块也固定 rotateY(180deg),存在“双重镜像”风险,某些像素密度下两半之间可能出现细缝。建议:

  • 视觉验收 RTL/LTR(深浅背景、不同尺寸、不同颜色)。
  • 如有缝隙,改为“叠放两层绝对定位图标 + 宽度裁剪”避免缝隙。
components/rate/AnimatedIcon.tsx (1)

13-17: 补齐 delay 支持并改进清理函数。
defaultAnimationConfig 保持一致,避免忽略用户自定义的 delay。

   const {
-    scale = defaultAnimationConfig.scale,
-    easing = defaultAnimationConfig.easing,
-    duration = defaultAnimationConfig.duration,
+    scale = defaultAnimationConfig.scale,
+    easing = defaultAnimationConfig.easing,
+    duration = defaultAnimationConfig.duration,
+    delay = defaultAnimationConfig.delay,
   } = config
@@
-  React.useEffect(() => {
-    const animation = Animated.timing(animatedSize.current, {
-      toValue: active ? scale : 1,
-      useNativeDriver: true,
-      easing,
-      duration,
-    })
-
-    animation.start()
-    return animation.stop
-  }, [active, scale, easing, duration])
+  React.useEffect(() => {
+    const animation = Animated.timing(animatedSize.current, {
+      toValue: active ? scale : 1,
+      useNativeDriver: true,
+      easing,
+      duration,
+      delay,
+    })
+    animation.start()
+    return () => animation.stop()
+  }, [active, scale, easing, duration, delay])

Also applies to: 21-31

components/rate/index.tsx (5)

130-142: 与动画配置保持一致:使用合并后的 delay
这里应使用 memoAnimationOptions.config.delay,否则用户自定义 delay 无效。

-        setTimeout(() => {
-          setInteracting(false)
-        }, defaultAnimationConfig.delay)
+        setTimeout(() => {
+          setInteracting(false)
+        }, memoAnimationOptions.config.delay)

同理建议在 onPanResponderTerminate 中也替换为 memoAnimationOptions.config.delay


176-176: 样式合并用数组,避免丢失样式与提升性能。
RN 推荐 style={[a, b]},对象展开会丢失数组样式且有额外开销。

-                  style={{ ...styles.icon, ...iconStyle }}>
+                  style={[styles.icon, iconStyle]}>

66-71: 评分取整中的 + 0.2 偏移请确认依据。
该偏移会提前晋级到下一半星,易引发边界感知不一致。建议:

  • 说明设计依据或加入注释;
  • 或将偏移提取为常量(并允许配置);
  • 或移除偏移,仅基于标准舍入。

134-142: 终止回调可能传递 -1
onPanResponderTerminateendRating.current,若从未移动则为 -1。建议回退到 internalValue

-      onPanResponderTerminate: () => {
-        // called when user drags outside of the component
-        onRatingEnd?.(endRating.current)
+      onPanResponderTerminate: () => {
+        // called when user drags outside of the component
+        onRatingEnd?.(endRating.current >= 0 ? endRating.current : internalValue)
         endRating.current = -1
         startRating.current = -1
-        setTimeout(() => {
-          setInteracting(false)
-        }, defaultAnimationConfig.delay)
+        setTimeout(() => {
+          setInteracting(false)
+        }, memoAnimationOptions.config.delay)
       },

12-31: API 一致性:iconFilliconType 存在重叠。
PropsType 同时暴露 iconFill?: booleaniconType?: 'fill' | 'outline',但实现仅使用 iconType。建议统一一个 API,并在文档中标注另一个为废弃或移除。

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 44a7ca6 and cd84aff.

⛔ Files ignored due to path filters (2)
  • components/rate/__tests__/__snapshots__/demo.test.js.snap is excluded by !**/*.snap
  • tests/__snapshots__/index.test.js.snap is excluded by !**/*.snap
📒 Files selected for processing (15)
  • components/index.tsx (1 hunks)
  • components/rate/AnimatedIcon.tsx (1 hunks)
  • components/rate/PropsType.tsx (1 hunks)
  • components/rate/RateIcon.tsx (1 hunks)
  • components/rate/__tests__/demo.test.js (1 hunks)
  • components/rate/constants.ts (1 hunks)
  • components/rate/demo/basic.md (1 hunks)
  • components/rate/demo/basic.tsx (1 hunks)
  • components/rate/index.en-US.md (1 hunks)
  • components/rate/index.tsx (1 hunks)
  • components/rate/index.zh-CN.md (1 hunks)
  • components/rate/style/index.tsx (1 hunks)
  • components/rate/utils.ts (1 hunks)
  • components/types.ts (1 hunks)
  • rn-kitchen-sink/demoList.js (1 hunks)
🧰 Additional context used
🧬 Code graph analysis (7)
components/rate/AnimatedIcon.tsx (2)
components/rate/PropsType.tsx (1)
  • AnimatedIconProps (53-58)
components/rate/constants.ts (1)
  • defaultAnimationConfig (4-9)
components/rate/__tests__/demo.test.js (1)
tests/shared/demoTest.js (1)
  • rnDemoTest (6-24)
components/rate/index.tsx (5)
components/rate/PropsType.tsx (2)
  • RateProps (10-30)
  • AnimationOptions (48-51)
components/rate/constants.ts (1)
  • defaultAnimationConfig (4-9)
components/style/index.tsx (1)
  • WithTheme (68-92)
components/rate/style/index.tsx (2)
  • RateStyle (4-7)
  • theme (9-18)
components/rate/utils.ts (1)
  • getStars (1-9)
components/rate/demo/basic.tsx (1)
components/flex/Flex.tsx (1)
  • Flex (19-84)
components/rate/RateIcon.tsx (2)
components/icon/index.tsx (1)
  • Icon (15-44)
components/rate/PropsType.tsx (1)
  • RateIconProps (32-39)
components/rate/constants.ts (1)
components/rate/PropsType.tsx (1)
  • AnimationConfig (41-46)
components/rate/PropsType.tsx (1)
components/types.ts (1)
  • RateProps (49-49)
🔇 Additional comments (9)
components/rate/__tests__/demo.test.js (1)

1-3: 测试文件结构正确。

测试文件遵循了项目中其他组件的标准模式,正确使用共享的 demoTest 工具来测试 Rate 组件的 demo。

components/index.tsx (1)

38-38: Rate 组件导出正确。

Rate 组件的导出遵循了现有模式,并且按字母顺序正确放置在 Radio 和 Result 之间。

components/types.ts (1)

49-49: RateProps 类型导出正确。

RateProps 类型的导出遵循了现有模式,并且按字母顺序正确放置。

rn-kitchen-sink/demoList.js (1)

194-199: Rate demo 配置正确。

Rate demo 配置项遵循了现有的结构模式,正确放置在 UICONTROLS 部分,并且包含了所有必需的字段。

components/rate/style/index.tsx (1)

1-18: 样式定义正确且遵循最佳实践。

Rate 组件的样式定义遵循了项目中其他组件的标准模式:

  • 使用 StyleSheet.create 创建样式
  • 通过 Theme 使用一致的间距值
  • rateContainer 的 flexDirection 和 alignSelf 设置适合水平排列的星星布局
components/rate/constants.ts (1)

4-9: 默认动画配置设计合理,类型严格,直接可用。
覆盖了 easing/duration/scale/delay 且与 AnimationConfig 对齐,无需改动。

components/rate/demo/basic.tsx (1)

1-6: Demo 覆盖场景全面,接口使用正确。
示例可直接跑通,便于验证交互。

components/rate/PropsType.tsx (2)

10-30: 接口设计良好!

RateProps 接口结构完整且合理:

  • 支持受控/非受控模式(value/defaultValue)
  • 提供了丰富的交互配置选项
  • animationConfig?: boolean | AnimationConfig 的设计很好,既支持简单的开关,也支持自定义配置
  • 回调函数涵盖了评分的完整生命周期

32-58: 类型定义清晰且一致!

剩余的类型定义都很合理:

  • RateIconProps:为单个图标提供了必要的渲染属性
  • AnimationConfig:所有字段可选,提供了灵活的动画配置
  • AnimationOptions:正确使用 Required<AnimationConfig> 确保内部使用时所有配置都存在
  • AnimatedIconProps:为动画包装组件提供了合适的属性接口

类型层次结构清晰,各类型职责分明。

@lqr131115
Copy link
Contributor Author

lqr131115 commented Oct 23, 2025

展示效果:#1456

@1uokun 1uokun changed the base branch from master to 5.5.0 October 24, 2025 09:26
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants