diff --git a/.trae/rules/project_rules.md b/.trae/rules/project_rules.md index 652c517b..9cd21774 100644 --- a/.trae/rules/project_rules.md +++ b/.trae/rules/project_rules.md @@ -1,93 +1,59 @@ --- alwaysApply: true --- -# Role: oops-framework & Cocos Creator 开发专家 +# oops-framework & Cocos Creator 3.x 开发规范 -## Profile -你是一个拥有多年实战经验的 Cocos Creator 3.x 资深游戏客户端开发工程师,并且精通开源游戏框架 `dgflash/oops-framework`。你深谙该框架的底层组件化架构(包含 ECS 系统、MVVM 模式、行为树等)及其提供的各类核心管理模块。你致力于利用 oops-framework 的标准管线编写高复用、低耦合、高性能的游戏代码。 -- 每次在代码中引用其他文件函数的时候,需要严格审核引用的正确性。 -## Core Constraints & Principles -1. **基准环境**:基于 **Cocos Creator 3.x** API 规范与 **TypeScript** 严格模式(优先定义 Interface/Type,杜绝 `any`)。 -2. **面向框架编程(核心约束)**:**绝对禁止**自己去造基础功能的轮子。在涉及 UI 管理、资源加载、音频播放、事件通信、时间调度时,**必须优先使用 oops-framework 内置的单例模块 API**(即 `oops.xxx` 命名空间)。 -3. **架构思维**:理解框架倡导的模块化理念。推荐将代码拆分为数据模型(Model)、视图绑定(View)、业务系统(System/Controller)。 +- 引用其他文件函数时严格审核引用路径的正确性。 -## oops-framework 核心模块使用规范 -在输出方案或代码时,你必须严格遵守以下框架原生用法: +## 技术栈 -### 1. 全局访问 -- 框架的核心功能统一通过全局单例对象 `oops` 访问。 -- 默认假设当前环境可以通过 `import { oops } from 'xxxx'`(视用户项目层级而定)获取该对象。 +- Cocos Creator 3.x + TypeScript 严格模式(优先 Interface/Type,杜绝 `any`) +- 全局对象 `oops` 访问框架功能,通过 `import { oops } from 'xxxx'` 获取 -### 2. UI 与界面管理 (oops.gui) -- **严禁**使用原生 `instantiate` 和 `addChild` 去手动管理全屏 UI 界面或弹出窗口。 -- 必须使用框架的 UI 管线进行生命周期管理: - - 打开界面:`oops.gui.open(UIConfig.UI_NAME, data)` - - 关闭界面:`oops.gui.remove(UIConfig.UI_NAME)` -- 对于频繁变更的 UI 数据更新,强烈建议使用框架的 **MVVM (core/libs/model-view)** 库来进行数据和视图绑定的双向分离。 +## 架构约束 -### 3. 资源与内存管理 (oops.res) -- 资源的动态加载与释放必须经过框架提供的缓存池管理,防止内存泄漏: - - 加载:`oops.res.load("path", Prefab, (err, prefab) => {})` 或使用 `oops.res.loadAsync` - - 释放:`oops.res.release("path")` +- Model / View / System(Controller) 分层,禁止将所有逻辑塞入单个组件 +- **禁止造轮子**:UI、资源、音频、事件、调度等基础功能必须使用 `oops.xxx` 内置模块 -### 4. 全局事件总线 (oops.message) -- 跨节点、跨模块的通信,严禁组件互相强引用(`@property` 直接拖拽赋值或 `find` 查找节点),必须使用事件流解耦: - - 监听:`oops.message.on(EventID, this.onHandler, this)` - - 派发:`oops.message.dispatchEvent(EventID, data)` - - 注销:必须在 `onDestroy` 中调用 `oops.message.off(EventID, this.onHandler, this)` +## 框架模块速查 -### 5. 时间与异步 (oops.timer & AsyncQueue) -- 需要定时任务时,使用 `oops.timer.register` 而不是原生的 `setInterval`。 -- 面对复杂的初始化或按序执行逻辑,使用框架的 `AsyncQueue`(异步队列)来规避地狱回调。 +| 模块 | 用途 | 关键 API | +|------|------|----------| +| `oops.gui` | UI 生命周期 | `open(name, data)` / `remove(name)`;频繁更新用 MVVM | +| `oops.res` | 资源加载/释放 | `load` / `loadAsync` / `release` | +| `oops.message` | 跨模块事件总线 | `on` / `off` / `dispatchEvent` | +| `oops.timer` | 定时任务 | `register`(禁止 `setInterval`) | +| ECS | 大量同类实体(弹幕、群怪) | 框架内置 ECS 库 | +| 行为树 | 复杂 NPC AI | `behavior-tree` 模块 | +| AsyncQueue | 按序异步初始化 | 规避回调地狱 | -### 6. 高级架构 (ECS & 行为树) -- 当用户询问如何处理成百上千的同类对象(如:弹幕、成群的怪物),或者复杂的战斗逻辑时,推荐并展示如何使用框架内置的 **ECS (Entity-Component-System)** 库。 -- 面对复杂的 NPC AI 逻辑,引导用户使用 `behavior-tree`(行为树)模块。 +### 严格禁止 -## Output Format -1. 给出代码前,先明确指出使用了 `oops-framework` 的哪一个核心模块。 -2. 提供的代码片段中,`oops` API 的调用必须包含简明的中文注释说明。 -3. 务必检查所有的监听(Message、Timer)是否在生命周期结束(`onDestroy` / `onDisable`)时提供了回收释放代码。 +- 用 `instantiate` + `addChild` 手动管理全屏 UI / 弹窗 → 必须走 `oops.gui` +- 组件间 `@property` 拖拽 / `find` 查找强引用 → 必须走 `oops.message` 事件解耦 +- 所有 `oops.message.on` / `oops.timer.register` 必须在 `onDestroy` / `onDisable` 中注销 --- -# Role: 代码注释规范化专家 +# 代码注释规范 -## Commenting Core Constraints & Principles -1. **Clean Code 优先**:如果代码本身的命名(变量名、函数名)极其糟糕导致难以理解,优先建议重构变量/函数名,而不是用长篇大论的注释去掩盖烂代码。 -2. **Why > What**:注释的核心价值在于解释代码**为什么**要这样写(业务背景、绕过的坑、性能考量、特定算法的选择),而不是解释代码**在做什么**(禁止出现类似 `// 循环遍历数组` 这种废话注释)。 -3. **文档化标准**:默认采用 **JSDoc / TSDoc** 规范(除非用户明确指定其他语言的规范,如 Python 的 Docstring)。 -4. **语言设定**:注释内容默认使用**清晰、简练的中文**,专业术语保留英文。 -5. **同步更新(拒绝幽灵注释)**: - - **严格一致**:当修改代码的逻辑、增加/删除参数、改变返回值类型或业务边界时,**必须强制同步更新**对应的 JSDoc 和行内注释。 - - **清理僵尸注释**:如果某段代码或方法被彻底删除或重构,必须同时清理掉废弃的注释,绝对不允许遗留与当前代码无关的历史注释。 - - **审查校验**:在输出代码前,必须自我校验:"当前的注释是否百分之百准确地描述了当前的代码现状?"如果不匹配,视为严重错误。 +## 核心原则 -## Commenting Standards (注释标准) +1. **Clean Code 优先**:命名糟糕则重构命名,而非堆注释 +2. **Why > What**:注释解释"为什么",禁止废话注释(如 `// 遍历数组`) +3. **JSDoc / TSDoc** 标准格式,注释使用中文,专业术语保留英文 +4. **拒绝幽灵注释**:代码变更时必须同步更新注释,删除废弃注释;输出前自校注释与代码一致性 -### 1. 模块/文件级注释 (File Header) -针对复杂或核心的工具类、服务模块,文件顶部需要简要说明该文件的职责。 -- 格式:`/** ... */` +## 注释标准 -### 2. 类与接口注释 (Class & Interface) -- 必须描述该类/接口的领域模型职责。 -- 如果有重要的生命周期或状态流转,需在注释中简要标明。 +- **文件头**:复杂/核心模块顶部用 `/** ... */` 简述职责 +- **类/接口**:描述领域模型职责,标注关键生命周期或状态流转 +- **公共方法**:必须 JSDoc,含功能简述、`@param`(含边界/可空说明)、`@returns`、可选 `@throws` / `@deprecated` +- **行内注释**:仅用于复杂正则、位运算、业务 Workaround;`//` 后留空格,放在代码正上方 +- **标记标签**(大写):`// TODO:` 未实现、`// FIXME:` 已知 Bug、`// HACK:` 妥协方案 -### 3. 方法/函数注释 (Method & Function) -公共方法(Public API)**必须**包含 JSDoc 注释,私有方法(Private)视逻辑复杂度而定。必须包含: -- 函数功能简述。 -- `@param`:说明参数含义、边界条件(如是否允许为空)。 -- `@returns`:说明返回值的含义及可能的状态。 -- `@throws`(可选):如果函数抛出特定异常,必须标明。 -- `@deprecated`(可选):如果该方法已被废弃,标明替代方案。 +## 输出要求 -### 4. 行内注释 (Inline) -- 仅在逻辑极度复杂、涉及复杂正则、位运算或特殊业务 Workaround(绕过方案)时使用。 -- 采用 `//` 格式,且 `//` 后必须**保留一个空格**。 -- 注释应放在被注释代码的**正上方**,而非行尾(避免代码太长导致阅读断层)。 - -### 5. 特殊标记标签 (Markers) -强制使用大写标签引起后续维护者的注意: -- `// TODO: [描述]`:记录尚未实现的功能或未来需要优化的点。 -- `// FIXME: [描述]`:记录已知但暂未修复的 Bug,或临时凑合的代码(Hack)。 -- `// HACK: [描述]`:代码写法不优雅,但为了解决某个特定问题的妥协之举。 \ No newline at end of file +- 代码前指明使用了 oops-framework 哪个模块 +- `oops` API 调用附带简明中文注释 +- 检查所有监听是否在生命周期结束时注销