# HKUnityTools
**Repository Path**: JingChanChangFan/hk_-unity-tools
## Basic Information
- **Project Name**: HKUnityTools
- **Description**: Unity的工具集(基于QFramework和Dotween)
- **Primary Language**: C#
- **License**: MIT
- **Default Branch**: master
- **Homepage**: None
- **GVP Project**: No
## Statistics
- **Stars**: 45
- **Forks**: 16
- **Created**: 2021-08-24
- **Last Updated**: 2025-06-26
## Categories & Tags
**Categories**: Uncategorized
**Tags**: Unity, 工具集, tools, UnityTools
## README
# HKUnityTools介绍:
HKUnityTools 是我们团队在 Unity 项目中开发的工具集,涵盖编辑器和运行时功能,旨在优化工作流程并降低开发负担。若有任何疑问,欢迎联系 `QQ : 511919078` `微信 : JingChanChangFan`
本项目部分模块基于:
* QFramework v1.0.203
* Dotween v1.2.765
HKUnityTools更新日志:https://kdocs.cn/l/caGHelWvXD0f
团队案例:https://kdocs.cn/l/cdU0cffoGtxL
**(号外!我们团队位于青岛,专注于XR、虚拟仿真及数字化展项等项目开发,现诚邀开发者加入。感兴趣请私信或联系QQ和微信!)**

HKUnityTools Gitee地址:[传送门](https://gitee.com/JingChanChangFan/hk_-unity-tools)
QFramework Github地址:[传送门](https://github.com/liangxiegame/QFramework)
In-game Debug Console Github地址:[传送门](https://github.com/yasirkula/UnityIngameDebugConsole)
# 初始设置(敲重点):
HKUnityTools 基于 QFramework 实现扩展功能。开发和测试时默认采用 HK_DefaultArchitecture 框架。在其他项目中引入 HKUnityTools 时,务必替换为对应项目的框架(Architecture),并注册 HKUnityTools 的系统层、模型层和工具层,否则相关功能将无法正常使用
对于新建的 Unity 工程,可借助“自动化生成项目脚本模板”工具,依据 QFramework 的规则生成初始化模板,生成后在全局设置里更改当前框架(Architecture)。
## 1.全局设置:
提供专门的全局设置窗口,方便管理和切换 HKUnityTools 应用的框架(Architecture),并配置各类工具的启用状态。
**使用方式:**
1. 在 Unity 编辑器菜单栏依次点击 `HKTools -> GlobalSettings...`。
2. 弹出窗口会自动检测工程中所有继承自 `Architecture` 的框架类,通过下拉菜单选取当前项目适用的 Architecture。
3. 点击 “设置为当前 Architecture” 按钮,完成 HKTools 使用框架的重新设定,同时自动更新 `HK_ArchitectureProvider.cs` 脚本文件。

4. 也可手动修改 `Assets/HKTools/GlobalSettings/HK_ArchitectureProvider.cs` 脚本文件来设定框架。
```csharp
///
/// HKTools 框架提供工具
///
public static class HK_ArchitectureProvider
{
static IArchitecture architecture;
///
/// 获取当前项目的架构实例,确保在第一次访问时进行初始化。
///
public static IArchitecture Architecture
{
get
{
// 懒加载架构实例
if (architecture == null)
{
SetArchitecture();
}
return architecture;
}
}
///
/// 设置当前项目的架构实例。
///
static void SetArchitecture()
{
// 修改此处,设定为当前项目 Architecture 框架
architecture = HKTools.HK_DefaultArchitecture.Interface;
}
}
```
--------------------------------------------------------------------------------------------------------------------------------------------
## 2.自动化生成项目脚本模板:
可使用 `AutoGenerateTemplate` 工具,依据 QFramework 框架规则,自动生成项目脚本模板和基础文件夹结构,帮助开发者快速搭建项目架构,主要功能如下:
* **快捷使用**:在菜单栏找到 `HKTools -> Auto Generate Template (自动化生成项目模板)` 选项并点击,可自定义 Architecture 框架名称,未指定则默认使用当前工程 ProductName。在打开窗口点击 “项目模板生成” 按钮,在弹出提示窗口点击 “确认” 即可自动生成。
* **自动生成文件夹结构**:在项目 `Assets` 目录下创建 `_Scripts` 文件夹及其子文件夹,包括 `Commands`、`Events`、`Models`、`Systems`、`ViewControllers`。
* **自动生成脚本模板**:根据项目名称和预定义模板,生成以下脚本文件:
* 项目架构脚本:`[项目名]_Architecture.cs`,继承自 QFramework 的 Architecture,负责注册模型层、系统层等。
* 控制器通用基类脚本:`Controller.cs`,视图层基类,提供对项目架构的引用。
* 初始化数据模型层脚本:`IInitModel.cs`,定义初始化数据模型层接口和实现类。
* 运行时数据模型层脚本:`IRuntimeModel.cs`,定义运行时数据模型层接口和实现类。
* 全局事件脚本:`Events_Global.cs`,声明全局事件和消息。
* 音频管理系统层脚本:`IAudioSystem.cs`,定义音频管理系统接口和实现类。
* **注意事项**:
* 避免重复生成:自动检测 `Assets` 根目录下是否存在 `_Scripts` 或 `_Script` 文件夹,存在则取消操作。
* 项目名称规范:自定义 Architecture 名称会进行合法性过滤,移除数字开头及非法字符;未指定则根据当前工程 ProductName 命名,需确保 Unity 项目名称正确设置。

------------------------------------------------------------------------------------------------------------------------------------------
# 运行时功能:
## 1. HK_FreeCam:
**功能描述:**
HK_FreeCam 是一款轻量级的运行时摄像机控制系统,为开发调试阶段设计的场景漫游预览工具。主要功能包括:
* 全自由度摄像机控制:支持 WASD 三维移动、鼠标右键视角旋转和滚轮视野缩放
* 动态加速机制:按住 Shift 键可实现移动加速(默认加速倍率为 2x)
* 俯仰角限制:防止摄像机翻转(默认俯仰角范围:-45° 至 +45°)
* 即插即用:无需复杂配置,移除后无残留依赖
**使用方式:**
* 将 `HK_FreeCam.cs` 脚本添加到某个物体或主摄像机上(如`MainCamera`)。
* 调整 `HK_FreeCam` 组件上的的参数,如下:
| 参数名 | 类型 | 默认值 | 说明 |
| ------------ | ------- | -------- | -------------- |
| Move Speed | float | 10 | 移动速度 |
| Rotate Speed | float | 300 | 视角旋转灵敏度 |
| X Axis Range | Vector2 | (-45,45) | 俯仰角度限制 |
* 运行时,按住 W、A、S、D 键,进行前后左右移动。
* 运行时,按住 Q、E 键进行上下移动。
* 运行时,按住 Shift 键,进行移动加速。
* 运行时,按住 鼠标右键并移动鼠标,进行视角旋转。
* 运行时,滑动 鼠标滚轮,进行视野缩放。
* 开发调试阶段后,可将 `HK_FreeCam.cs` 脚本移除。
**外部依赖:**
* 无
------------------------------------------------------------------------------------------------------------------------------------------
## 2. HK_TargetCam(基于 QFramework 架构):
**功能描述:**
HK_TargetCam 是一套多功能的摄像机多目标管理系统,提供灵活的相机控制方案,支持多种目标类型,可根据目标类型进行相机切换,主要功能如下:
多目标切换,各目标类型及切换效果如下:
* **RotTarget**:控制 Camera 围绕 Target 旋转、缩放,并可设置旋转边界。
* **AreaTarget**:在 Target 设定的区域内,实现 Camera 的自由平移与缩放。
* **FollowTarget**:Camera 跟随 Target 移动,同时支持围绕 Target 的旋转与缩放。
* **BirdViewTarget**:在 Target 设定区域内,提供 Camera 的俯仰与缩放控制,并切换至正交视角。
运行时控制功能:
* 通过 Command 指令,可进行切换目标。
* 通过 Command 指令切换目标时,可配置以下参数:
* Camera 缩放速度
* Camera 移动速度
* 俯仰角限制
* 目标切换动画时间
* 是否冻结操控
* 通过 Event 事件,可订阅目标切换开始/完成事件。
* 通过 Query 查询指令,可查询当前目标。
* 支持闪现/眨眼效果的目标切换。
* 支持可视化编辑,可在 Scene 视窗中进行目标编辑。

**使用方式:**
* 在当前项目的 Architecture 中注册 `IHK_TargetCamSystem`:
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
this.RegisterSystem(new HK_TargetCamSystem());
}
}
```
* 删除场景中默认的 `Main Camera`,将 `TargetCamera` 预设体拖入场景。
* 在 Scene 视窗右上角开启 Gizmos 单选按钮,本工具可视化编辑基于 Gizmos 绘制。

* 根据项目需求,在场景中添加 `RotTarget`、`AreaTarget`、`FollowTarget`、`BirdViewTarget`,可通过拖拽预设体快速编辑。
* 编辑 `HK_RotTarget`、`HK_AreaTarget`、`HK_FollowTarget`、`BirdViewTarget` 的目标类型(`TargetType`),可点击 “根据物体名称,添加 Target 类型” 按钮,根据选中物体名称自动添加相应 `TargetType`。

* 目标类型(`TargetType`)是本工具的核心属性之一,系统将根据此属性来进行目标切换。为确保工具的正常运行,请务必保证在同一场景下该属性的唯一性。若发现重复设置,系统将发出警告提示。

* 对场景中各目标的 `HK_RotTarget`、`HK_AreaTarget`、`HK_FollowTarget`、`HK_BirdViewTarget`组件,调整其各项属性,如 FOV(视场角)、默认距离等参数,以满足项目需求。
* 对场景中的 `TargetCamera` 物体的 `HK_TargetCamera` 组件,进行初始化参数调整。
* 若 `HK_TargetCamera` 组件指定了 `initTarget` (初始化目标点),则运行后 `TargetCamera` 会自动切换到 `initTarget` 对应的目标。
* 运行时,可发送 `CMD_SetMoveAndZoomSpeed` 指令(并传入对应参数)设置 Camera 默认的 MoveSpeed(默认值为1.5)和 ZoomSpeed(默认值为3)。
```csharp
// 设置相机的移动速度和缩放速度
this.SendCommand(new CMD_SetMoveAndZoomSpeed(1.5f, 3));
```
* 运行时,可发送 `CMD_SetPitchAngle` 指令(并传入对应参数)设置 Camera 的俯仰角范围。
```csharp
// 设置相机的俯仰角范围
this.SendCommand(new CMD_SetPitchAngle(5, 85));
```
* 运行时,可发送 `CMD_SetTargetChangeTime` 指令(并传入对应参数)设置 Camera 切换目标的运动市场。
```csharp
// 设置相机切换目标的运动市场为2秒
this.SendCommand(new CMD_SetTargetChangeTime(2f));
```
* 运行时,可发送 `CMD_SetFreezeMode` 指令(并传入true/false)对 TargetCamera 进行冻结/解冻。
```csharp
// 冻结相机
this.SendCommand(new CMD_SetFreezeMode(true));
// 解冻相机
this.SendCommand(new CMD_SetFreezeMode(false));
```
* 运行时,可发送 `CMD_ChangeCamTarget` 指令(并传入对应参数)进行 Camera 目标切换。
```csharp
// 相机切换至 RotTarget_01
this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_01));
```
* 可通过 `SetUsingFlash` 链式方法,设置相机目标切换为闪现方式(默认启用眨眼特效,若不启用则传入false)。
```csharp
// 相机切换至 RotTarget_01,使用闪现的方式
this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_01).SetUsingFlash());
```
* 运行时,可发送 `Query_GetCurrentTarget` 查询指令,查询当前目标。
```csharp
// 获取当前相机的目标类型
HK_TargetEnum targetType = this.SendQuery(new Query_GetCurrentTarget());
```
* 可订阅事件,在摄像机目标切换前后进行响应:
* 订阅 `Event_SwitchTargetBegin` 事件,当目标切换开始时接收到该事件。
* 订阅 `Event_SwitchTargetEnd` 事件,当目标切换完成后接收到该事件。
* 具体用法,可参考 Test_UseTargetCam 脚本。
```csharp
using UnityEngine;
using QFramework;
using DG.Tweening;
using HKTools;
using UnityEngine.UI;
///
/// Camera多目标切换管理工具,测试脚本
///
public class Test_UseTargetCam : HKTargetCam_BaseController
{
// 相机状态及设置
[SerializeField] Text tips_Txt;
[SerializeField] Toggle toggle_FreezeCam;
[SerializeField] Button btn_QueryTarget;
[SerializeField] Slider slider_TargetChangeTime;
[SerializeField] Text txt_TargetChangeTime;
[SerializeField] Button btn_Ensure;
// 正常切换方式的按钮
[SerializeField] Button btn_RotTarget01;
[SerializeField] Button btn_RotTarget02;
[SerializeField] Button btn_RotTarget03;
[SerializeField] Button btn_RotTarget04;
[SerializeField] Button btn_AreaTarget01;
[SerializeField] Button btn_AreaTarget02;
[SerializeField] Button btn_BirdViewTarget01;
[SerializeField] Button btn_FollowTarget01;
// 闪现切换方式的按钮
[SerializeField] Button btn_RotTarget01_Flash;
[SerializeField] Button btn_RotTarget02_Flash;
[SerializeField] Button btn_RotTarget03_Flash;
[SerializeField] Button btn_RotTarget04_Flash;
[SerializeField] Button btn_AreaTarget01_Flash;
[SerializeField] Button btn_AreaTarget02_Flash;
[SerializeField] Button btn_BirdViewTarget01_Flash;
[SerializeField] Button btn_FollowTarget01_Flash;
// 测试用的移动目标
[SerializeField] Transform testMoveNPC;
void Start()
{
// 设置相机的移动速度和缩放速度
this.SendCommand(new CMD_SetMoveAndZoomSpeed(1.5f, 3));
// 设置相机的俯仰角度范围,从5度到85度
this.SendCommand(new CMD_SetPitchAngle(5, 85));
toggle_FreezeCam.onValueChanged.AddListener(isOn =>
{
if (isOn)
{
// 冻结相机
this.SendCommand(new CMD_SetFreezeMode(true));
}
else
{
// 解冻相机
this.SendCommand(new CMD_SetFreezeMode(false));
}
});
btn_QueryTarget.onClick.AddListener(() =>
{
// 获取当前相机的目标类型
HK_TargetEnum targetType = this.SendQuery(new Query_GetCurrentTarget());
HKDebug.Log("当前目标为:" + targetType.ToString());
});
txt_TargetChangeTime.text = slider_TargetChangeTime.value.ToString("0.00" + " 秒");
slider_TargetChangeTime.onValueChanged.AddListener(value =>
{
txt_TargetChangeTime.text = value.ToString("0.00" + " 秒");
});
// 点击按钮,设置目标切换时间
btn_Ensure.onClick.AddListener(() =>
{
var targetChangeTime = slider_TargetChangeTime.value;
this.SendCommand(new CMD_SetTargetChangeTime(targetChangeTime));
});
btn_RotTarget01.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_01)));
btn_RotTarget02.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_02)));
btn_RotTarget03.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_03)));
btn_RotTarget04.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_04)));
btn_AreaTarget01.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.AreaTarget_01)));
btn_AreaTarget02.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.AreaTarget_02)));
btn_BirdViewTarget01.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.BirdViewTarget_01)));
btn_FollowTarget01.onClick.AddListener(() =>
{
this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.FollowTarget_01));
/*---------------------测试-----------------*/
testMoveNPC.position = new Vector3(-15f, 1, 4.5f);
testMoveNPC.DOMoveX(13f, 6f).SetEase(Ease.Linear).SetDelay(1f);
/*------------------------------------------*/
});
btn_RotTarget01_Flash.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_01).SetUsingFlash()));
btn_RotTarget02_Flash.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_02).SetUsingFlash()));
btn_RotTarget03_Flash.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_03).SetUsingFlash()));
btn_RotTarget04_Flash.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.RotTarget_04).SetUsingFlash()));
btn_AreaTarget01_Flash.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.AreaTarget_01).SetUsingFlash()));
btn_AreaTarget02_Flash.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.AreaTarget_02).SetUsingFlash()));
btn_BirdViewTarget01_Flash.onClick.AddListener(() => this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.BirdViewTarget_01).SetUsingFlash()));
btn_FollowTarget01_Flash.onClick.AddListener(() =>
{
this.SendCommand(new CMD_ChangeCamTarget(HK_TargetEnum.FollowTarget_01).SetUsingFlash());
/*---------------------测试-----------------*/
testMoveNPC.position = new Vector3(-15f, 1, 4.5f);
testMoveNPC.DOMoveX(13f, 6f).SetEase(Ease.Linear).SetDelay(1f);
/*------------------------------------------*/
});
// 注册 开始切换 Target 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"开始 切换 Target:{args._targetEnum}");
}).UnRegisterWhenGameObjectDestroyed(gameObject);
// 注册 完成切换 Target 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"完成 切换 Target:{args._targetEnum}");
tips_Txt.text = $"当前 Target 为:{args._targetEnum}";
}).UnRegisterWhenGameObjectDestroyed(gameObject);
}
}
```
**外部依赖:**
* Dotween
* ActionKit
------------------------------------------------------------------------------------------------------------------------------------------
## 3. HK_RoamingCam(基于 QFramework 架构):
**功能描述:**
HK_RoamingCam 是一套漫游相机管理系统,适用于虚拟展厅类相机控制,主要功能如下:
* PC端、WebGL端、Android端虚拟展厅类体验相机控制管理工具;
* 支持通过鼠标点击、手指触摸两种方式进行交互;
* 视角控制分为:第一人称漫游、三维俯视漫游、鸟瞰正交漫游三种模式;
* 第一人称漫游(`RoamView`):通过点击地面标识点进行位移(依赖Unity Navigation);
* 鸟瞰正交漫游(`BirdView`):上帝视角进行观察,相机为 Orthographic
* 三维俯视漫游(`ThreeDView`):上帝视角进行观察,相机为 Perspective
**使用方式:**
* 在本项目的 Architecture 中注册 `IHK_RoamingCamSystem`;
* 在场景中设置好 Navigation Static,并进行 Navigation 烘焙,生成合适的 NavMesh;
* 在场景中指定 RoamView 使用的 Point点位(附带HK_Point脚本),并设置好LookAtType;
* 在场景中指定好 BirdView 和 ThreeDView 使用的 OverlookPos 及 RotAroundTarget;
* 将HK_RoamPlayer 预设体放入场景中,并进行初始化设置;
* 具体用法,可参考 Test_UIRoamCamCtrl 脚本;
**外部依赖:**
* Dotween
------------------------------------------------------------------------------------------------------------------------------------------
## 4. HK_FirstPersonCam(基于 QFramework 架构)
**功能描述:**
HK_FirstPersonCam 是一套第一人称相机管理系统,主要功能如下:
* PC端的第一人称视角控制相机;
* 支持通过鼠标、键盘进行第一人称角色控制;
**使用方式:**
* 在本项目的 Architecture 中注册 `IHK_FirstPersonCamSystem`;
* 将场景中需碰撞的物体(如地面等),设置好碰撞体,并设置好Layer;
* 将 `FirstPersonPlayer` 预设体,拖入场景中;
* 在 `FirstPersonPlayer` 预设体的 `HK_FirstPersonCtrl` 组件中,设置好 `GroundMask` 层级;
* 设置完成后即可通过鼠标、键盘进行操控,按住鼠标右键控制角色旋转,按WASD键控制角色移动;
* 在表现层脚本中通过发送 `CMD_ChangeFirstPersonPos` 指令(并传入对应参数),可根据目标切换位置;
* 参考 Test_FirstPlayerCamChangePos 进行位置切换设置;
**外部依赖:**
* Dotween
* ActionKit
------------------------------------------------------------------------------------------------------------------------------------------
## 5. HK_SimpleTaskSystem(基于 QFramework 架构):
**功能描述:**
HK_SimpleTaskSystem 是一套简易任务管理系统,适用于 `线性任务流程` 的使用场景,支持任务队列的初始化、执行、中断和查询等操作。该系统使用枚举 (enum) 定义 `任务队列(TaskQueue)` 和 `任务(Task)`,可根据业务需求,自定义任务队列和任务步骤,主要功能如下:
* 无外部配置:没有外部配置,在代码中通过枚举定义任务队列和任务;
* 线性任务队列:任务按顺序执行,适用于按照线性步骤完成的简易任务流程;
* 指令、查询及事件:
* 通过指令(Command),初始化/驱动任务队列及任务
* 通过查询(Query),获取任务队列的进度,或任务队列中所有的任务名
* 通过事件(Event),监听任务队列及任务的状态变化
**使用方式:**
* 注册任务系统:在当前项目的 Architecture 中注册 `IHK_SimpleTaskSystem`。
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
RegisterSystem(new HK_SimpleTaskSystem());
}
}
```
* 自定义任务队列及任务:通过修改枚举类型 `TaskQueueType` 和 `TaskType`,定义自己的任务队列和任务(任务类型可新增)。
```csharp
///
/// 简易任务队列类型,只可对内部的枚举值进行新增或修改
///
public enum STS_TaskQueueType
{
Queue1,
Queue2,
}
///
/// 任务队列1 相关任务,基于泛型使用,可新增或删除
///
public enum TaskQueue01
{
Step01_放置干扰天线支架,
Step02_安装干扰天线,
Step03_连接干扰天线与干扰源,
Step04_放置抗干扰天线支架,
Step05_安装抗干扰天线,
Step06_连接抗干扰天线与电脑,
Step07_将干扰天线对准抗干扰天线,
Step08_放置标定天线,
}
///
/// 任务队列2 相关任务,基于泛型使用,可新增或删除
///
public enum TaskQueue02
{
Step01_开启设备电源,
Step02_初始化设备参数,
Step03_运行设备自检,
Step04_开始数据采集,
Step05_保存采集结果,
}
```
* 初始化并开始任务队列:使用 `CMD_STS_InitTaskQueue` 指令,初始化并开始任务队列;
```csharp
Queue taskQueue = new Queue(new TaskQueue01[]
{
TaskQueue01.Step01_放置干扰天线支架,
TaskQueue01.Step02_安装干扰天线,
TaskQueue01.Step03_连接干扰天线与干扰源,
TaskQueue01.Step04_放置抗干扰天线支架,
TaskQueue01.Step05_安装抗干扰天线,
TaskQueue01.Step06_连接抗干扰天线与电脑,
TaskQueue01.Step07_将干扰天线对准抗干扰天线,
TaskQueue01.Step08_放置标定天线,
});
// 初始化并开始 任务队列1
this.SendCommand(new CMD_STS_InitTaskQueue(STS_TaskQueueType.Queue1, taskQueue));
```
* 完成当前任务(按顺序):使用 `CMD_STS_CompleteCurrentTask` 指令,完成当前任务,任务将按照预先定义的顺序执行。(可传入延时时间,控制下个任务开始的时间)
```csharp
// 按顺序完成 任务队列1 当前任务
this.SendCommand(new CMD_STS_CompleteCurrentTask(STS_TaskQueueType.Queue1));
// 按顺序完成 任务队列1 当前任务,延时1.5秒后,开始下个任务
this.SendCommand(new CMD_STS_CompleteCurrentTask(STS_TaskQueueType.Queue1, 1.5f));
```
* 完成指定任务(按任务类型):使用 `CMD_STS_CompleteAppointTask` 指令,可通过任务类型完成当前任务,但仍要求按顺序执行,无法跳过未完成的任务。(可传入延时时间,控制下个任务开始的时间)
```csharp
// 完成步骤1
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step01_放置干扰天线支架));
// 完成步骤1,延时1.5秒后,开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step01_放置干扰天线支架, 1.5f));
```
* 查询任务队列所有任务名:使用 `Query_STS_AllTaskNames` 查询,可通过任务队列类型查询该队列所有的任务名。
```csharp
// 查询 任务队列1的所有任务名
List allTaskNames = this.SendQuery(new Query_STS_AllTaskNames(STS_TaskQueueType.任务队列1));
allTaskNames.ForEach(taskName => HKDebug.Log(taskName));
```
* 查询任务队列进度:使用 `Query_STS_TaskQueue` 查询,可通过任务队列类型查询该队列当前进度。
```csharp
// 查询 任务队列1的进度
float progress = this.SendQuery(new Query_STS_TaskQueue(STS_TaskQueueType.任务队列1));
HKDebug.Log($"任务队列1的进度为:{progress}");
```
* 中断并终止任务队列:使用 `CMD_STS_BreakUpTaskQueue` 指令,中断并终止一个任务队列。
```csharp
// 中断 任务队列1
this.SendCommand(new CMD_STS_BreakUpTaskQueue(STS_TaskQueueType.任务队列1));
```
* 注册事件监听:提供以下 5 个事件,可根据需要进行注册,监听任务队列和任务的状态变化:
* 任务队列开始事件:`Event_STS_TaskQueueBegin`
* 任务队列结束事件:`Event_STS_TaskQueueEnd`
* 任务队列中断事件:`Event_STS_TaskQueueBreakUp`
* 任务开始事件:`Event_STS_TaskStart`
* 任务完成事件:`Event_STS_TaskFinish`
```csharp
// 注册 任务队列开始 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务队列 开始:{args._taskQueueType}", LogColor.Blue);
});
// 注册 任务队列结束 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务队列 结束:{args._taskQueueType}", LogColor.Blue);
});
// 注册 任务队列中断 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务队列 中断:{args._taskQueueType}", LogColor.Yellow);
});
// 注册 任务开始 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务 开始:{args._taskQueueType} : {args._taskName}", LogColor.Green);
});
// 注册 任务完成 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务 结束:{args._taskQueueType} : {args._taskName}", LogColor.Green);
});
```
* 在Unity编辑器下,运行时,可通过“`HK_SimpleTaskViewer(简易任务系统查看器)`”查看当前任务队列状态。

* 具体用法,可参考 Test_UseSimpleTask 示例脚本。
**示例代码:**
```csharp
///
/// 简单版任务系统 演示测试脚本
///
public class Test_UseSimpleTask : MonoBehaviour, IController
{
public IArchitecture GetArchitecture()
{
return HK_ArchitectureProvider.Architecture;
}
void Start()
{
// 注册 任务队列开始 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务队列 开始:{args._taskQueueType}", LogColor.Blue);
});
// 注册 任务队列结束 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务队列 结束:{args._taskQueueType}", LogColor.Blue);
});
// 注册 任务队列中断 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务队列 中断:{args._taskQueueType}", LogColor.Yellow);
});
// 注册 任务开始 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务 开始:{args._taskQueueType} : {args._taskName}", LogColor.Green);
});
// 注册 任务完成 事件
this.RegisterEvent(args =>
{
HKDebug.Log($"任务 结束:{args._taskQueueType} : {args._taskName}", LogColor.Green);
});
}
void Update()
{
if (Input.GetKeyDown(KeyCode.F1))
{
Queue taskQueue = new Queue(new TaskQueue01[]
{
TaskQueue01.Step01_放置干扰天线支架,
TaskQueue01.Step02_安装干扰天线,
TaskQueue01.Step03_连接干扰天线与干扰源,
TaskQueue01.Step04_放置抗干扰天线支架,
TaskQueue01.Step05_安装抗干扰天线,
TaskQueue01.Step06_连接抗干扰天线与电脑,
TaskQueue01.Step07_将干扰天线对准抗干扰天线,
TaskQueue01.Step08_放置标定天线,
});
// 初始化并开始 任务队列1
this.SendCommand(new CMD_STS_InitTaskQueue(STS_TaskQueueType.Queue1, taskQueue));
}
if (Input.GetKeyDown(KeyCode.F2))
{
Queue taskQueue = new Queue(new TaskQueue02[]
{
TaskQueue02.Step01_开启设备电源,
TaskQueue02.Step02_初始化设备参数,
TaskQueue02.Step03_运行设备自检,
TaskQueue02.Step04_开始数据采集,
TaskQueue02.Step05_保存采集结果,
});
// 初始化并开始 任务队列2
this.SendCommand(new CMD_STS_InitTaskQueue(STS_TaskQueueType.Queue2, taskQueue));
}
if (Input.GetKeyDown(KeyCode.Escape))
{
// 中断 任务队列1
this.SendCommand(new CMD_STS_BreakUpTaskQueue(STS_TaskQueueType.Queue1));
}
if (Input.GetKeyDown(KeyCode.Q))
{
// 查询 任务队列1的所有任务名
List allTaskNames = this.SendQuery(new Query_STS_AllTaskNames(STS_TaskQueueType.Queue1));
allTaskNames.ForEach(taskName => HKDebug.Log(taskName));
}
if (Input.GetKeyDown(KeyCode.W))
{
// 查询 任务队列1的进度
float progress = this.SendQuery(new Query_STS_TaskQueueProgress(STS_TaskQueueType.Queue1));
HKDebug.Log($"任务队列1的进度为:{progress}");
}
if (Input.GetKeyDown(KeyCode.Space))
{
// 按顺序完成 任务队列1 当前任务,延时1秒开始下个任务
this.SendCommand(new CMD_STS_CompleteCurrentTask(STS_TaskQueueType.Queue1, 1f));
}
if (Input.GetKeyDown(KeyCode.Alpha1))
{
// 完成步骤1,延时1.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step01_放置干扰天线支架, 1.5f));
}
if (Input.GetKeyDown(KeyCode.Alpha2))
{
// 完成步骤2,延时0.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step02_安装干扰天线, 0.5f));
}
if (Input.GetKeyDown(KeyCode.Alpha3))
{
// 完成步骤3,延时0.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step03_连接干扰天线与干扰源, 0.5f));
}
if (Input.GetKeyDown(KeyCode.Alpha4))
{
// 完成步骤4,延时0.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step04_放置抗干扰天线支架, 0.5f));
}
if (Input.GetKeyDown(KeyCode.Alpha5))
{
// 完成步骤5,延时0.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step05_安装抗干扰天线, 0.5f));
}
if (Input.GetKeyDown(KeyCode.Alpha6))
{
// 完成步骤6,延时0.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step06_连接抗干扰天线与电脑, 0.5f));
}
if (Input.GetKeyDown(KeyCode.Alpha7))
{
// 完成步骤7,延时0.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step07_将干扰天线对准抗干扰天线, 0.5f));
}
if (Input.GetKeyDown(KeyCode.Alpha8))
{
// 完成步骤8,延时0.5秒开始下个任务
this.SendCommand(new CMD_STS_CompleteAppointTask(STS_TaskQueueType.Queue1, TaskQueue01.Step08_放置标定天线, 0.5f));
}
}
}
```
**外部依赖:**
* ActionKit
------------------------------------------------------------------------------------------------------------------------------------------
## 6. HK_TaskSystem(基于 QFramework 架构):
**功能描述:**
HK_TaskSystem 是一套任务管理系统,适用于 `线性及非线性任务流程` 的使用场景,支持任务链的初始化、执行、中断和查询等操作,主要功能如下:
* 任务管理系统(通过配置文件对任务流进行配置及编辑);
* 可在Unity编辑器中对任务流进行编辑,编辑后在运行时进行使用。
**使用方式:**
* 在当前项目的 Architecture 中注册 `IHK_TaskSystem`;
* 本系统分三个层级:任务链 `TaskList`、任务 `Task`、条件 `Condition`;
* 对外方法有四个:
`StartNewTaskList(string taskDataName)` //开启 新的 任务链
`BreakOffTaskList()` // 中断 当前 任务链
`AchieveCondition(HK_ConditionType condition)` // 达成指定条件
`StopTaskAudio()` // 停止当前播放的任务语音
`ImmediateFinishTaskList()` // 立即完成当前任务连(主要用于开发测试)
* 推荐使用 Command 指令来使用 TaskSystem,四个对外方法分别对应四个Command:
`CMD_StartNewTaskList` :开启新的任务链指令
`CMD_BreakOffTaskList` :中断当前任务链指令
`CMD_AchieveCondition` :达成指定条件指令(可传入延时时间,延时达成条件)
`CMD_StopTaskAudio` :停止当前播放的任务语音指令
`CMD_ImmediateFinishTaskList` :立即完成当前任务连(主要用于开发测试)
* 可通过 Query 来查询某条件是否达成:
`Query_ConditionState` : 查询某条件是否达成
* 外部可监听事件有六个:
`Event_TaskListStart` // 任务链开始 事件
`Event_TaskListFinish` // 任务链结束 事件
`Event_TaskListBreadOff` // 任务链中断 事件
`Event_TaskStart` // 任务开始 事件
`Event_TaskFinish` // 任务结束 事件
`Event_ConditionAchieve` // 条件达成 事件
**外部依赖:**
* ActionKit
* AudioKit
**示例代码:**
```csharp
public class Test_TaskUse : HK_TaskSystemController
{
void Update()
{
if (Input.GetKeyDown(KeyCode.Escape))
{
this.SendCommand();
}
if (Input.GetKeyDown(KeyCode.P))
{
this.SendCommand();
}
if (Input.GetKeyDown(KeyCode.F1))
{
this.SendCommand(new CMD_StartNewTaskList("到应聘公司"));
}
if (Input.GetKeyDown(KeyCode.Alpha1))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C1_1到电梯门口));
}
if (Input.GetKeyDown(KeyCode.Alpha2))
{
// 延时 1s 达成条件
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C1_2跟门卫打招呼, 1));
}
if (Input.GetKeyDown(KeyCode.Alpha3))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C2_1按电梯按键));
}
if (Input.GetKeyDown(KeyCode.Alpha4))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C2_2走到光圈位置));
}
if (Input.GetKeyDown(KeyCode.Alpha5))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C3_1选择指示标));
}
if (Input.GetKeyDown(KeyCode.F2))
{
this.SendCommand(new CMD_StartNewTaskList("参与面试"));
}
if (Input.GetKeyDown(KeyCode.Q))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C4_1回答问题1));
}
if (Input.GetKeyDown(KeyCode.W))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C4_2回答问题2));
}
if (Input.GetKeyDown(KeyCode.E))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C5_1做笔试题1));
}
if (Input.GetKeyDown(KeyCode.R))
{
this.SendCommand(new CMD_AchieveCondition(HK_ConditionType.C5_2做笔试题2));
}
if (Input.GetKeyDown(KeyCode.Space))
{
bool isConditionFinish = this.SendQuery(new Query_ConditionState(HK_ConditionType.C1_1到电梯门口));
Debug.Log("Condition_C1_1到电梯门口 是否完成:" + isConditionFinish);
}
if(Input.GetKeyDown(KeyCode.Backspace))
{
this.SendCommand();
}
}
}
```
------------------------------------------------------------------------------------------------------------------------------------------
## 7. HK_SimpleDialogSystem(基于 QFramework 架构):
**功能描述:**
HK_SimpleDialogSystem 是一套3D场景的简易对话系统,用于3D场景或VR场景的对话开发,主要功能如下:
* 简易对话系统(通过 CSV 配置文件对话进行配置及编辑);
* 在 Excel 中对对话流程进行编辑,编辑后另存为 CSV 文件,放在 Resource 文件夹下;
* 需确保 CSV 文件为UTF-8编码格式;
* 目前支持3D的对话UI,主要为适配VR开发;
**使用方式:**
* 在本项目的 Architecture 中注册 `IHK_SimpleDialogSystem`;
* 使用 Command 指令来使用 HK_SimpleDialogSystem,三个指令分别为:
* `CMD_StartNewDialog3D` :开启新的3D对话指令
* `CMD_EndCurDialog3D` : 停止当前的3D对话指令
* `CMD_PlayForwardDialog` :继续推进对话指令
* 外部可监听事件:
* `Event_DialogStart` // 对话开始 事件
* `Event_DialogEnd` // 对话结束 事件
* `Event_OptionChoiced` // 选项做出选择 事件
**外部依赖:**
* Dotween
------------------------------------------------------------------------------------------------------------------------------------------
## 8. HK_Tips(基于 QFramework 架构):
**功能描述:**
HK_Tips 是一套三维场景中悬浮提示标签工具,可快速摆放编辑,运行时支持点击事件响应,主要功能如下:
* 本工具是三维场景中,进行悬浮提示标签的便捷工具;
* 可在场景中快速摆放编辑,运行时可通过点击的方式进行事件响应;
**使用方式:**
* 在当前项目的 Architecture 中注册 `IHK_SimpleTaskSystem`;
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
this.RegisterSystem(new HK_TipSystem());
}
}
```
* 在场景中摆放 `Prefabs` 文件夹下的 `HK_Tip` 预设体并编辑。
* 运行时可点击 `HK_Tip` 标签会自动发送点击事件 `Event_HKTipClick`。
* 使用 Command 指令来进行整体控制:
* `CMD_HideAllHKTips` : 控制所有 HKTip 隐藏
* `CMD_ShowAllHKTips` : 控制所有 HKTip 显示
* `CMD_SetAllHKTipActiveState` : 控制所有 HKTip 激活状态
```csharp
// 显示所有的 HKTip
this.SendCommand();
// 隐藏所有的 HKTip
this.SendCommand();
// 禁用所有的 HKTip
this.SendCommand(new CMD_SetAllHKTipActiveState(false));
// 激活所有的 HKTip
this.SendCommand(new CMD_SetAllHKTipActiveState(true));
```
* 外部可监听事件:
* `Event_HKTipClick` : HKTip点击事件
```csharp
this.RegisterEvent(args =>
{
Debug.Log("点击的Tip名称为:" + args._tipName);
Debug.Log("点击的Tip类型为:" + args._tipType);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
```
**外部依赖:**
* Dotween
------------------------------------------------------------------------------------------------------------------------------------------
## 9. HK_DebugTool:
**功能描述:**
HKDebug 对 Unity 内置 Debug 功能的扩展和封装,提供更灵活、强大的日志管理方案。通过使用 HKDebug,可以轻松控制和优化日志输出,提升调试效率和代码可维护性,主要功能如下:
* **日志颜色设置:** 支持白色、红色、黄色、绿色、蓝色和青色,通过不同颜色区分日志类型。
* **日志样式设置:** 支持普通、粗体、斜体和粗体斜体,通过样式区分日志重要性。
* **日志类型:**
* 普通日志:`HKDebug.Log` 方法输出,适用于一般调试信息。
* 警告日志:`HKDebug.LogWarning` 方法输出,默认黄色粗体,提示潜在问题。
* 错误日志:`HKDebug.LogError` 方法输出,默认红色粗体,标识严重错误。
* **日志时间戳:** 根据配置启用,日志消息自动附加当前时间戳(精确到毫秒)。
* **日志保存:** 仅在 Editor 及 Windows 下可用,根据配置启用,日志保存到项目目录下的 HKLog 文件夹,每次启动项目创建新文件。
**使用方式:**
* **普通日志输出:**`HKDebug.Log` 方法用于输出普通的日志消息,替代 Unity 原生的 `Debug.Log` 方法。支持指定日志的颜色和样式,提升信息的可读性。
```csharp
HKDebug.Log("这是默认白色普通日志");
HKDebug.Log("这是黄色普通日志", LogColor.Yellow);
HKDebug.Log("这是绿色粗斜体日志", LogColor.Green, LogStyle.BoldAndItalic);
HKDebug.Log("这是蓝色粗体日志", LogColor.Blue, LogStyle.Bold);
HKDebug.Log("这是青色普通日志", LogColor.Cyan);
HKDebug.Log("这是红色普通日志",LogColor.Red);
```
* **警告日志输出:**`HKDebug.LogWarning` 方法用于输出警告日志消息,替代 Unity 原生的 `Debug.LogWarning` 方法。默认采用黄色粗体显示,便于快速识别潜在问题。
```csharp
HKDebug.LogWarning("这是一个警告日志");
```
* **错误日志输出:**`HKDebug.LogError` 方法用于输出错误日志消息,替代 Unity 原生的 `Debug.LogError` 方法。默认采用红色粗体显示,标识严重的错误信息。
```csharp
HKDebug.LogError("这是一个错误日志");
```

* **HKDebug配置:**
* 点击 `HKTools/HKDebugSettings (HKDebug配置)`,打开 HKDebug 配置窗口,在该窗口中可对 HKDebug 进行设置。
* 是否显示时间戳(默认关闭):通过 IsDebugTime 参数,设置打印日志时,是否包含时间信息。
* 是否日志保存(默认关闭,仅支持Editor及Windows):通过 IsSave 及 IsSaveNormalLog 参数,设置是否启用日志保存功能及选择是否保存普通日志,需注意日志保存仅在 Editor 及 发布Windows时可用,若启用日志保存,则日志文件将自动保存在项目目录下的 HKLog 文件夹中,每次启动项目时,将生成一个新的日志文件,文件名包含启动时间,便于分类和管理,日志文件中不仅包含日志消息,还记录了系统和设备的详细信息,辅助后期调试。

**外部依赖:**
* 无
------------------------------------------------------------------------------------------------------------------------------------------
## 10. HK_Video:
**功能描述:**
HK_Video 是一套视频播放控制工具,对Unity的VideoPlayer进行了封装,分为完整版播放器 `HK_VideoPanel` 和 简易版播放器 `HK_SimpleVideoPanel` 两类。
**使用方式:**
* 包含完整版播放器 HK_VideoPanel 和 简易版播放器 HK_SimpleVideoPanel 两种。
* 将 HK_VideoPanel 或 HK_SimpleVideoPanel 预设体拖拽入当前场景中进行使用(放置在Canvas下)。
* 通过获取 HK_VideoPanel 或 HK_SimpleVideoPanel 脚本进行使用。
* 调用对应脚本的 PlayAssignedVideoA() 方法,传入视频的URL或VideoClip进行播放。
**外部依赖:**
* 无
------------------------------------------------------------------------------------------------------------------------------------------
## 11. HK_SerialPortSystem(基于 QFramework 架构):
**功能描述:**
HK_SimpleDialogSystem 是一套串口通信管理系统,可通过配置文件 `HK_SerialConfig.json` 进行外部配置,主要功能如下:
* 提供Unity下的串口通信功能。
* 可通过配置文件 HK_SerialConfig.json 在外部进行配置。
* 使用时,Unity项目工程的 `Api Compatibility Level` 必须为`.Net Framework`。
* 工具仅可应用于 `Windows端`。
**使用方式:**
* 确认当前Unity项目工程的 `Api Compatibility Level` 选择了 `.Net Framework`,位置如下图:

* 确认 `StreamingAssets` 文件夹下是否有 `HK_SerialConfig.json` 配置文件,可通过自动化工具生成或重置。

* 修改 `StreamingAssets/HK_SerialConfig.json` 配置文件,调整串口配置;
```json
{
"PortName": "COM3",
"BaudRate": 9600,
"Parity": "None",
"DataBits": 8,
"StopBits": "None"
}
```
* 在当前项目的 Architecture 中注册 `IHK_SerialPortSystem`;
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
this.RegisterSystem(new HK_SerialPortSystem());
}
}
```
* 通过调用 InitSerialPort 方法,并传入串口通信指令长度参数,进行初始化;
```csharp
this.GetSystem().InitSerialPort(6);
```
* 通过调用 OpenSerialPort 方法,开启串口;
```csharp
this.GetSystem().OpenSerialPort();
```
* 通过调用 CloseSerialPort 方法,关闭当前串口;
```csharp
this.GetSystem().CloseSerialPort();
```
* 注册 Event_ReceiveSerialPortData 事件,接口串口通信数据;
```csharp
this.RegisterEvent(args =>
{
Debug.Log("接收到串口数据: " + args._serialPortData);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
```
**外部依赖:**
* ActionKit
------------------------------------------------------------------------------------------------------------------------------------------
## 12. HK_UGUITools:
### HK_UIFramework(基于 QFramework 架构)
**功能描述:**
本UI框架旨在管理各种UI面板的打开、关闭及其层级、排序关系,本框架提供了一套机制,使得开发者可以方便地操控UI元素,确保界面层级按照预期显示,并且不同面板类型(全局面板和层级面板)能够和谐共存。
全局面板(Global Panel):
+ 全局性面板,通常涵盖应用的全局功能,例如顶部栏、全局设置窗口、确认窗口等。
+ 全局面板通常具有较高的显示优先级顺序 (Order 属性)。
层级面板(Hierarchy Panel):
+ 层级面板,通常覆盖整个应用界面,由栈来进行管理,例如软件的各层级页面等。
+ 层级面板以栈的形式管理,栈顶的面板总是当前活动面板。
+ 打开新的层级面板时,当前活动的层级面板会被暂停,新的面板成为活动面板。
+ 关闭栈顶层级面板时,之前被暂停的面板将重新变为活动状态。
**使用方式:**
+ 在当前项目的 Architecture 中注册 IHK_UISystem
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
this.RegisterSystem(new HK_UISystem());
}
}
```
+ 将UI_Root预设体拖入场景中,在ForDesign节点下编辑各个面板,并添加控制脚本(需继承HK_BasePanel)。
+ 编辑后的脚本作为预设体,存放在Project某目录下。
+ 若预设体实例发生修改,在Hierarchy中会显示“更新”按钮。

+ 编辑 HK_UIConfig,对各面板进行参数配置。

+ 可在 全局面板 及 层级面板 下设计子页面(子页面脚本需继承 HK_ChildPanelBase),并对子页面进行生命周期方法的同步管理。

------------------------------------------------------------------------------------------------------------------------------------------
### HK_CollapsibleMenu(基于 QFramework 架构)
+ 折叠菜单UI预设,可直接推拽至Canvas下进行适用。
+ 通过改1、2、3级MenuItem的预设体,适配不同的UI。
+ MenuItem按钮点击后发送指令。
------------------------------------------------------------------------------------------------------------------------------------------
### HK_UIOverride
+ 重写的UGUI Button组件:
通过在Inspector面板中修改AudioType,播放对应的Button点击音效(需注册对应的音效播放事件)。
通过在Inspector面板中修改AnimType,启用相应的Button动效(使用Dotween,可自行在脚本中修改)。
+ 重写的UGUI Toggle组件:
通过在Inspector面板中修改AudioType播放对应的Toggle点击音效(需注册对应的音效播放事件)。
+ 重写的UGUI Dropdown组件:
通过在Inspector面板中修改AudioPressType和AudioSelectType,播放对应的点击及选中音效(需注册对应的音效播放事件)。
------------------------------------------------------------------------------------------------------------------------------------------
### HK_SlidePage2D
* 2D轮播图工具,支持循环和往返两种切换模式。功能包含:
* 自动轮播与手动拖动切换
* 页码按钮联动
* 左右切换按钮控制
* 平滑动画过渡(基于DOTween)
------------------------------------------------------------------------------------------------------------------------------------------
### HK_SlidePage3D
* 3D轮播图工具,支持自适应屏幕布局与深度视觉差。功能包含:
* 自动旋转与手动控制切换
* 子物体深度排序与层级管理
* 透视缩放及透明度渐变效果
* 平滑旋转动画(基于DOTween)
------------------------------------------------------------------------------------------------------------------------------------------
### HK_Curve2D
+ 自定义的UI组件,用于在UGUI中绘制2D曲线,并可控制曲线默认显示状态,以及沿不同方向生长出现。
+ HK_Curve2DCtrl中的SetCurveInitState(bool isShow)方法:设置曲线的默认显示状态。
+ HK_Curve2DCtrl中的PlayGrowAnim(CurveGrowAnimType animType)方法:调用曲线的生长动画(根据动画类型)。
+ 曲线的形状、纹理、颜色等编辑在 HK_Curve2D 脚本中。
------------------------------------------------------------------------------------------------------------------------------------------
### HK_SimpleFrameSequence
HK_SimpleFrameSequence 是 一个轻量化的 Unity 序列帧动画控制器,可自动适配 UI Image 和 SpriteRenderer 两种渲染模式,支持精确帧率控制与循环播放。提供一键式纹理优化功能(关闭 Mipmap/ReadWrite),并通过自动补充渲染组件和首帧同步简化使用流程。

**功能描述:**
* **双渲染组件支持**:自动适配 UI Image(Canvas 环境)和 SpriteRenderer(2D 场景)
* **播放模式**:单次播放(定格末帧)/ 循环播放
* **自动化配置**:添加组件时自动补充 Image 组件或 SpriteRenderer 组件,序列帧赋值时自动同步首帧
* **纹理优化**:支持一键批量关闭 Mipmap/ReadWrite
**使用方式:**
* **安装与配置:**
* 将脚本添加到 GameObject,自动检测并添加所需渲染组件(Canvas 下添加 Image,其他环境添加 SpriteRenderer)
* **Inspector 配置:**
* 是否自动播放 - 勾选后立即开始播放
* 是否循环播放 - 控制动画循环模式
* 帧率 - 精确到毫秒的帧间隔计算
* 序列帧 - 拖拽添加 Sprite 序列帧
* **序列帧批量优化:**
* 关闭所有序列帧的 Mipmap 按钮 - 禁用关联纹理的Mipmap生成
* 禁用所有序列帧的 Read/Write Enabled 按钮 - 关闭关联纹理的CPU读写权限
* **运行时脚本控制:**
* 获取组件实例后,调用 StartFramesAnim(bool isLoop) 方法开始播放动画
* 获取组件实例后,调用 StopFramesAnim() 方法开始播放动画
------------------------------------------------------------------------------------------------------------------------------------------
### HK_FrameSequence
HK_FrameSequence 是一个进阶版的 Unity 序列帧动画控制器,支持三段式动画流程(初始→循环→结束),内置动画状态机自动处理阶段转换,可自动适配 UI Image 和 SpriteRenderer 双渲染模式,提供精准帧率控制与循环间隔播放功能,提供一键式纹理优化功能(关闭 Mipmap/ReadWrite),并通过自动补充渲染组件和首帧同步简化使用流程。

**功能描述:**
* **三段式动画流程**:支持初始帧、循环帧和结束帧的设置,自动管理动画状态转换,简化动画控制
* **双渲染组件支持**:自动适配 UI Image(Canvas 环境)和 SpriteRenderer(2D 场景)
* **播放模式**:单次播放 / 循环播放
* **自动化配置**:添加组件时自动补充 Image 组件或 SpriteRenderer 组件,序列帧赋值时自动同步首帧
* **纹理优化**:支持一键批量关闭 Mipmap/ReadWrite
**使用方式:**
* **安装与配置:**
* 将脚本添加到 GameObject,自动检测并添加所需渲染组件(Canvas 下添加 Image,其他环境添加 SpriteRenderer)
* **Inspector 配置:**
* 是否自动播放 - 勾选后立即开始播放
* 是否循环播放 - 控制动画循环模式
* 循环间隔 - 控制每次循环的间隔时间
* 帧率 - 精确到毫秒的帧间隔计算
* 初始序列帧 - 拖拽添加 初始的 Sprite 序列帧
* 循环序列帧 - 拖拽添加 循环的 Sprite 序列帧
* 结束序列帧 - 拖拽添加 结束的 Sprite 序列帧
* **序列帧批量优化:**
* 关闭所有序列帧的 Mipmap 按钮 - 禁用关联纹理的Mipmap生成
* 禁用所有序列帧的 Read/Write Enabled 按钮 - 关闭关联纹理的CPU读写权限
* **运行时脚本控制:**
* 获取组件实例后,调用 StartFramesAnim(bool isLoop) 方法开始播放动画
* 获取组件实例后,调用 StopFramesAnim() 方法开始播放动画
------------------------------------------------------------------------------------------------------------------------------------------
### HK_CircularSlider
* 基于 Unity 的自定义圆形滑块工具脚本,用于在游戏或应用中创建圆形滑块控件。
* 该控件允许用户通过拖动来选择一个介于 0 到 1 之间的值,并且可以根据用户的设置进行顺时针或逆时针滑动。
------------------------------------------------------------------------------------------------------------------------------------------
## 13. HK_TcpCommunicateSystem(基于 QFramework 架构):
**功能描述:**
HK_TcpCommunicateSystem 是为 Unity 设计的局域网 TCP 通信工具,包含了Server端和Client端两个部分,使用 TCP 协议实现客户端和服务器之间的消息传递。该系统通过 QFramework 框架进行管理,提供了服务器端和客户端的启动、关闭及消息发送等功能。以下是系统的主要功能:
主要特性如下:
+ 多客户端支持:服务器端可以同时处理多个客户端连接。
+ 线程管理:使用多线程和 CancellationTokenSource 管理服务器和客户端的生命周期,确保资源的正确释放。
+ Server端功能:
+ 启动Server:监听指定端口,等待客户端连接。
+ 关闭Server:通知所有客户端即将断开连接,并关闭所有客户端连接。
+ 发送消息给所有客户端:向所有已连接的客户端发送消息。
+ 发送消息给指定客户端:通过IP和端口号或Socket向指定客户端发送消息。
+ 设置Debug状态:控制是否在控制台输出Debug信息。
+ Client端功能:
+ 启动Client:连接到指定的服务器IP和端口。
+ 关闭Client:通知服务器即将断开连接,并关闭客户端连接。
+ 发送消息给服务器:向服务器发送消息。
+ 设置Debug状态:控制是否在控制台输出Debug信息。
+ 事件和指令:通过 QFramework 的事件和指令,使用该系统层,并将接收到的消息传递到主线程,方便在 Unity 环境中进行处理。
注意事项如下:
* 以下平台支持完整功能:
* Windows
* Mac
* Linux
* Android
* iOS
* 以下平台受限不可使用:
* WebGL
**使用方式:**
+ 在本项目的 Architecture 中注册 Server端或Client端的系统层;
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
// 注册 Client端系统层
this.RegisterSystem(new HK_TcpClientSystem());
// 注册 Server端系统层
this.RegisterSystem(new HK_TcpServerSystem());
}
}
```
+ 通过指令开启 Server端;
```csharp
// 作为 Server端,开启
this.SendCommand(new CMD_TCP_StartAsServer());
```
+ 通过指令给Client端发送消息;
```csharp
// 作为 Server端,给 所有的Client端 发送指令
this.SendCommand(new CMD_TCP_SendMsgS2C("Hello Client"));
```
+ Server端订阅事件;
```csharp
// 当 Client端 连接时
this.RegisterEvent(args =>
{
HKDebug.Log($"Event:Client端 {args._address}:{args._port} 加入", LogColor.Green);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
// 当 Client端 断开连接时
this.RegisterEvent(args =>
{
HKDebug.Log($"Event:Client端 {args._address}:{args._port} 退出", LogColor.Green);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
// 作为 Server端,接收 Client端 发送的消息
this.RegisterEvent(args =>
{
HKDebug.Log($"Event:Client端 {args._address}:{args._port} 发送消息 {args._msg}", LogColor.Green);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
```
+ 通过指令关闭 Server端;
```csharp
// 关闭 Server端
this.SendCommand(new CMD_TCP_CloseServer());
```
+ 通过指令开启 Client端;
```csharp
// 作为 Client端,开启,并传入 Server端的Ip及端口号
this.SendCommand(new CMD_TCP_StartAsClient("192.168.0.135", 8080));
```
+ 通过指令给Server端发送消息;
```csharp
// 作为 Client端,给 Server端发送指令
this.SendCommand(new CMD_TCP_SendMsgC2S("Hello Server"));
```
+ Client端订阅事件;
```csharp
this.RegisterEvent(args =>
{
HKDebug.Log($"Event:连接入Server端", LogColor.Green);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
this.RegisterEvent(args =>
{
HKDebug.Log($"Event:与Server端断开连接", LogColor.Green);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
this.RegisterEvent(args =>
{
HKDebug.Log($"Event:Server端 发送消息 {args._msg}", LogColor.Green);
}).UnRegisterWhenGameObjectDestroyed(gameObject);
```
+ 通过指令关闭 Client端;
```csharp
// 关闭 Client端
this.SendCommand(new CMD_TCP_CloseClient());
```
**外部依赖:**
+ 无
-----------------------------------------------------------------------------------------------------------------------------------------------
## 14. HK_UdpCommunicateSystem(基于 QFramework 架构):
**功能描述:**
HK_UdpCommunicateSystem 是为 Unity 设计的局域网 UDP 通信工具,支持单播、多播、广播三种通信模式,具备消息接收、ACK校验、多线程处理等特性,适用于实时通信场景(如多人VR、展厅多端交互等)。
主要功能及特性如下:
* 通信模式支持:
* 单播:向指定IP和端口的目标设备发送定向消息(如 192.168.0.14:7878)。
* 多播:向特定多播组(IPv4 D类地址,范围 224.0.0.0~239.255.255.255)发送消息,支持加入/离开多播组操作。
* 广播:向局域网内所有设备发送消息,显式启用广播功能(udpClient.EnableBroadcast = true),兼容不同平台默认设置。
* 生命周期管理:
* 启动UDP时绑定本地端口,支持重复启动校验(通过 isRunning 标志防止重复启动)。
* 关闭UDP时释放资源(udpClient.Client.Shutdown(SocketShutdown.Both)),避免端口被占用。
* 消息可靠性机制(ACK/RACK):
* 支持广播ACK消息(需确认的消息),接收方收到ACK消息后返回RACK确认,发送方通过回调感知发送结果。
* 初始化时可注册关注的ACK消息列表(CMD_UDP_InitAckList),仅处理列表内的ACK消息。
* 多线程与安全处理:
* 消息接收使用 ThreadPool.QueueUserWorkItem 启动子线程,避免阻塞主线程。
* 通过 SynchronizationContext 将事件分发到Unity主线程,确保UI操作安全。
* 参数校验与错误处理:
* 命令层(如 CMD_UDP_JoinMulticastGroup)严格校验多播地址格式(IPv4 D类地址)、端口号范围(0~65535)等,非法参数输出详细错误日志。
注意事项如下:
* 以下平台支持完整功能(单播、多播、广播、ACK校验等):
* Windows
* Mac
* Linux
* Android
* iOS
* 以下平台受限不可使用:
* WebGL
* 其他需注意内容:
* 多播组限制:部分路由器或网络环境可能禁用多播(如组播),需确保测试环境支持多播协议(如 IGMP)
* 广播范围:广播消息(BroadcastMsg)仅能在局域网(同一子网)内传播,跨路由器时无法到达
**使用方式:**
* 1.注册系统层:在项目的 Architecture 中注册 IHK_UdpSystem 系统层
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
this.RegisterSystem(new HK_UdpSystem());
}
}
```
* 2.基础操作(启动/关闭):通过指令控制UDP的启动与关闭
```csharp
// 启动UDP(绑定7878端口)
this.SendCommand(new CMD_UDP_Start(7878));
// 关闭UDP
this.SendCommand(new CMD_UDP_Close());
```
* 3.单播消息发送(定向发送到指定IP和端口)
```csharp
// 发送单播消息(7878端口)
this.SendCommand(new CMD_UDP_UnicastMsg("单播测试消息", "192.168.0.14", 7878));
// 发送单播消息(8787端口)
this.SendCommand(new CMD_UDP_UnicastMsg("单播测试消息", "192.168.0.14", 8787));
```
* 4.多播功能(加入/离开组 + 发送消息)
```csharp
// 加入多播组(示例地址:224.0.0.100)
this.SendCommand(new CMD_UDP_JoinMulticastGroup("224.0.0.100"));
// 发送多播消息(默认本机绑定端口)
this.SendCommand(new CMD_UDP_MulticastMsg("多播测试消息", "224.0.0.100"));
// 发送多播消息(指定7878端口)
this.SendCommand(new CMD_UDP_MulticastMsg("多播测试消息", "224.0.0.100", 7878));
// 离开多播组
this.SendCommand(new CMD_UDP_LeaveMulticast("224.0.0.100"));
```
* 5.广播与ACK消息
```csharp
// 初始化关注的ACK消息列表(仅处理列表内的ACK消息)
this.SendCommand(new CMD_UDP_InitAckList(new List() { "广播测试ACK消息01", "广播测试ACK消息02" }));
// 发送普通广播消息(8787端口)
this.SendCommand(new CMD_UDP_BroadcastMsg("广播测试消息", 8787));
// 发送ACK广播消息(8787端口,带发送成功回调)
this.SendCommand(new CMD_UDP_BroadcastAckMsg("广播测试ACK消息02", 8787, () => HKDebug.Log("确认发送成功!")));
```
* 6.监听消息事件
```csharp
// 监听普通消息(如广播消息)
this.RegisterEvent(args =>
{
HKDebug.Log($"接收到UDP消息:{args._msg}");
// 示例:收到"广播测试消息"时创建球体
if (args._msg == "广播测试消息")
{
GameObject.CreatePrimitive(PrimitiveType.Sphere).name = args._msg;
}
}).UnRegisterWhenGameObjectDestroyed(gameObject);
// 监听ACK消息(如广播ACK消息)
this.RegisterEvent(args =>
{
HKDebug.Log($"接收到UDP ACK消息:{args._ackMsg}");
// 示例:收到"广播测试ACK消息01"时创建立方体
if (args._ackMsg == "广播测试ACK消息01")
{
GameObject.CreatePrimitive(PrimitiveType.Cube).name = args._ackMsg;
}
}).UnRegisterWhenGameObjectDestroyed(gameObject);
```
**外部依赖:**
+ 无
------------------------------------------------------------------------------------------------------------------------------------------
## 15. HK_SimpleQuiz:
*+* (引入了QF框架)简单的考题功能,目前包含了:单选题、多选题、判断题,可通过Json或Excel文件对题库进行配置其中通过Excel配置的方式只支持PC端。
------------------------------------------------------------------------------------------------------------------------------------------
## 16. HK_FPSSystem(基于 QFramework 架构):
**功能描述:**
本工具是一个 FPS(每秒帧数)监控系统,可用于实时监测和优化 Unity 应用程序的性能。其主要功能包括:
* 实时显示 FPS:在游戏或应用界面上显示当前的帧率,直观了解应用的运行表现。
* 控制 FPS 显示:提供方法来显示或隐藏 FPS 监控,便于在开发过程中进行调试和性能分析。
* 设置目标帧率:可设置应用程序的目标帧率,以实现性能优化和稳定性提升。
通过上述功能,能够辅助在不同设备和场景下监控和优化应用性能,确保获得流畅的体验。
**使用方式:**
* 在本项目的 Architecture 中注册 HK_FPSSystem系统层;
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
// 注册 Client端系统层
this.RegisterSystem(new HK_FPSSystem());
}
}
```
* 通过 CMD_ShowFPSDisplay() 指令,在应用界面上激活显示 FPS;
```csharp
this.SendCommand(new CMD_ShowFPSDisplay());
```
* 通过 CMD_HideFPSDisplay() 指令,在应用界面上隐藏 FPS;
```csharp
this.SendCommand(new CMD_HideFPSDisplay());
```
* 通过 CMD_SetTargetFrameRate() 指令,设置目标刷新率;
```csharp
// 关闭 垂直同步,将目标刷新率设置为 60
if (Input.GetKeyDown(KeyCode.F3))
{
this.SendCommand(new CMD_SetTargetFrameRate(60, false));
}
// 开启 垂直同步,不限制目标刷新率
if (Input.GetKeyDown(KeyCode.F4))
{
this.SendCommand(new CMD_SetTargetFrameRate(-1, true));
}
```
* 具体用法,可参考 Test_FPSSystem 脚本。
```csharp
public class Test_FPSSystem : MonoBehaviour, IController
{
public IArchitecture GetArchitecture()
{
return HK_ArchitectureProvider.Architecture;
}
void Update()
{
// 显示 当前刷新率
if (Input.GetKeyDown(KeyCode.F1))
{
this.SendCommand(new CMD_ShowFPSDisplay());
}
// 隐藏 当前刷新率
if (Input.GetKeyDown(KeyCode.F2))
{
this.SendCommand(new CMD_HideFPSDisplay());
}
// 关闭 垂直同步,将目标刷新率设置为 60
if (Input.GetKeyDown(KeyCode.F3))
{
this.SendCommand(new CMD_SetTargetFrameRate(60, false));
}
// 开启 垂直同步,不限制目标刷新率
if (Input.GetKeyDown(KeyCode.F4))
{
this.SendCommand(new CMD_SetTargetFrameRate(-1, true));
}
}
}
```
**外部依赖:**
* 无
------------------------------------------------------------------------------------------------------------------------------------------
## 17. HK_StopwatchSystem(基于 QFramework 架构):
**功能描述:**
HK_StopwatchSystem 是一个多功能倒计时管理系统,为开发者提供精确的时序控制能力,主要功能如下:
* 通过可配置的倒计时实例,支持灵活的开始、暂停、恢复、重启等操作,满足复杂的时间管理需求。
* 采用数据绑定机制实时反馈剩余时间,并通过事件驱动架构实现状态变更的自动化通知。
**使用方式:**
* 在本项目的 Architecture 中注册 HK_FPSSystem系统层;
```csharp
public class XXX_Architecture : Architecture
{
protected override void Init()
{
// 注册 Client端系统层
this.RegisterSystem(new HK_StopwatchSystem());
}
}
```
* 通过系统层实例化一个Stopwatch实例,传入时间、回调方法等参数,进行初始化;
```csharp
// 创建30秒倒计时
stopwatch = this.GetSystem().CreateStopwatch(30, () =>
{
HKDebug.Log("倒计时结束");
});
```
* 可注册Stopwatch实例的 RemainingTime 响应式属性进行使用;
```csharp
// 绑定剩余时间显示(带初始值注册)
stopwatch.RemainingTime.RegisterWithInitValue((value) =>
{
txt_RemainingTime.text = $"剩余时间:{value:F1}秒";
}).UnRegisterWhenGameObjectDestroyed(gameObject);
```
* 可通过Stopwatch实例的 Start、Pause、Resume、Restart、Stop 方法,进行倒计时的控制;
```csharp
btn_Start.onClick.AddListener(() =>
{
stopwatch?.Start();
});
btn_Pause.onClick.AddListener(() =>
{
stopwatch?.Pause();
});
btn_Resume.onClick.AddListener(() =>
{
stopwatch?.Resume();
});
btn_Restart.onClick.AddListener(() =>
{
stopwatch?.Restart();
});
btn_Stop.onClick.AddListener(() =>
{
stopwatch?.Stop();
});
```
* 具体用法,可参考 Test_Stopwatch 脚本。
```csharp
public class Test_Stopwatch : MonoBehaviour, IController
{
public IArchitecture GetArchitecture()
{
return HK_ArchitectureProvider.Architecture;
}
[Header("UI Controls")]
[SerializeField] Button btn_CreateStopwatch; // 创建新计时器
[SerializeField] Button btn_Start; // 开始计时
[SerializeField] Button btn_Pause; // 暂停计时
[SerializeField] Button btn_Resume; // 恢复计时
[SerializeField] Button btn_Stop; // 停止并重置
[SerializeField] Button btn_Restart; // 重新开始
[Header("Display")]
[SerializeField] Text txt_RemainingTime; // 剩余时间显示文本
// 当前活动的倒计时实例
HK_Stopwatch stopwatch;
void Awake()
{
// 初始化按钮交互逻辑
btn_CreateStopwatch.onClick.AddListener(() =>
{
// 创建新实例前清理旧计时器
stopwatch?.Stop();
stopwatch = null;
// 创建30秒倒计时(测试用例)
stopwatch = this.GetSystem().CreateStopwatch(30, () =>
{
HKDebug.Log("倒计时结束");
});
// 绑定剩余时间显示(带初始值注册)
stopwatch.RemainingTime.RegisterWithInitValue((value) =>
{
txt_RemainingTime.text = $"剩余时间:{value:F1}秒";
}).UnRegisterWhenGameObjectDestroyed(gameObject);
});
btn_Start.onClick.AddListener(() =>
{
stopwatch?.Start();
});
btn_Pause.onClick.AddListener(() =>
{
stopwatch?.Pause();
});
btn_Resume.onClick.AddListener(() =>
{
stopwatch?.Resume();
});
btn_Restart.onClick.AddListener(() =>
{
stopwatch?.Restart();
});
btn_Stop.onClick.AddListener(() =>
{
stopwatch?.Stop();
});
}
}
```
**外部依赖:**
* ActionKit
------------------------------------------------------------------------------------------------------------------------------------------
## 18. HK_BezierLineRenderer:
**功能描述:**
HK_BezierLineRenderer 用于在 Unity 场景中生成并渲染贝塞尔曲线的组件,需配合LineRenderer使用,持通过调整端点位置、控制柄旋转/长度、曲线分段数等参数动态控制曲线形状,支持世界坐标/局部坐标绘制模式,且支持编辑时(Editor)和运行时(Runtime)自动更新。

**使用方式:**
1. **组件添加:** 在目标GameObject上添加 `HK_BezierLineRenderer` 组件(将自动添加Unity内置的 `LineRenderer` 组件用于实际渲染)。
2. **Inspector面板配置:** 通过检查器面板调整部分核心参数:
* `isWorldSpace`:切换世界坐标/局部坐标模式(不勾选为局部坐标,则处于相对于组件所在物体的局部坐标)。
* `segmentCount`:设置曲线分段数(数值越大曲线越平滑)。
3. **Scene视图交互编辑:** 在 Scene 视图中通过以下手柄直观调整曲线参数(编辑器自动更新预览)。
4. **LineRenderer组件编辑:** 对 `LineRenderer` 组件进行常规编辑,如调整材质、颜色等。
**外部依赖:**
* 无
------------------------------------------------------------------------------------------------------------------------------------------
## 19. HK_Attributes:
### HK_ReadOnly(Attribute):
* 将脚本中的序列化变量,在Inspector面板中变为ReadOnly,只能看不能改。
------------------------------------------------------------------------------------------------------------------------------------------
### HK_Foldup(Attribute):
* 将脚本中的序列化变量,在Inspector面板中进行折叠收纳整理。
------------------------------------------------------------------------------------------------------------------------------------------
## 20. HK_Enum:
* 定制的可随机插入、删除的序列化的枚举类型。
------------------------------------------------------------------------------------------------------------------------------------------
## 21. HK_NetworkSystem(基于 QFramework 架构):
* 对Unity的Nedecode进行封装,提供便捷的使用方式
* 需确保在Package Manager中,已导入Netcode for GameObjects 包
* 再将 HK_NetworkSystem 包导入本工程中进行使用
------------------------------------------------------------------------------------------------------------------------------------------
## 22. HK_SplitAnim:
* 模型拆分动画控制功能,可在Scene视窗中对模型动画目标位置进行设置,方便进行管理。
------------------------------------------------------------------------------------------------------------------------------------------
## 23. HK_FileLoad:
* (引入了QF框架,该模块仅可用于PC端)从电脑中读取图片、视频,并存储在StreamingAssets中。
------------------------------------------------------------------------------------------------------------------------------------------
## 24. HK_LoginRegister:
* (引入了QF框架)用户注册登录功能模块,Server端是NodeJs的,客户端为Unity。
------------------------------------------------------------------------------------------------------------------------------------------
# 复用工具:
## 1. HKUtility(非Mono单例工具类):
### 1.1 IsClickUI:
* 判断是否点击到UI上了,如果点在 UI 则返回 true,如果没点击到 UI 返回false。
```csharp
void OnMouseDown()
{
// 判断是否点击到UI,如果点击的是UI则返回
if (HKUtility.Instance.IsClickUI())
return;
Debug.Log("点击到了GameObject");
}
```
### 1.2 IsInTheFront:
* 判断 物体B 是否在 物体A的前方,如果在前方,返回 true,如果在后方,返回 false
### 1.3 IsOnTheRight:
* 判断 物体B 是否在 物体A的右边,如果在右边,返回 true,如果在左边,返回 false
------------------------------------------------------------------------------------------------------------------------------------------
## 2. HKMonoUtility(Mono单例工具类):
### 2.1 GetJsonFromStreamingAssets:
* 从 StreamingAssets 中获取Json文件并解析,通过callback返回
```csharp
HKMonoUtility.Instance.GetJsonFromStreamingAssets("JsonDatas/TestData", jsonData =>
{
Debug.Log(jsonData.Name);
});
```
### 2.2 GetJsonFromURL:
* 从 URL 中获取Json文件并解析,通过callback返回
### 2.3 GetSpriteFromStreamingAssets
* 从 StreamingAssets 中加载Sprite,通过callback返回
```csharp
HKMonoUtility.Instance.GetSpriteFromStreamingAssets("Image/Texture.png", sprite =>
{
GetComponent().sprite = sprite;
});
```
# 编辑器功能:
## 1.1 HK_SmartCopy(智能复制):
HK_SmartCopy 智能复制工具,借鉴 `Maya` 的智能复制功能,能在 `Unity` 中实现高效的物体对象的智能复制。该工具通过精准记录位置、旋转和缩放的偏移量,助力开发者快速创建连续且增量的复制对象,极大提升场景中物体排列与布局的工作效率。具体使用方式如下:
* **初始复制:** 按 `Ctrl+Shift+D` 触发智能复制操作,操作前需确保在 `Hierarchy` 面板或 `Scene` 场景中仅选中一个物体对象。
* **设置偏移:** 对首次复制出的对象进行位移、旋转或缩放调整,工具会自动记录这些调整产生的偏移量。
* **连续复制:** 再次按下 `Ctrl+Shift+D`,工具将依据记录的偏移量持续创建新的复制对象。
* **自动重置:** 若当前选中对象发生变化,工具会自动重置复制流程,重新开始记录偏移量。
工具操作及效果示意如下图所示:

------------------------------------------------------------------------------------------------------------------------------------------
## 1.2 HK_MakeGroup(打组工具):
HK_MakeGroup 打组工具,借鉴 `Maya` 中的打组功能,用于将选中的多个 `Unity` 物体对象(`GameObjects`)打组操作。生成一个新的父对象,将所有选中的对象作为该新父对象的子对象,并将新父对象在层次视图中位置与第一个选中物体保持一致。具体使用方式如下:
* **选择物体:** 在 `Hierarchy` 面板中,选中需要打组的多个物体(`GameObjects`)。
* **执行打组操作:** 在 `HKTools` 菜单下,选择 `MakeGroup(打组工具)`,或按下快捷键 `Ctrl + G` 或 `Cmd + G`。
* **查看结果:** 此时会创建一个名为 `Parent_Go` 的新父对象,并按照预期层次结构和位置将选中的对象作为其子对象。
工具操作及效果示意如下图所示:

------------------------------------------------------------------------------------------------------------------------------------------
## 1.3 HK_ShortCutsExtension
Unity中部分MenuItem的快捷键拓展。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.1 HK_TodoList(代办事项清单工具)
本工具提供了在Unity中进行代办事项清单管理的功能,使用方法如下:
+ 添加 Todo 注释:在编写代码时,可以在需要标记为待办事项的行添加注释,工具会自动识别这些注释并将其记录为 Todo 条目,默认支持的注释前缀如下:
+ //TODO
+ //Todo
+ //todo
+ // TODO
+ // Todo
+ // todo
+ 存储 Todo 条目:识别出的 Todo 条目将自动存储在 HKTodoList 中,方便集中管理和查看。
+ 全局刷新:点击 “全局刷新” 按钮,工具会遍历整个 Unity 工程中的所有脚本文件,识别并更新所有 Todo 条目。
+ 快捷跳转:在 HKTodoList 中点击 “打开脚本” 按钮,可以快速打开包含该 Todo 条目的代码脚本,并自动跳转到对应的行数,方便快速定位和处理。
+ 关键词自定义:可以修改 HK_TodoConstants 脚本中的 TodoKeyWords 和 SkipKeyWords,来自定义 Todo 条目识别的注释关键字,以及需要过滤的路径关键字,如下图所示:

+ 工具界面如下图所示:

------------------------------------------------------------------------------------------------------------------------------------------
## 2.2 HK_ResetName(重命名工具):
本工具提供了两大主要功能:替换选中物体名称中的特定字符串 和 对选中物体进行重命名。
该工具使得开发者可以更高效地管理游戏对象的命名,提高项目的组织和维护便利性。
+ 替换功能: 查找选中物体名称中的特定字符串,并将其替换为新的字符串。适用于需要对名称进行部分修改的场景。
+ 重命名功能: 对选中物体进行批量重命名,并按照用户设定的起始编号进行命名排序。适用于需要对大量对象进行统一命名的场景。
使用方式如下:
+ 选择目标物体: 在Unity编辑器的Hierarchy窗口中,选择需要操作的物体;
+ 选择操作模式: 在工具界面中,从“Replace”和“Rename”两种模式中进行选择;
+ Replace 模式:输入待查找的字符串和替换的字符串,工具将扫描所有选中物体的名称,并将符合条件的部分替换为新字符串。
+ Rename 模式:输入新的名称和起始编号,工具将对选中物体进行重命名,并按编号顺序进行排序。
+ Tips:如需将所有选中物体修改为统一命名,直接在Inspector界面的输入框中输入目标名称,将自动替换所有选中物体的名称为统一名称,无需使用本工具。
+ 工具界面如下图所示:


------------------------------------------------------------------------------------------------------------------------------------------
## 2.3 HK_RandomRotOrScale(随机旋转缩放工具):
* 对选中的物体进行随机旋转和缩放。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.4 HK_DotweenEaseShow(Dotween动效预览工具):
* (依赖Dotween)该工具可对Dotween内置Ease缓动动画进行预览,可查看所有缓动类型的动画曲线及相应预览动画。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.5 HK_TagAndLayerViewer(标签与层级预览工具):
* 场景中Tag和Layer的管理工具,对项目中所有的Tag标签及Layer层级进行显示,显示当前场景中对应Tag标签(或Layer层级)包含的物体数量,且可进行选择。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.6 HK_TextureAndModelSetting(贴图、模型设置工具):
### HK_MaterialTextureMatch:
* 一个 Unity 编辑器扩展工具,旨在简化材质球与其对应贴图之间的匹配过程。
* 该工具支持多种渲染管线,包括内置渲染管线、URP 和 HDRP,并提供了灵活的贴图后缀匹配与自动分配功能。
### HK_TextureSetting:
* 贴图批量化设置及压缩工具,可批处理图片的分辨率(调整为4的倍数),也可批量设置图片的压缩格式;
* 目前只支持 Windows、WebGL、Android 目标平台);
* 设置图片分辨率时,直接选择图片文件进行操作;
* 设置压缩格式时,选择包含贴图的单一文件夹进行操作,工具只会压缩设置当前文件夹下的贴图;
### HK_ModelImporter:
本工具用于自动处理FBX及OBJ模型文件的导入设置。自动化设置如下:
* 当导入FBX或OBJ格式的模型文件时,该工具会自动激活并修改材质设置,将 Materials 的 Location 修改为 Use External Materials(Legacy),可简化材质管理流程。
### HK_NormalMapImporter:
本工具用于在导入贴图时自动检测并设置法线贴图的 TextureType 为 Normal map。自动化设置如下:
* 检查贴图文件名是否包含"_normal"、"_nrm"或"_n"等关键字。
* 对贴图进行颜色特征采样,通过分析部分像素的颜色平均值,判断是否符合法线贴图的特征(R、G通道值接近0.5,B通道值接近1.0)。
* 如果符合上述两个条件,则判定为法线贴图。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.7 HK_TMPCharsExtractor(TMP文本提取工具):
本工具用于提取Unity场景中 TextMeshPro 文本组件的所有唯一字符(主要用于WebGL项目);
* 支持TMP_Text(3D文本)和TMP_TextMeshProUGUI(UI文本)类型;
* 提取结果将保存为单行无换行的UTF-8文本文件,路径为Assets/_UniqueCharacters/[场景名]_AllChars.txt;
* 本工具适用于字体资源裁剪、字符集管理等需求。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.8 HK_CheckUITexturePath(UI图片路径检查工具):
* HK_CheckUITexturePath 工具,用于检查当前Scene场景中所有UI图片(Image/RawImage组件)的资源路径。
* 支持按资源根文件夹分组展示路径信息,显示每个路径关联的UI组件数量。
* 点击路径条目可快速选中关联的游戏对象并在Hierarchy视图中高亮显示。
* 工具支持在Light和Dark主题下自适应显示效果。
* 主要用于 WebGL 等项目,用于集中管理及优化UI图集。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.9 HK_HierarchySearch(查找物体工具):
* 根据条件(名字、组件),对Hierarchy中选择的物体进行查询并重新选定。
------------------------------------------------------------------------------------------------------------------------------------------
## 2.10 HK_CreateGoByPath(基于路径创建工具):
本工具,可帮助用户在指定的路径上生成多个GameObject实例,并配置其位置偏移和旋转偏移。用户可以通过该工具快速在场景中布置物体,提高工作效率。使用方式如下:
+ 打开编辑窗口:打开Create Go By Path窗口:在Unity菜单栏中,选择HKTools -> CreateGoByPath,打开 HK_CreateGoByPath 窗口。
+ 生成路径:点击“生成 Path”按钮,在Scene视窗中生成路径。
+ 编辑路径:选择路径物体,在检查器窗口中的 HK_Path 组件中添加路径点(waypoints)。路径点可以直接在场景视图中通过拖动控制柄进行调整。

+ 重置坐标和路径点(可选操作):
+ 重置 Path 物体坐标轴:点击该按钮,将路径的位置设定到所有WayPoints的中心点。
+ 重置 Way Points 坐标:点击该按钮,重新对齐WayPoints到与路径对象的相对位置。
+ 配置参数:
+ 需生成的物体:选择一个要复制的模板GameObject或者Prefab。
+ 生成数量:设置要生成的物体数量。
+ 高度偏移:设置生成物体在Y轴的偏移量。
+ Y轴旋转偏移:设置生成物体的Y轴旋转。

+ 沿路径生成:确保在层次窗口中只选择具有 HK_Path 组件的路径对象,点击 “沿路径生成物体” 按钮,在路径上生成配置模板的实例对象
+ 删除生成的子物体:点击 “删除所有已生成物体” 按钮,将Path下所有已删除的物体进行删除操作。
------------------------------------------------------------------------------------------------------------------------------------------
## 3.1 HK_AutoSwitchToUTF8:
本工具是一个 Unity 编辑器扩展工具,旨在解决在 Unity 中导入或新建脚本时,因编码问题导致的中文字符乱码现象。
当在 Unity 中新建或导入脚本(例如 .cs 或 .csv 文件)时,若脚本的编码不是 UTF-8,可能会在 Inspector 面板预览或编辑脚本时出现中文乱码。为了自动解决这个问题,本工具会在资产导入过程中自动检测并转换脚本文件的编码。主要功能如下:
* 自动检测新导入的脚本文件:当有新的资产导入到 Unity 中时,脚本会自动触发 OnPostprocessAllAssets 方法,对新导入的资产进行检测。
* 筛选需要处理的文件:只对位于 Assets/ 目录下的 .cs 和 .csv 文件进行处理,确保不影响其他类型的资产。
* 检测文件是否已处理:检测并转换过的脚本文件生成唯一标识符,并在 EditorPrefs 中记录已处理的文件,避免重复处理同一文件,提高效率。
* 检测文件编码类型:根据文件的前两个字节判断文件的编码类型。如果文件的编码不是 UTF-8,则需要进行转换。
* 转换文件编码为 UTF-8:非UTF-8的脚本,读取其文件的全部内容,使用原始编码解码,然后以 UTF-8 编码重新写入文件,确保文件的编码格式为 UTF-8。

------------------------------------------------------------------------------------------------------------------------------------------
## 3.2 HK_UIBorderPreview:
* 本工具用于在 Scene 视图中实时可视化 UI 元素的边界框,主要功能如下:
* 边界框绘制:为场景中的 UI 元素(Image/RawImage/Text 等)实时绘制彩色边框
* 尺寸信息显示:在边框附近显示 UI 元素的名称、尺寸和锚点位置信息
* 交互组件抑制:自动跳过包含 Button/Slider 等交互组件的子级可视化
* 动态颜色配置:通过 HK_UIBorderPreviewWindow 配置面板自定义边框颜色和线宽
------------------------------------------------------------------------------------------------------------------------------------------
## 4.1 HK_HierarchyPro:
HK_HierarchyPro 是一款用于增强Unity编辑器中Hierarchy(层级)面板显示功能的实用工具。通过该工具,开发者可以更直观地查看对象的状态、层级和组件信息,从而有效提高工作效率。该工具具备以下主要功能:
* 显示Hierarchy列表的外边框及背景色:
* 外边框绘制:在Hierarchy面板中为每个对象绘制外边框,清晰展示对象之间的层级关系。
* 背景色区分:根据奇数行和偶数行绘制不同的背景色,增强视觉对比,方便快速浏览和定位。
* Layer信息显示:
* 在Hierarchy面板中显示每个对象所属的Layer层级名称(Default层级除外),方便开发者快速识别和管理对象的Layer设置。
* 当Hierarchy面板宽度不足时,Layer信息会自动隐藏,保证界面整洁。
* 激活状态切换:
* 在Hierarchy面板中直接显示对象的激活状态切换按钮(即Active状态),无需展开Inspector面板即可快速启用或禁用对象。
* 组件图标显示:
* 在Hierarchy面板中显示特定组件的图标,如Canvas、Light、Camera、Collider等。通过图标直观了解对象包含的主要组件。
* 在Hierarchy面板中显示自定义的MonoBehaviour组件图标,便于识别和管理自定义脚本组件。
* 当显示组件数量较多时,可通过点击“•••”按钮分页查看更多组件图标。
* 标记功能:
* 通过快捷键Ctrl+M,对选中的对象进行标记或取消标记。
* 被标记的对象会在Hierarchy面板中显示星型符号(★),方便开发者对关键对象进行临时标记和管理。
* 注意事项:标记信息在场景关闭时会清空。
使用方式如下:
+ 在 HKTools/GlobalSettings...菜单中,可开启或关闭本工具,如下图所示。

------------------------------------------------------------------------------------------------------------------------------------------
## 4.2 HK_ProjectPro
HK_ProjectPro 用于在 Project 面板中为特定的文件夹显示自定义图标。这些文件夹包括但不限于脚本文件夹(Scripts)、预设体文件夹(Prefabs)、资源文件夹(Resources)等。该工具可以帮助开发者更直观地识别和管理项目中的不同类型文件夹,默认支持以下对应文件夹名称的图标显示(不区分大小写):
+ Scripts 文件夹:_Scripts, _Script, Scripts, Script
+ Prefabs 文件夹:_Prefabs, Prefabs, _Prefab, Prefab
+ Resources 文件夹:Resources
+ StreamingAssets 文件夹:Streamingassets
+ Scenes 文件夹:_Scenes, Scenes, _Scene, Scene
+ Materials 文件夹:Materials, Material, Mats, Mat, _Materials, _Material, _Mats, _Mat
+ UI 文件夹:UI, _UI, UIs, _UIs
使用方式如下:
+ 在 HKTools/Settings...菜单中,可开启或关闭本工具,如下图所示。

------------------------------------------------------------------------------------------------------------------------------------------
## 4.3 HK_InspectorPro
HK_InspectorPro 是一款用于增强Unity编辑器中 Inspector(监视器)面板显示功能的实用工具。主要功能如下:
* 增强一 HK_CSharpInspector C#脚本预览增强:
* 代码重新格式化:调整预览代码的词间距,使代码布局更加美观,便于开发者快速浏览和理解代码结构。
* 行号显示:在代码左侧显示行号,方便开发者快速定位代码行,提升调试效率。
* 字体优化:使用 Fira Code 等宽字体,提供更好的代码预览体验,确保字符间距一致,提升可读性。
* 动态主题适配:根据Unity编辑器主题设定,分为浅色和深色主题,模仿 Visual Studio 的主题风格,对 C# 的关键字、常见类、常见结构体、自定义方法等进行颜色高亮,提升代码的可读性和可视化效果。
* 动态主题自定义配置:在 HKTools/HK_InspectorProSettings/CSharpPreviewConfig 菜单中,可自定义关键词高亮的颜色,如下图所示:

* 增强前后对比如下图所示:

------------------------------------------------------------------------------------------------------------------------------------------
## 4.4 HK_ScenePro
HK_ScenePro是一个用于增强 Unity 编辑器中 Scene 视图功能的工具。主要提供了类似于 Photoshop 中的标尺和参考线功能,方便开发者在 Scene 视图中进行UI或场景的精确布局和排版工作。主要功能如下:
* 增强一 标尺及参考线功能:
* 显示/隐藏标尺和参考线:使用快捷键 Ctrl + R 可以切换标尺和参考线的显示和隐藏状态。
* 在 Scene 视图的顶部和左侧添加标尺,显示刻度,帮助您直观地了解场景中的位置和尺寸。
* 参考线功能仅在 2D 模式或使用 正交摄像机 时可用。
* 创建参考线:从标尺区域拖拽鼠标,可创建水平或垂直的参考线。
* 移动参考线:拖动已有的参考线,可调整其位置。
* 删除参考线:选中参考线后,按下 Delete 键即可删除。

------------------------------------------------------------------------------------------------------------------------------------------
## 5.1 HK_WebsiteCollection
* Unity开发相关站点的集合。
------------------------------------------------------------------------------------------------------------------------------------------