Skip to content

GuGu拼音游戏 (GuGu PinYin)

一句话总结:一款用“Q弹交互”和“森林探险”包装的,让孩子在点点按按中不知不觉学完21天拼音课程的数字化学习手账。


🌟 产品定位:沉浸式·游戏化拼音启蒙

“不只是学拼音,更是一场森林探险。”

我们正在打造一款对标 Duolingo(多邻国) 体验的,高互动、高反馈的儿童拼音启蒙 App。核心在于将枯燥的“跟读”转化为有趣的“点击与交互”。

🎨 1. 视觉主题:森林探险 & 贴纸手账

  • 世界观:以 “热带雨林” 为舞台,动物伙伴伴学。
  • 首页面交互:采用 独立卡片左右轮播 (Independent Card Horizontal Carousel) 设计,无限循环展示课程卡片。
  • 进度展示:点击用户头像弹出 普通弹框 (Standard Popup),清晰展示学习数据。
  • UI 风格“贴纸风” (Sticker UI),配合白色描边和圆润导角,营造“想去撕下来”的触感。

🎮 2. 交互体验:Juicy (多汁/Q弹)

拒绝生硬的 UI,追求**“像果冻一样”**的反馈:

  • 触感反馈JuicyButton 带来的挤压变形、回弹效果。
  • 视觉反馈:点击后的水波纹 (Ripple)、粒子爆发。
  • 流畅度:场景切换采用 无缝黑屏淡入淡出 (Seamless Fade Transition),拒绝生硬截断。

📚 3. 学习架构:21天卡片流

  • 微课模式:将课程打散为一张张独立的 “卡片” (Lesson Card),降低认知负荷。
  • 故事板驱动:可视化 Storyboard 配置流程,像导演一样安排学习剧本。
  • 成长路径:明确的 21天课程地图

📊 数据架构:本地化存储

  • JSON 存档:基于 AppSave 系统的本地化存储,记录 firstLoginDatecurrentStreaktotalLearningSeconds 等核心指标。
  • 数据埋点:自动统计活跃天数与学习时长,为未来的成就系统打下基础。

📱 UI 适配方案:UIRootAdapter

针对“手机宽屏”与“iPad方屏”差异,采用高度锚定缩放策略:

  • iPad 原生保留:在 iPad 比例下不修改任何数据,保持预制体原始显示效果。
  • 手机动态缩放:检测到宽屏时,通过 localScale 强行匹配屏幕高度,并反向延展 sizeDelta.x 扩充逻辑画布。
  • 内容自适应:利用横向逻辑空间的增加,自动展示更多卡片或侧边元素,解决超宽屏“顶天立地”导致的画面被切问题。

功能特点

🎮 核心游戏机制

  • 萤火虫互动系统:21只萤火虫对应21个学习单元
  • 触摸交互:支持点击和拖拽操作
  • 实时预览:触摸萤火虫时显示对应课程内容
  • 进度跟踪:记录学习进度,已学习的萤火虫保持点亮状态

📚 学习内容

  • 拼音基础:单韵母、声母、复韵母、前后鼻韵母
  • 系统学习:按照标准拼音教学顺序安排
  • 巩固复习:定期复习已学内容

🎯 学习进度

项目包含完整的21课拼音学习体系:

  1. aoe - 单韵母学习
  2. iuü - 单韵母扩展
  3. 巩固复习6个单韵母
  4. bpmf - 声母学习
  5. dtnl - 声母扩展
  6. 巩固复习8个声母
  7. gkh - 声母进阶
  8. jqx - 特殊拼读规则
  9. 巩固复习14个声母
  10. zcs - 平舌音
  11. zh ch sh r - 翘舌音
  12. yw - 半元音
  13. 巩固复习23个声母
  14. ai ei ui - 复韵母
  15. ao ou iu - 复韵母扩展
  16. ie üe er - 特殊复韵母
  17. 巩固复习9个复韵母
  18. an en in un ün - 前鼻韵母
  19. ang eng ing ong - 后鼻韵母
  20. 巩固复习前、后鼻韵母
  21. 总复习

🔧 技术特点

  • Unity 3D引擎:跨平台游戏开发
  • 性能优化:场景性能监控系统
  • 异步加载:分帧处理避免卡顿
  • 资源管理:高效的资源加载和释放机制

技术架构

🏗️ 新架构特性(2024年重构)

本项目采用流水线式模块化架构,专为AI协作和快速迭代设计:

流水线式页面管理

  • LessonFlowController:总控管理器,统一调度页面流转
  • ILessonPage接口:标准化页面生命周期(Initialize → StartPage → StopPage → ResetPage)
  • 模块独立性:每个页面完全独立,互不耦合
  • 资源统一管理:AudioSource、UI按钮等共用资源集中分配

AI协作友好设计

  • 设计钩子:代码中嵌入清晰的架构说明注释
  • 一叶知秋:看任何一个文件都能理解整体架构
  • 标准化接口:统一的命名规范和开发模式
  • 快速测试:支持从任意课程页面开始调试(startFromPage参数)

核心组件

新架构组件

  • LessonFlowController:流水线总控管理器
  • Lesson01Page1/2/3:独立的课程页面模块
  • LessonFlowSetupWizard:一键配置工具
  • VoiceRecorder:跨平台录音组件
  • AudioWaveDisplay:实时音波图显示

原有组件

  • FireflyLessonManager:萤火虫课程管理器
  • ScenePerformanceMonitor:场景性能监控
  • AllConst:游戏常量和配置管理
  • AudioManager:音频统一管理

主要系统

  • 流水线课程系统:模块化页面管理,支持快速切换和测试
  • 智能录音系统:支持iOS/Android/PC平台的语音录制和回放
  • 实时音波图:超高灵敏度音量检测和可视化显示
  • 交互系统:触摸事件处理和手势识别
  • 进度系统:学习进度跟踪和状态管理

开发环境

  • Unity版本:Unity 2022.3 LTS或更高版本
  • 平台支持:iOS、Android
  • 开发语言:C#
  • 第三方插件
    • Sirenix Odin Inspector
    • DOTween动画库
    • 各类性能优化插件

项目结构

Assets/
├── Scripts/                    # 核心脚本
│   ├── Manager/               # 管理器类
│   │   ├── LessonFlowController.cs    # 📋 流水线总控(架构核心)
│   │   ├── AudioManager.cs           # 🔊 音频统一管理
│   │   └── ...
│   ├── Interfaces/            # 接口定义
│   │   └── ILessonPage.cs            # 📜 页面标准接口(必读)
│   ├── Lessons/Pages/         # 课程页面模块
│   │   ├── Lesson01Page1.cs          # 📄 第一页(句子+拼音)
│   │   ├── Lesson01Page2.cs          # 📄 第二页(AOE卡片)
│   │   └── Lesson01Page3.cs          # 📄 第三页(跟读录音)
│   ├── Audio/Manager/         # 音频系统
│   │   └── VoiceRecorder.cs          # 🎤 跨平台录音组件
│   ├── UI/                    # UI组件
│   │   └── AudioWaveDisplay.cs       # 🌊 实时音波图
│   ├── Setup/                 # 配置工具
│   │   └── LessonFlowSetupWizard.cs  # 🛠️ 一键配置向导
│   ├── Const/                 # 常量定义
│   └── ARCHITECTURE_PATTERN.md       # 🎯 架构设计文档(AI协作关键)
├── Images/                    # 游戏图片资源
├── Fonts/                     # 字体资源
├── Resources/                 # 可加载资源
│   └── Audio/                # 音频资源
│       ├── lesson01/         # 第一课音频
│       └── 拼音表/           # 拼音音频库
├── Scenes/                    # 游戏场景
└── Plugins/                   # 第三方插件

🚀 快速开始

开发者快速上手

  1. 理解架构:先阅读 Assets/Scripts/ARCHITECTURE_PATTERN.md
  2. 配置环境:使用Unity菜单 Tools → GuGu拼音 → 设置课程流水线
  3. 快速测试:设置 startFromPage = 3 直接测试录音功能
  4. 开始开发:参考现有页面实现,遵循ILessonPage接口

AI模型协作指南

  1. 架构理解:阅读架构文档理解流水线模式
  2. 接口学习:掌握ILessonPage的4个标准方法
  3. 模式复制:按照现有页面模式创建新功能
  4. 钩子识别:寻找代码中的"设计钩子"注释

安装与运行

  1. 使用Unity Hub打开项目
  2. 确保Unity版本为2022.3 LTS或更高
  3. 导入必要的第三方插件
  4. 在Unity中打开 Assets/Scenes/00Agree.unity 场景
  5. 点击播放按钮开始游戏

贡献指南

  1. Fork本项目
  2. 创建功能分支 (git checkout -b feature/AmazingFeature)
  3. 提交更改 (git commit -m 'Add some AmazingFeature')
  4. 推送到分支 (git push origin feature/AmazingFeature)
  5. 开启Pull Request

许可证

本项目采用私有许可证,仅供内部开发使用。

联系方式

  • 开发团队:南京蒲雷坦网络科技有限公司
  • 微信公众号:古古识字
  • 邮箱:[email protected]

🔍 MVC架构详解:初始化流程和题目呈现机制

MVC架构概览

本项目采用严格的MVC(Model-View-Controller)模式,实现完全的职责分离和单向数据流。这个架构特别适合多邻国式的题型驱动学习应用。

┌─────────────────┐    事件通知      ┌─────────────────┐
│                 │ ──────────────> │                 │
│   View Layer    │                 │ Controller Layer│
│   (UI显示)       │ <────────────── │   (流程控制)     │
│                 │    UI更新指令     │                │
└─────────────────┘                  └────────┬───────┘

                                              │ 数据读写

                                    ┌─────────────────┐
                                    │                 │
                                    │   Model Layer   │
                                    │   (纯数据)       │
                                    │                 │
                                    └─────────────────┘

核心架构层级

层级职责依赖关系关键文件
Model纯数据+业务规则不依赖任何层LessonModel.cs, ProgressModel.cs, QuestionModel.cs
View纯显示+用户输入不依赖Model/ControllerQuestionView.cs, ListenAndChooseView.cs, LessonUIView.cs
Controller流程控制依赖Model,控制ViewLessonController.cs
Service工具服务被所有层使用AudioService.cs

🚀 初始化流程详解

1. 系统启动阶段 (Scene Load)

入口点:LessonController.cs:62

csharp
void Start()
{
    InitializeLesson();
}

启动序列:

  1. 单例初始化 (LessonController.cs:46-59)

    • 创建或获取LessonController单例
    • 查找并绑定LessonUIView引用
    • 保证全局只有一个控制器实例
  2. 课程数据创建 (LessonController.cs:77-107)

    csharp
    private void CreateTestLesson()
    {
        lessonModel = new LessonModel(1, "拼音第一课");
        
        // 创建测试题目1: "bā"
        var question1 = new QuestionModel(QuestionType.ListenAndChoose, "bā");
        question1.options.Add(new OptionModel("bā"));
        question1.options.Add(new OptionModel("pá"));
        // ... 更多选项
        lessonModel.questions.Add(question1);
    }
  3. 进度模型初始化 (LessonController.cs:72)

    csharp
    progressModel = new ProgressModel(lessonModel.GetTotalQuestions());

2. 数据组合阶段

Model层数据结构:

  • LessonModel: 课程容器

    • lessonId: 课程编号
    • lessonName: 课程名称
    • questions: 题目列表
    • 业务方法:GetTotalQuestions(), GetQuestion(index)
  • QuestionModel: 单题数据

    • questionType: 题型枚举(听音选字、配对等)
    • correctAnswer: 正确答案
    • options: 选项列表
    • audioClip: 对应音频
    • 验证方法:ValidateAnswer()
  • ProgressModel: 进度跟踪

    • currentQuestionIndex: 当前题目索引
    • correctCount: 正确计数
    • totalQuestions: 总题数
    • 计算方法:GetProgress(), GetAccuracy(), IsComplete()

🎯 第一道题呈现流程

1. 题目显示准备 (LessonController.cs:131-161)

csharp
private void ShowCurrentQuestion()
{
    // 1. 检查是否完成
    if (progressModel.IsComplete()) {
        CompleteLesson();
        return;
    }
    
    // 2. 清理上一题
    ClearCurrentQuestion();
    
    // 3. 从Model获取当前题目数据
    var questionModel = lessonModel.GetQuestion(progressModel.currentQuestionIndex);
    
    // 4. 根据题型创建对应View
    var questionGO = InstantiateQuestionByType(questionModel.questionType);
    currentQuestionView = questionGO.GetComponent<QuestionView>();
    
    // 5. 初始化View并绑定事件
    currentQuestionView.Initialize(questionModel);
    currentQuestionView.OnAnswerSelected += OnAnswerSelected;
    currentQuestionView.OnAnswerSubmitted += OnAnswerSubmitted;
    
    // 6. 更新UI进度
    UpdateProgress();
}

2. View初始化过程 (ListenAndChooseView.cs:56-87)

csharp
public override void Initialize(QuestionModel model)
{
    base.Initialize(model);
    currentAudioClip = model.audioClip;
    StartCoroutine(AutoPlayAudioOnStart()); // 自动播放音频
}

protected override void SetupUI()
{
    correctAnswer = questionModel.correctAnswer;
    
    // 遍历选项,设置UI内容
    for (int i = 0; i < optionCards.Count && i < questionModel.options.Count; i++)
    {
        var option = questionModel.options[i];
        var card = optionCards[i];
        
        card.label.text = option.text;  // 设置选项文字
        card.cardObject.SetActive(true);
        
        if (option.text == correctAnswer) {
            correctIndex = i;  // 记录正确答案索引
        }
        
        ResetCardVisual(card);  // 重置视觉状态
    }
}

3. 用户交互响应链

事件流程:用户点击选项 → 显示CHECK按钮 → 点击CHECK → 验证答案 → 显示反馈

  1. 选项点击 (ListenAndChooseView.cs:117-134)

    csharp
    private void OnOptionSelected(int index)
    {
        if (isAnswerLocked) return;
        
        selectedIndex = index;
        ShowSelectedEffect(optionCards[index]);  // 视觉反馈
        NotifyAnswerSelected();  // 通知Controller
    }
  2. Controller响应 (LessonController.cs:191-197)

    csharp
    private void OnAnswerSelected()
    {
        if (uiView != null) {
            uiView.ShowCheckState(OnCheckButtonClicked);  // 显示CHECK按钮
        }
    }
  3. CHECK按钮处理 (LessonController.cs:199-205)

    csharp
    private void OnCheckButtonClicked()
    {
        if (currentQuestionView != null) {
            currentQuestionView.SubmitAnswer();  // 触发验证
        }
    }
  4. 答案验证 (ListenAndChooseView.cs:147-150)

    csharp
    protected override bool ValidateAnswer()
    {
        return selectedIndex == correctIndex;  // 纯业务逻辑验证
    }
  5. 结果处理 (LessonController.cs:207-227)

    csharp
    private void OnAnswerSubmitted(bool isCorrect)
    {
        progressModel.AnswerQuestion(isCorrect);  // 更新Model
        
        if (isCorrect) {
            uiView.ShowCorrectState(OnContinueButtonClicked);  // 正确UI
        } else {
            uiView.ShowIncorrectState(OnRetryButtonClicked);   // 错误UI
        }
        
        OnQuestionComplete?.Invoke(isCorrect);  // 事件通知
    }

🔄 状态流转机制

按钮状态管理 (LessonUIView.cs:72-88)

系统通过统一的按钮状态机制管理用户界面:

csharp
public enum ButtonState
{
    NormalNext,    // 普通下一步
    Unselected,    // 未选择状态
    Selected,      // 已选择(显示CHECK)
    Incorrect,     // 答错(显示RETRY)
    Correct,       // 答对(显示CONTINUE)
    Disabled       // 禁用状态
}

状态转换流程:

Disabled → Unselected → Selected → (Correct|Incorrect) → Unselected

进度计算和更新

进度模型 (ProgressModel.cs:36-51)

csharp
public float GetProgress()
{
    if (totalQuestions == 0) return 0f;
    return (float)currentQuestionIndex / totalQuestions;
}

public float GetAccuracy()
{
    if (currentQuestionIndex == 0) return 0f;
    return (float)correctCount / currentQuestionIndex;
}

🏗️ 架构优势

  1. 严格分离:Model/View/Controller职责清晰,互不依赖
  2. 易于测试:每层可独立单元测试
  3. 易于扩展:新题型只需继承基类,遵循协议
  4. 统一流程:所有题型都走相同的数据流
  5. 可维护性:修改UI不影响逻辑,修改逻辑不影响UI

🚀 快速扩展新题型

要添加新题型(如拖拽配对),只需:

  1. 扩展Model:在QuestionType枚举中添加新类型
  2. 创建View:继承QuestionView基类,实现抽象方法
  3. 配置Controller:在InstantiateQuestionByType()中添加case分支
  4. 创建预制体:设计UI并配置到LessonController

整个过程遵循相同的MVC模式,保证代码一致性和可维护性。


让孩子在游戏中快乐学习拼音!


Unity Duolingo 风格交互复刻开发白皮书

1. 核心设计宗旨 (Design Philosophy)

本项目的最高准则是 "Juicy UI" (多汁的 UI)。所有可交互元素必须具备物理反馈。

  • 拒绝对话框式弹窗:尽量使用底部抽屉 (Bottom Sheet) 或全屏推入。
  • 拒绝生硬切换:所有状态变化必须有过渡动画 (Tween)。
  • 视觉欺骗:通过 2D 图层的 Y 轴位移模拟 3D 按压感。

2. 美术资源需求清单 (Asset Requirements)

为了达到 1:1 的效果,美术资源必须严格按照**“三明治结构”**拆分。请将以下需求发给你的 UI 设计师。

2.1 核心控件:通用果冻按钮 (The Jelly Button)

Duolingo 的按钮不是一张图,而是由两部分组成的。

  • 资源 A:顶层表面 (Face)
    • 格式:PNG (带透明通道)
    • 形状:圆角矩形,圆角半径极大(通常是高度的 50%)。
    • 颜色:亮色(如亮绿 #58CC02)。
    • 高光:顶部边缘有微妙的亮白色内描边(增加塑料质感)。
  • 资源 B:底层阴影/厚度 (Edge/Shadow)
    • 格式:PNG
    • 形状:同上,完全一致。
    • 颜色:深色(如深绿 #2B8500)。
    • 用途:垫在 A 的下面,用于在 A 抬起时露出“侧边厚度”。

【关键要求】:所有 UI 面板、卡片、按钮,必须全部切成 9-Slice (九宫格) 格式,确保在 Unity 中任意拉伸圆角不失真。

2.2 图标与插画

  • 格式:SVG (推荐使用 Vector Graphics 包导入) 或 高清 PNG。
  • 风格:粗描边 (Stroke width = 3px~5px),扁平化,无渐变或微渐变。

2.3 字体

  • 主要字体:寻找类似 Feather Bold 或 DIN Round 的圆体字。
  • 备选:Nunito (Google Fonts, Bold & ExtraBold)。

3. 交互技术细节 (Interaction Mechanics)

3.1 核心:3D-in-2D 按钮逻辑 (DoTween 实现)

这是多邻国的灵魂。按钮点击不是缩放,而是 Y 轴下沉。

  • 组件结构
    [Button_Root] (空物体,挂载 Button 脚本, Height = 60)
     ├── [Shadow_Layer] (Image, Color = Dark, Anchor = Stretch)
     └── [Face_Layer]   (Image, Color = Light, Anchor = Stretch, Pivot Y=0.5)
          └── [Content] (Text/Icon)
  • 初始状态设定Face_LayerAnchoredPosition.y 设置为 12 (即厚度)。Button_Root 的高度要包含这额外的 12px。
  • 交互脚本 (DoTween)
    csharp
    // 必须引用的命名空间
    using DG.Tweening;
    
    public class JuicyButton : MonoBehaviour, IPointerDownHandler, IPointerUpHandler
    {
        [Header("References")]
        public RectTransform faceLayer;
        public Image faceImage; // 用于改色
    
        [Header("Settings")]
        public float pressDepth = 12f; // 下压深度,必须等于初始 Y 偏移量
        public float duration = 0.1f;
        
        // 状态机,防止动画冲突
        private bool _isPressed = false;
    
        public void OnPointerDown(PointerEventData eventData)
        {
            if (!interactable) return;
            _isPressed = true;
    
            // 1. 瞬间下压 (或极快) - 模拟受力
            faceLayer.DOKill(); // 清除之前的动画
            faceLayer.DOAnchorPosY(0f, 0.05f).SetEase(Ease.OutQuad);
    
            // 2. 颜色变暗 (模拟被遮挡光线,可选)
            // faceImage.DOColor(pressedColor, 0.05f);
    
            // 3. 触觉反馈 (必做!)
            HapticFeedback.Light(); 
        }
    
        public void OnPointerUp(PointerEventData eventData)
        {
            if (!_isPressed) return;
            _isPressed = false;
    
            // 1. 弹性回弹 (这是精髓)
            // OutElastic 带来“果冻”般的抖动感
            faceLayer.DOKill();
            faceLayer.DOAnchorPosY(pressDepth, 0.3f).SetEase(Ease.OutElastic, 0.8f);
    
            // 2. 触发点击逻辑
            // 建议延迟 0.1s 执行逻辑,让用户看清回弹动画
            DOVirtual.DelayedCall(0.1f, () => onClick.Invoke());
        }
    }

3.2 列表选项卡 (Selection Card)

针对你上传的截图,选项卡有三种状态。

  • Normal (未选中):
    • Face: 白色
    • Shadow: 浅灰 (#E5E5E5)
    • Border: 浅灰 (#E5E5E5) 2px 宽
  • Selected (选中):
    • Face: 极淡蓝 (#DDF4FF)
    • Shadow: 亮蓝 (#1CB0F6)
    • Border: 亮蓝 (#1CB0F6) 2px 宽
    • 文本: 变蓝
  • Wrong (错误 - 答题模式用):
    • Face: 极淡红
    • Shadow: 红色
    • Border: 红色

切换动画:当用户点击另一个选项时,不要瞬间切换。

csharp
// 选中动画
transform.DOPunchScale(new Vector3(0.05f, 0.05f, 0), 0.2f, 10, 1); // 轻微缩放震动
borderImage.DOColor(blueColor, 0.2f);
faceImage.DOColor(lightBlueColor, 0.2f);

3.3 进度条连贯性 (Progress Bar)

逻辑:进度条增长不能是线性的,要有“刹车感”。 DoTween 写法:

csharp
// value 是 0 到 1
progressBarFill.DOFillAmount(targetValue, 0.5f).SetEase(Ease.OutBack);

注意:OutBack 会让进度条稍微冲过头一点点再缩回来,这是非常细腻的“多邻国味”。

4. 衔接与转场 (Transitions & Flow)

多邻国没有“黑屏加载”。所有界面都是滑进来或弹出来的。

4.1 页面入场 (Page Enter)

假设进入一个新的答题卡片。

  • 动画:从屏幕右侧滑入。
  • DoTween:
    csharp
    rectTransform.anchoredPosition = new Vector2(Screen.width, 0); // 初始在右侧外
    rectTransform.DOAnchorPosX(0, 0.4f).SetEase(Ease.OutCubic); // 减速滑入

4.2 底部抽屉 (Bottom Sheet / Feedback)

当用户点击 "CHECK" (检查) 后,底部会弹出一个结果栏(正确是绿色,错误是红色)。

  • 动画:从屏幕底部迅速升起。
  • 连贯性要求
    1. 点击 CHECK 按钮 -> 按钮下压。
    2. 播放音效 ("Ding" or "Womp").
    3. 底部抽屉 DOAnchorPosY 升起。
    4. 同时,角色 (Duo) 播放对应动画(开心跳跃 或 失望哭泣)。

5. 角色系统联动 (Character System)

为了让“壳”不仅是 UI,你需要一个 CharacterReactionController

  • 状态定义:
    • Idle (眨眼,轻微呼吸)
    • Happy (回答正确)
    • Sad (回答错误)
    • Talking (对话泡泡出现时)
  • 实现:使用 Spine 最好,如果没有,使用序列帧或简单的 DoTween 缩放/旋转。
  • 例子:回答正确时,让猫头鹰跳一下。
    csharp
    characterRect.DOJump(characterRect.anchoredPosition, 30f, 1, 0.5f);

6. 音效与震动 (Audio & Haptics) - 灵魂所在

没有声音的多邻国是也是没有灵魂的。

  • SFX 清单
    • Click_Normal: 短促的木头敲击声。
    • Click_Toggle: 类似于气泡破裂的轻响。
    • Success_Chime: 标志性的上行三和弦。
    • Error_Buzz: 沉闷的低音。
  • 震动 (Haptics):使用 CandyCoded.Haptic 或 iOS 原生插件。
    • Light: 普通按钮点击。
    • Medium: 选中答案。
    • Heavy/Double: 答错时的惩罚反馈。

7. 总结:开发验收标准

在你的 Unity 工程 Review 时,请检查以下几点:

  1. 按压感:点击任何可点击物体,必须看到它“凹”下去了。
  2. 松手回弹:松开手指时,必须看到它弹回原位,且带有一点点 Q 弹。
  3. 声音同步:按下瞬间必须有声音,不能有延迟。
  4. 无死板动画:所有位移、缩放,都必须使用 Ease Function (推荐 OutBack, OutElastic, OutQuad),严禁使用 Linear

8. Lottie 动画集成指南 (Vector Animation)

本项目集成了 unity-rlottie 插件以支持高质量的矢量动画。

✅ 最佳实践配置

为了确保 Lottie 动画在 Unity 中 高清方向正确,请遵循以下规范:

  1. 组件使用:使用 AnimatedImage (Namespace: LottiePlugin.UI)。
  2. 纹理设置 (关键)
    • Texture Width/Height:必须设置为 10242048 (默认为128会导致模糊)。
    • 即使是矢量文件,插件也是通过渲染纹理(RenderTexture)来实现的,因此分辨率决定了清晰度。
  3. 坐标修正 (关键)
    • Unity (左下原点) 与 Lottie (左上原点) Y轴相反。
    • 必须将 RectTransform 的 Scale Y 设置为 -1 以修正倒置问题。
  4. 预制体
    • 推荐使用 Assets/Prefabs/Lottie/LottiePlayer 预制体,已预设好上述参数。

南京蒲雷坦网络科技有限公司