Compare commits

...

115 Commits

Author SHA1 Message Date
Alex-Rachel
5887133894 更新Procedure流程
更新Procedure流程
2025-02-20 01:39:52 +08:00
Alex-Rachel
6166fd24c6 yoo2.2,9
yoo2.2,9
2025-01-25 13:46:17 +08:00
Alex-Rachel
634a392a1f Update HybridCLR -> 7.3.0
Update HybridCLR -> 7.3.0
2025-01-15 23:54:31 +08:00
Alex-Rachel
b869a05220 #104 目前调用 HideUI 会将 UIWindow 的 Visible 设置为 false,但是如果又调用 CloseUI 方法,会将刚才 Visible 设置为 false 的窗口重新设置为 true。 2024-12-22 13:13:59 +08:00
ALEX
37d88c2d94 Merge pull request #103 from 6ag/main
更新文档
2024-12-17 10:07:14 +08:00
feng
f3aa8824d8 更新文档 2024-12-17 10:03:53 +08:00
ALEX
99c5afcbc5 Merge pull request #102 from 6ag/main
UIWindow新增Hide方法,将UIWindow中的UserData和UserDatas属性移动到UIBase
2024-12-16 23:46:33 +08:00
feng
4075588c34 UIWindow新增Hide方法,将UIWindow中的UserData和UserDatas属性移动到UIBase 2024-12-16 22:36:26 +08:00
Alex-Rachel
fdd9f34132 Merge branch 'main' of https://github.com/ALEXTANGXIAO/TEngine 2024-12-09 11:34:17 +08:00
Alex-Rachel
a2ab6efc71 #101 2024-12-09 11:34:05 +08:00
ALEX
67025c806e Update README.md 2024-12-09 11:12:02 +08:00
ALEXTANGXIAO
38afa45f9c #100 2024-12-04 10:45:19 +08:00
ALEXTANGXIAO
0dc572f43e #97 2024-12-02 23:51:53 +08:00
ALEXTANGXIAO
0679d924c1 Merge branch 'main' of https://github.com/ALEXTANGXIAO/TEngine 2024-12-02 23:48:12 +08:00
ALEXTANGXIAO
3de8cad99a #99 2024-12-02 23:46:08 +08:00
ALEX
065d5a7303 Merge pull request #98 from 6ag/main
适配 luban-next 最新版本的配表结构,新增 Mac 设备相关的 shell 脚本支持
2024-11-30 23:29:45 +08:00
feng
c089eb32ba 适配 luban-next 最新版本的配表结构,新增 Mac 设备相关的 shell 脚本支持 2024-11-30 23:09:45 +08:00
ALEXTANGXIAO
d571a937f8 UIWindow同一帧关闭导致GameObject无法销毁的极小概率bug修复 2024-11-22 23:09:44 +08:00
ALEXTANGXIAO
89210483a9 ScriptGenerator控制台日志 2024-10-16 22:56:39 +08:00
ALEXTANGXIAO
058ac2c9a5 RemoveAllListenerByOwner 倒序移除 2024-10-11 21:47:21 +08:00
ALEXTANGXIAO
990222c7c6 资源释放时序优化 2024-10-05 15:18:51 +08:00
ALEXTANGXIAO
d3914a96bb Merge branch 'main' of https://github.com/ALEXTANGXIAO/TEngine 2024-09-20 22:43:29 +08:00
ALEXTANGXIAO
4b178a9fa9 #80 2024-09-20 22:43:08 +08:00
ALEXTANG
79929c4ac3 Merge pull request #95 from landoU/main
修正:异步获取窗口方法GetUIAsync获取不到已加载的窗口
2024-09-20 22:29:28 +08:00
liufeiwei
38fa4d5cbc 修正:异步获取窗口方法GetUIAsync获取不到已显示的窗口 2024-09-18 09:42:12 +08:00
ALEXTANG
3ac6977f93 Rmv 2024-09-02 16:40:19 +08:00
ALEXTANGXIAO
3facec8f93 Update ProcedureInitPackage.cs 2024-08-25 19:09:07 +08:00
ALEXTANGXIAO
0570982b97 * support package mode tengine setting
* support package mode tengine setting
2024-08-25 19:07:11 +08:00
ALEXTANG
f785264873 #94 资源加载assetLoadingList处理
#94 资源加载assetLoadingList处理
2024-08-24 21:02:12 +08:00
ALEXTANGXIAO
4911ec074c 新增GetUIAsync,ShowUIAsyncAwait
新增GetUIAsync,ShowUIAsyncAwait
2024-08-11 10:24:27 +08:00
ALEXTANGXIAO
6ff9546152 Update RedNoteMgr.cs 2024-08-10 22:21:17 +08:00
ALEXTANG
5a8dc04b9c Merge pull request #92 from Kojima648/main
[opt] TEngine 设置界面逻辑优化
2024-08-10 17:24:37 +08:00
chengshengfei
d4482cf1c4 [opt]
中文:优化设置界面的tab切换,页面数据保存逻辑
English: Optimize tab switching and page data saving logic in the settings interface
2024-08-10 16:47:30 +08:00
ALEXTANG
c7fad139ba Merge pull request #91 from mi1890/main
* [fix] installed  as a  package ,class not found issue
2024-08-09 00:43:18 +08:00
mr.zz
650469a7db * support package mode tengine setting 2024-08-09 00:25:48 +08:00
mr.zz
c7c00eac9f * [fix] installed as a package ,class not found issue 2024-08-07 23:58:47 +08:00
ALEXTANG
5a883bc8ec Merge pull request #88 from kenkinky/main
[fixed]选中ResourceModule时进入Play模式抛出异常
2024-08-03 18:55:40 +08:00
BCC
79c1026c7c [fixed]选中ResourceModule时进入Play模式抛出异常 2024-08-02 12:54:25 +08:00
ALEXTANGXIAO
f2c69d58b2 DefaultLogger支持Unity6 2024-07-14 14:51:44 +08:00
ALEXTANGXIAO
c38d3b7cfa 支持Unity6 2024-07-14 14:37:43 +08:00
ALEXTANGXIAO
98cb74537a update hybridclr_version & UnityPackage Version 2024-07-14 14:32:00 +08:00
ALEXTANGXIAO
ed19a75be9 Update GameApp_RegisterSystem.cs 2024-07-14 14:30:43 +08:00
ALEXTANG
fd82ddf427 Merge pull request #85 from Vorik-S/main
加载热更新程序集的崩溃bug修正
2024-07-11 12:23:12 +08:00
沈挺
e53ceb0095 单例对象销毁时的检查,修正由此错误的销毁单例对象的bug 2024-07-09 18:49:55 +08:00
沈挺
9afda78735 修正GameApp_RegisterSystem文件漏写基类导致真机上无法正确执行GameApp.Instance.Active方法的bug 2024-07-09 17:23:24 +08:00
沈挺
5734d4f995 加载热更新程序集的崩溃bug修正 2024-07-09 16:11:41 +08:00
ALEXTANG
dc7ab7fd64 Merge branch 'main' of https://github.com/ALEXTANGXIAO/TEngine 2024-06-27 21:02:55 +08:00
ALEXTANG
fcb3416acd Update ResourceManager.cs 2024-06-27 21:02:47 +08:00
ALEXTANG
3df18c006d Merge pull request #82 from SaberArtoriaFan/Dev2
扩展绑定TE UI框架的便捷工具
2024-06-21 14:19:12 +08:00
EdwardLee
6cfae215dc 11 2024-06-21 00:59:26 +08:00
ALEXTANG
1aaa46c82c 资源模块增加设置:是否使用系统释放无用资源策略。
资源模块增加设置:是否使用系统释放无用资源策略。
2024-06-20 09:42:49 +08:00
ALEXTANG
ca79adce7c Merge pull request #79 from Severn17/main
新增WebGL一键打包功能 及 全平台运行增加WebGL示例图片
2024-06-17 15:22:15 +08:00
yangshiqi
b520eba187 新增WebGL一键打包功能 及 全平台运行增加WebGL示例图片 2024-06-14 15:09:01 +08:00
ALEXTANG
b5afaca217 Merge pull request #78 from Senfee-Cheng/main
[fix] 在注册事件之前调用初始化
2024-06-13 17:32:39 +08:00
chengshengfei
ea2efbf588 [fix] 在注册事件之前调用初始化 2024-06-13 16:21:40 +08:00
ALEXTANG
a4b1befc5a Merge pull request #77 from Senfee-Cheng/main
[opt] (编辑器下)如果有多个资源的Package,组件提供一个下拉,使用Yoo收集器的列表
2024-05-28 19:22:53 +08:00
ALEXTANG
8dcddfa328 Update EventInterfaceGenerate.cs 2024-05-28 19:19:01 +08:00
chengshengfei
dd37d130da [opt] (编辑器下)如果有多个资源的Package,组件提供一个下拉,使用Yoo收集器的列表 2024-05-28 19:16:45 +08:00
ALEXTANG
24d7dbc677 EventInterfaceGenerate支持List与Dictionary(但不推荐用)
EventInterfaceGenerate支持List与Dictionary(但不推荐用)
2024-05-28 18:09:13 +08:00
ALEXTANG
491100b932 Merge pull request #76 from Senfee-Cheng/main
[opt] 优化下载更新界面的显示
2024-05-28 16:55:42 +08:00
chengshengfei
c84c21574d [opt] 优化下载更新界面的显示 2024-05-28 15:56:05 +08:00
ALEXTANG
7914660f8c Update SingletonSystem.cs 2024-05-24 14:00:51 +08:00
ALEXTANG
b00679a276 Merge pull request #75 from SunXuebing/main
调整编辑器模式下模块销毁顺序,解决编辑器退出运行后资源管理器销毁了还被调用问题
2024-05-20 14:17:40 +08:00
sxb
cd9a10ccac Update RootModule.cs
修复条件判断
2024-05-20 13:31:57 +08:00
sxb1067
f11098d32e 调整编辑器模式下模块销毁顺序,解决编辑器退出运行后资源管理器销毁了还被调用问题 2024-05-20 11:25:01 +08:00
ALEXTANGXIAO
db6e715fa6 Update ActorEventDispatcher.cs 2024-05-19 22:03:53 +08:00
ALEXTANG
c2edf71ee4 Update AssetItemObject.cs 2024-05-17 17:55:53 +08:00
ALEXTANG
75af7c22c7 Merge pull request #73 from Senfee-Cheng/main
[fix] 移除 `BuildDLLCommand` 构造函数以尝试解决hotfix dll数组被清除的问题
2024-05-17 15:48:27 +08:00
chengshengfei
2f9edf83bf Merge branch 'main' of github.com:Senfee-Cheng/TEngine 2024-05-17 15:45:26 +08:00
chengshengfei
815095efaf [fix] 移除 BuildDLLCommand 构造函数以尝试解决数组被清除的问题 2024-05-17 15:45:06 +08:00
ALEXTANG
3101a64a48 Merge pull request #72 from Severn17/main
yooasset 微信小游戏设置,详情看yooasset微信小游戏支持解决方案文档
2024-05-16 16:05:41 +08:00
yangshiqi
457e0f36a4 yooasset 微信小游戏设置,详情看yooasset微信小游戏支持解决方案文档 2024-05-16 15:19:32 +08:00
ALEXTANG
0bd30def23 移除示例package文件 2024-05-16 13:16:25 +08:00
ALEXTANG
d24db83c8b Update 99-各平台运行RunAble.md 2024-05-16 12:34:55 +08:00
ALEXTANG
18a2840777 Merge pull request #70 from Senfee-Cheng/main
[Platform] Supports console
2024-05-16 10:26:13 +08:00
chengshengfei
1d901514e1 新的平台支持[Sony Console] 2024-05-16 10:18:03 +08:00
chengshengfei
983279c56d 更新文档,添加新增的支持的平台。 2024-05-16 10:14:22 +08:00
ALEXTANG
e9540c620a Merge pull request #69 from Severn17/main
修改编辑器下webgl  平台名字 宏问题
2024-05-14 17:57:38 +08:00
yangshiqi
39be280d88 修改编辑器下webgl 平台名字 宏问题 2024-05-14 17:45:40 +08:00
ALEXTANG
f9f9122027 单例系统完善生命周期、支持Dispose 2024-05-13 14:09:32 +08:00
ALEXTANG
682a0bd786 Update UnityExtension.cs 2024-05-08 17:11:39 +08:00
ALEXTANG
34c514cae8 Update README.md 2024-05-08 10:31:41 +08:00
ALEXTANG
c707cc1a38 GameApp Shutdown 2024-05-08 10:06:33 +08:00
ALEXTANG
f016fdd0a6 Update ReleaseTools.cs 2024-05-07 20:09:15 +08:00
ALEXTANG
4c0f5a77f9 支持编辑器下EnterPlayMode Options 2024-05-07 18:05:41 +08:00
ALEXTANG
ae0d00424f Update ProfilerDefineSymbols.cs 2024-04-30 17:42:36 +08:00
ALEXTANG
c8ecac5815 Update README.md 2024-04-29 12:27:40 +08:00
ALEXTANG
4f8c1cdfdd 修正SpritePostprocessor处理Atlas的override 2024-04-25 15:43:44 +08:00
ALEXTANG
dff043e075 Update SahderVariantCollect
Update SahderVariantCollect
2024-04-24 11:17:38 +08:00
ALEXTANG
e69dc47b8f 修正编辑器调用转表bat 当前路径的问题
修正编辑器调用转表bat 当前路径的问题
2024-04-17 14:27:28 +08:00
ALEXTANG
fc2ef0714c 设置DefaultYooFolderName为package。原本设置默认为yoo。
设置DefaultYooFolderName为package。原本设置默认为yoo。
2024-04-15 19:58:57 +08:00
ALEXTANG
d75c1c8c93 升级YooAsset->2.1.1、UniTask->2.5.4
升级YooAsset->2.1.1、UniTask->2.5.4
2024-04-15 19:37:42 +08:00
ALEXTANG
83bea559e4 Merge pull request #65 from Senfee-Cheng/main 2024-04-12 18:19:10 +08:00
ALEXTANG
26689639ed Merge pull request #64 from ZemelLing/dev-launcher 2024-04-12 18:17:06 +08:00
chengshengfei
bd6ac5f4da 优化代码。 2024-04-12 10:58:06 +08:00
ZemelLing
70dcb03a3f 确保Launcher打开的main场景,而不是其他名称里包含main的场景。 2024-04-11 13:09:16 +08:00
ALEXTANG
59b3649155 优化框架轮询逻辑 ,用脏数据构建Execute数组。
优化框架轮询逻辑 ,用脏数据构建Execute数组。
2024-04-08 15:37:06 +08:00
ALEXTANG
2c025efe3b 修正预加载流程 2024-04-08 14:41:16 +08:00
ALEXTANG
7ae6ef94ba 修正同时对一个图片进行异步SetSprite的处理
修正同时对一个图片进行异步SetSprite的处理
2024-04-07 15:45:32 +08:00
ALEXTANG
d5bb64b314 资源异步加载从缓存中延迟分帧处理。 2024-04-07 15:33:45 +08:00
ALEXTANG
4c34858ce0 Update SettingsUtils.cs 2024-03-29 15:24:02 +08:00
ALEXTANG
5adb2f83e5 Update AssetBundleCollectorSetting.asset 2024-03-29 14:38:44 +08:00
ALEXTANG
f10a89180e 支持边玩边下载,合理化webgl下的流程
支持边玩边下载,合理化webgl下的流程
2024-03-28 15:55:27 +08:00
ALEXTANG
3e3314858e 优化加载游戏物体接口,常用Parent参数前置,编辑器模式下增加超时保护提示
优化加载游戏物体接口,常用Parent参数前置,编辑器模式下增加超时保护提示
2024-03-25 14:27:42 +08:00
ALEXTANGXIAO
da57ed845f 修正同时对一个资源进行异步加载的处理
修正同时对一个资源进行异步加载的处理
2024-03-24 15:58:57 +08:00
ALEXTANGXIAO
df570f453a Create UnityEditor.iOS_I2Loc.Xcode.dll 2024-03-24 15:50:44 +08:00
ALEXTANG
a500a08a30 更新Luban配置表使用文档 2024-03-19 14:25:48 +08:00
ALEXTANG
2daac0e065 默认一键打包使用ClearAndCopyAll 2024-03-19 14:09:27 +08:00
ALEXTANG
514da6e99e Update README.md 2024-03-18 15:44:29 +08:00
ALEXTANG
7f91241df7 Update Version.cs 2024-03-18 15:06:48 +08:00
ALEXTANG
071974ab4f Update GameLogic.asmdef 2024-03-18 15:05:40 +08:00
ALEXTANG
c01e03ff70 Update AssetBundleCollectorSetting.asset 2024-03-18 15:02:23 +08:00
ALEXTANG
6fec792e05 TEngine全面更新,升级YooAsset2.1.1、UniTask、UIWindow、I2Localization
TEngine全面更新,升级YooAsset2.1.1、UniTask、UIWindow、I2Localization
2024-03-18 14:53:26 +08:00
ALEXTANG
04ecf71eab Update ProcedureLoadAssembly.cs 2024-02-27 12:05:26 +08:00
ALEXTANG
693ca5bb3d 编辑器模式重定向所有热更dll,以防编辑器运行AB时出现两份元数据。
编辑器模式重定向所有热更dll,以防编辑器运行AB时出现两份元数据。
2024-01-25 15:10:30 +08:00
1390 changed files with 62635 additions and 46732 deletions

View File

@@ -13,11 +13,12 @@
![image](src/1-2.png)
### 4.打包运行
* 1.运行菜单 HybridCLR/Define Symbols/Enable HybridCLR 运行开启HybridCLR热更新
* 2.运行菜单 HybridCLR/Generate/All 进行必要的生成操作。这一步不可遗漏!!!
* 3.运行菜单 HybridCLR/Build/BuildAssets And CopyTo AssemblyPath生成热更新dll并copy到热更程序集中。
* 4.运行菜单 YooAsset/AssetBundle Builder 构建AB
* 5.打开Build Settings对话框点击Build And Run打包并且运行热更新示例工程
* 1.运行菜单 HybridCLR/Install... 安装HybridCLR,每次更新HybridCLR版本需要重新执行一次安装。
* 2.运行菜单 HybridCLR/Define Symbols/Enable HybridCLR 运行开启HybridCLR热更新。
* 3.运行菜单 HybridCLR/Generate/All 进行必要的生成操作。这一步不可遗漏!!!
* 4.运行菜单 HybridCLR/Build/BuildAssets And CopyTo AssemblyPath生成热更新dll并copy到热更程序集中。
* 5.运行菜单 YooAsset/AssetBundle Builder 构建AB
* 6.打开Build Settings对话框点击Build And Run打包并且运行热更新示例工程。
### 遇到问题请查看HybridlCLR的<a href="https://hybridclr.doc.code-philosophy.com/docs/help/commonerrors"><strong>常见错误(commonerrors)</strong></a>
@@ -33,26 +34,30 @@
### 目录结构
```
Assets
├── AssetRaw 资源目录
── Atlas 图集目录
├── GameScripts 热更程序集目录
├── Scenes 主场景目录
└── TEngine
── AssetSetting YooAsset资源设置
├── Editor TEngine-Editor程序集
└── Runtime TEngine-Runtime程序集
├── AssetArt // 美术资源目录
│ └── Atlas // 自动生成图集目录
├── AssetRaw // 热更资源目录
│ ├── UIRaw // UI图片目录
├── Atlas // 需要自动生成图集的UI素材目录
│ │ ── Raw // 不需要自动生成图集的UI素材目录
├── Editor // 编辑器脚本目录
├── HybridCLRData // hybridclr相关目录
├── Scenes // 主场景目录
├── GameScripts // 程序集目录
└── TEngine // 框架核心目录
├── AssetSetting // YooAsset资源设置
├── Editor // TEngine-Editor程序集
└── Runtime // TEngine-Runtime程序集
```
### 热更新程序集划分
```
Assets/GameScripts
├── Editor 编辑器程序集
── HotFix 游戏热更程序集目录 [Folder]
| ├── GameBase 游戏基础框架程序集 [Dll]
| ├── GameProto 游戏配置协议程序集 [Dll]
| ── BattleCore 游戏核心战斗程序集 [Dll]
| └── GameLogic 游戏业务逻辑程序集 [Dll]
| ── GameApp.cs 热更主入口
| └── GameApp_RegisterSystem.cs 热更主入口注册系统
└── Runtime Runtime程序集
├── Main // 主程序程序集(启动器与流程)
── HotFix // 游戏热更程序集目录 [Folder]
├── GameBase // 游戏基础框架程序集 [Dll]
├── GameProto // 游戏配置协议程序集 [Dll]
── GameLogic // 游戏业务逻辑程序集 [Dll]
├── GameApp.cs // 热更主入口
── GameApp_RegisterSystem.cs // 热更主入口注册系统
```

View File

@@ -51,17 +51,15 @@ public abstract class Module : MonoBehaviour
## 热更域程序集设计与说明
```
Assets/GameScripts
├── Editor 编辑器程序集
── HotFix 游戏热更程序集目录 [Folder]
| ├── GameBase 游戏基础框架程序集 [Dll]
| ├── GameProto 游戏配置协议程序集 [Dll]
| ── BattleCore 游戏核心战斗程序集 [Dll]
| ── GameLogic 游戏业务逻辑程序集 [Dll]
| ── GameApp.cs 热更主入口
| └── GameApp_RegisterSystem.cs 热更主入口注册系统
└── Runtime Runtime程序集
├── Main // 主程序程序集(启动器与流程)
── HotFix // 游戏热更程序集目录 [Folder]
├── GameBase // 游戏基础框架程序集 [Dll]
├── GameProto // 游戏配置协议程序集 [Dll]
── GameLogic // 游戏业务逻辑程序集 [Dll]
── GameApp.cs 热更主入口
── GameApp_RegisterSystem.cs 热更主入口注册系统
```
游戏内主要玩法逻辑包括UI会在GameLogic中编写GameBase则存放一些通用性的逻辑GameProto存放与服务区交互的协议以及配置表逻辑BattleCore为帧同步分离的逻辑层做预留。若有项目需求完全可以进行自定义增删HotFix程序集。
游戏内主要玩法逻辑包括UI会在GameLogic中编写GameBase则存放一些通用性的逻辑GameProto存放与服务区交互的协议以及配置表逻辑。若有项目需求完全可以进行自定义增删HotFix程序集。
PS注意增删程序集后需要同步到HybridClr的Setting面板以及TEngineSetting的面板。TEngineSettings面板有按钮可以从HybridClr中同步AOT与热更程序集。

View File

@@ -1,11 +1,19 @@
# 3-6.配置表模块 - ConfigLoader
# 3-6.配置表模块 - ConfigSystem
接入最佳游戏配置解决方案 - <a href="https://github.com/focus-creative-games/luban"><strong>Luban</strong></a>
<a href="https://luban.doc.code-philosophy.com/#/manual/traits"><strong>Luban文档 </strong></a>
### 在TEngine中Luban工具集位于以下目录
### 在TEngine中Luban配置表目录位于以下目录
![image](src/3-6-1.png)
### 安装luban配置表
1.在TEngine根目录同级克隆下最新的luban-next仓库。
![image](src/3-6-2.png)
2.Tools目录执行build-luban完成
![image](src/3-6-3.png)
3.转表则去luban配置目录执行对应bat
TEngine内置默认使用懒加载配置也支持基于UniTask的异步加载同步加载包括服务器的Task异步加载使用对应转表的bat即可。
### 介绍

View File

@@ -6,6 +6,8 @@
### ProcedureInitPackage - 流程初始化Package
### ProcedurePreload - 流程预加载
### ProcedureInitResources - 流程初始化Resources
### ProcedureUpdateVersion - 流程更新版本Version
@@ -20,5 +22,6 @@
### ProcedureClearCache - 流程清理缓存
### ProcedureLoadAssembly - 流程加载进入热更新程序集
### ProcedureLoadAssembly - 流程加载进入热更新程序集
### ProcedureStartGame - 流程开始游戏

View File

@@ -13,4 +13,14 @@
![image](src/Android-RunSuccessed.png)
### IOS真机运行
![image](src/Iphone-RunSuccessed.png)
![image](src/Iphone-RunSuccessed.png)
### WebGL真机运行
![image](src/WebGL-RunSuccessed.png)
### 索尼 PS5 真机运行
![image](src/Console%20Viewer.png)
![image](src/Console%20Output.png)

Binary file not shown.

Before

Width:  |  Height:  |  Size: 40 KiB

After

Width:  |  Height:  |  Size: 74 KiB

BIN
Books/src/3-6-2.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 32 KiB

BIN
Books/src/3-6-3.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 40 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 124 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 477 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 101 KiB

18
BuildCLI/build_android.sh Normal file
View File

@@ -0,0 +1,18 @@
#!/bin/bash
cd "$(dirname "$0")"
source ./path_define.sh
"${UNITYEDITOR_PATH}/Unity" "${WORKSPACE}" \
-logFile "${BUILD_LOGFILE}" \
-executeMethod TEngine.ReleaseTools.AutomationBuildAndroid \
-quit -batchmode \
-CustomArgs:Language=en_US "${WORKSPACE}"
while IFS= read -r line; do
echo "$line"
done < "${BUILD_LOGFILE}"
echo "按任意键继续..."
read -k1

14
BuildCLI/path_define.sh Normal file
View File

@@ -0,0 +1,14 @@
#!/bin/bash
cd "$(dirname "$0")"
export WORKSPACE="/Users/your_user/github/TEngine/UnityProject" # 请替换为 macOS 上的实际路径
export UNITYEDITOR_PATH="/Applications/Unity/Hub/Editor/2021.3.20f1c1/Unity.app/Contents/MacOS" # 请替换为 macOS 上的 Unity 路径
export BUILD_DLL_LOGFILE="./build_dll.log"
export BUILD_LOGFILE="./build.log"
echo "环境变量已设置:"
echo "WORKSPACE=${WORKSPACE}"
echo "UNITYEDITOR_PATH=${UNITYEDITOR_PATH}"
echo "BUILD_DLL_LOGFILE=${BUILD_DLL_LOGFILE}"
echo "BUILD_LOGFILE=${BUILD_LOGFILE}"

View File

@@ -42,16 +42,9 @@ public class ConfigSystem : Singleton<ConfigSystem>
/// <returns>ByteBuf</returns>
private ByteBuf LoadByteBuf(string file)
{
TextAsset textAsset = null;
textAsset = GameModule.Resource.GetPreLoadAsset<TextAsset>(file);
if (textAsset != null)
{
return new ByteBuf(textAsset.bytes);
}
else
{
textAsset = GameModule.Resource.LoadAsset<TextAsset>(file);
return new ByteBuf(textAsset.bytes);
}
TextAsset textAsset = GameModule.Resource.LoadAsset<TextAsset>(file);
byte[] bytes = textAsset.bytes;
GameModule.Resource.UnloadAsset(textAsset);
return new ByteBuf(bytes);
}
}

View File

@@ -1,3 +1,6 @@
Cd /d %~dp0
echo %CD%
set WORKSPACE=../..
set LUBAN_DLL=%WORKSPACE%\Tools\Luban\Luban.dll
set CONF_ROOT=.

View File

@@ -0,0 +1,24 @@
#!/bin/bash
cd "$(dirname "$0")"
echo "当前目录: $(pwd)"
export WORKSPACE="$(realpath ../../)"
export LUBAN_DLL="${WORKSPACE}/Tools/Luban/Luban.dll"
export CONF_ROOT="$(pwd)"
export DATA_OUTPATH="${WORKSPACE}/UnityProject/Assets/AssetRaw/Configs/bytes/"
export CODE_OUTPATH="${WORKSPACE}/UnityProject/Assets/GameScripts/HotFix/GameProto/GameConfig/"
cp -R "${CONF_ROOT}/CustomTemplate/ConfigSystem.cs" \
"${WORKSPACE}/UnityProject/Assets/GameScripts/HotFix/GameProto/ConfigSystem.cs"
dotnet "${LUBAN_DLL}" \
-t client \
-c cs-bin \
-d bin \
--conf "${CONF_ROOT}/luban.conf" \
-x outputCodeDir="${CODE_OUTPATH}" \
-x outputDataDir="${DATA_OUTPATH}"
echo "操作完成,按任意键退出..."
read -k1

View File

@@ -1,3 +1,6 @@
Cd /d %~dp0
echo %CD%
set WORKSPACE=../..
set LUBAN_DLL=%WORKSPACE%\Tools\Luban\Luban.dll
set CONF_ROOT=.

View File

@@ -0,0 +1,25 @@
#!/bin/bash
cd "$(dirname "$0")"
echo "当前目录: $(pwd)"
export WORKSPACE="$(realpath ../../)"
export LUBAN_DLL="${WORKSPACE}/Tools/Luban/Luban.dll"
export CONF_ROOT="$(pwd)"
export DATA_OUTPATH="${WORKSPACE}/UnityProject/Assets/AssetRaw/Configs/bytes/"
export CODE_OUTPATH="${WORKSPACE}/UnityProject/Assets/GameScripts/HotFix/GameProto/GameConfig/"
cp -R "${CONF_ROOT}/CustomTemplate/ConfigSystem.cs" \
"${WORKSPACE}/UnityProject/Assets/GameScripts/HotFix/GameProto/ConfigSystem.cs"
dotnet "${LUBAN_DLL}" \
-t client \
-c cs-bin \
-d bin \
--conf "${CONF_ROOT}/luban.conf" \
--customTemplateDir "${CONF_ROOT}/CustomTemplate/CustomTemplate_Client_LazyLoad" \
-x outputCodeDir="${CODE_OUTPATH}" \
-x outputDataDir="${DATA_OUTPATH}"
echo "操作完成,按任意键退出..."
read -k1

View File

@@ -1,3 +1,6 @@
Cd /d %~dp0
echo %CD%
set WORKSPACE=../../
set LUBAN_DLL=%WORKSPACE%/Tools/Luban/Luban.dll
set CONF_ROOT=.

View File

@@ -0,0 +1,21 @@
#!/bin/bash
cd "$(dirname "$0")"
echo "当前目录: $(pwd)"
export WORKSPACE="$(realpath ../../)"
export LUBAN_DLL="${WORKSPACE}/Tools/Luban/Luban.dll"
export CONF_ROOT="$(pwd)"
export DATA_OUTPATH="${WORKSPACE}/Server/GameConfig"
export CODE_OUTPATH="${WORKSPACE}/Server/Hotfix/Config/GameConfig"
dotnet "${LUBAN_DLL}" \
-t server \
-c cs-bin \
-d bin \
--conf "${CONF_ROOT}/luban.conf" \
-x outputCodeDir="${CODE_OUTPATH}" \
-x outputDataDir="${DATA_OUTPATH}"
echo "操作完成,按任意键退出..."
read -k1

View File

@@ -33,9 +33,6 @@
#### TEngine是一个简单(新手友好开箱即用)且强大的Unity框架全平台解决方案,对于需要一套上手快、文档清晰、高性能且可拓展性极强的商业级解决方案的开发者或者团队来说是一个很好的选择。
## <a href="http://1.12.241.46:5000/"><strong>文档快速入门 »</strong></a>
## 文档快速预览 - 5分钟
* [全平台跑通示意](Books/99-各平台运行RunAble.md): 全平台跑通示意。
* [01_介绍](Books/0-介绍.md): 简单介绍。
@@ -53,39 +50,38 @@
0. 开箱即用5分钟即可上手整套开发流程代码整洁思路清晰功能强大。高内聚低耦合。您可以很轻易的把您不需要的模块进行移除替换。
1. 严格按照商业要求使用次世代的HybridClr进行热更新、最佳的Luban配置表(TEngine支持懒加载、异步加载、同步加载配置。)、百万DAU游戏验证过的YooAsset资源框架框架管理资源引用与释放。全平台热更新流程已跑通。
2. 严格按照商业化流程执行的热更新、商业化的UI开发流程、以及资源管理等等设计并实现了YooAsset资源自动释放、支持LRU、ARC严格管理资源内存。
3. C#双端解决方案服务器使用Fantasy是一套源于ETServer但极为简洁性能更强更好上手的一套商业级服务器框架
4. 支持全平台已有项目使用TEngine上架Steam、Wechat-minigame、AppStore。
3. 支持全平台已有项目使用TEngine上架Steam、Wechat-minigame、AppStore
## <strong>资源重要拓展概念
* AssetReference (资源引用标识) 通用加载资源的时候绑定一个引用标识使你无需关心手动Dispose资源句柄。
## <strong>最新的Demo飞机大战位于demo分支
* AssetGroup资源组数据进行资源分组绑定管理内存中的生命周期资源生命周期托管给资源组的根节点进行Dispose。
## <strong>服务器相关
TEngine本身为纯净的客户端。不强绑定任何服务器。但是个人开发以及中小型公司开发双端则推荐C#服务器
* LruCacheTable (Least Recently Used Cache缓存表)
* ArcCacheTable (Adaptive Replacement Cache缓存表)
## <strong>为什么服务器使用C#
Net Core现在已经更新到了8.0的版本在性能和设计上其实是远超JAVA和GO。在JAVAER还在为JVM更新和添加更多功能时其实他们已经被国内大环境所包围了看不到.Net Core的性能之强组件化的结构。国内大环境是JAVA和GO的天下这个不可否认但是国外C#也确实很多。其实.Net Core最大的问题是大多数自己人都不知道他的优点(AOT、JIT混合编译、热重载等等)甚至很多守旧派抵制core。GO喜欢吹性能但其实目前来看除了协程的轻量级大多数性能测试其实不如JAVA和.Net。简单可以说出了C++的性能以外Net Core其实都打得过。
<strong>当然作为商业级解决方案服务器的耦合度也极低,如果不喜欢您也可以很轻松直接移除替换成你的服务器。</strong>
需要服务器可以合并<a href="https://github.com/ALEXTANGXIAO/GameNetty"><strong>GameNetty</strong></a>过来或者分支Fantasy为接好的带有Fantasy服务器的双端分支。
## <strong>项目结构概览
```
Assets
├── AssetArt // 美术资源目录
│ └── Atlas // 自动生成图集目录
├── AssetRaw // 热更资源目录
├── Atlas // 自动生成图集目录
│ ├── UIRaw // UI图片目录
│ │ ├── Atlas // 需要自动生成图集的UI素材目录
│ │ └── Raw // 不需要自动生成图集的UI素材目录
├── Editor // 编辑器脚本目录
├── HybridCLRData // hybridclr相关目录
├── Scenes // 主场景目录
├── TEngine // 框架核心目录
└── GameScripts // 程序集目录
├── Editor // 编辑器程序集
├── Main // 主程序程序集(启动器与流程)
└── HotFix // 游戏热更程序集目录 [Folder]
├── GameBase // 游戏基础框架程序集 [Dll]
├── GameProto // 游戏配置协议程序集 [Dll]
├── BattleCore // 游戏核心战斗程序集 [Dll]
├── GameProto // 游戏配置协议程序集 [Dll]
└── GameLogic // 游戏业务逻辑程序集 [Dll]
├── GameApp.cs // 热更主入口
└── GameApp_RegisterSystem.cs // 热更主入口注册系统
└── GameApp_RegisterSystem.cs // 热更主入口注册系统
TEngine
@@ -94,7 +90,7 @@ TEngine
```
- 必要:项目使用了以下第三方插件,请自行购买导入:
- /Unity/Assets/Plugins/Sirenix
- /UnityProject/Assets/Plugins/Sirenix
---
## <strong>优质开源项目推荐
@@ -105,12 +101,11 @@ TEngine
#### <a href="https://github.com/focus-creative-games/hybridclr"><strong>HybridCLR</strong></a> - 特性完整、零成本、高性能、低内存的近乎完美的Unity全平台原生c#热更方案
#### <a href="https://github.com/qq362946/Fantasy"><strong>Fantasy</strong></a> - Fantasy是一套源于ETServer但极为简洁性能更强,更好上手的一套商业级服务器框架。
#### <a href="https://github.com/qq362946/Fantasy"><strong>Fantasy</strong></a> - Fantasy是一套源于ETServer但极为简洁更好上手的一套商业级服务器框架。
## <strong>交流群
### <a href="http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=MzOcQIzGVLQ5AC5LHaqqA3h_F6lZ_DX4&authKey=LctqAWGHkJ7voQvuj1oaSe5tsGrc1XmQG3U4QniieGUlxY3lC7FtDIpEvPOX0vT8&noverify=0&group_code=862987645">群 号862987645 </strong></a>
#### <a href="https://github.com/ALEXTANGXIAO/GameNetty"><strong>GameNetty</strong></a> - GameNetty是一套源于ETServer首次拆分最新的ET8.1的前后端解决方案客户端最精简大约750k完美做成包的形式几乎零成本 无侵入的嵌入进你的框架。
## <strong>Buy me a coffee.
## <strong>Buy me a 奶茶.
[您的赞助会让我们做得更快更好如果觉得TEngine对您有帮助不妨赞助我买杯咖啡吧~](Books/Donate.md)
[您的赞助会让我们做得更快更好如果觉得TEngine对您有帮助不妨请我可爱的女儿买杯奶茶吧~](Books/Donate.md)

3
Tools/FileServer/instal.sh Executable file
View File

@@ -0,0 +1,3 @@
#!/bin/bash
npm install yumu-static-server -g

3
Tools/FileServer/start.sh Executable file
View File

@@ -0,0 +1,3 @@
#!/bin/bash
server -p 8081 -cors

View File

@@ -90,6 +90,7 @@ Sandbox/
# [Aa]ssets/Plugins/Sirenix.meta
#YooAssets
package/
yoo/
[Aa]ssets/TEngine/AssetSetting/Resources/BuiltinFileManifest.asset
[Aa]ssets/TEngine/AssetSetting/Resources/BuiltinFileManifest.asset.meta

View File

@@ -1,14 +1,13 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!612988286 &4096168566840163508
SpriteAtlasAsset:
--- !u!687078895 &4343727234628468602
SpriteAtlas:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_Name: UIRaw_Atlas_Common
m_MasterAtlas: {fileID: 0}
m_ImporterData:
m_EditorData:
serializedVersion: 2
textureSettings:
serializedVersion: 2
@@ -34,6 +33,30 @@ SpriteAtlasAsset:
m_Overridden: 1
m_AndroidETC2FallbackOverride: 0
m_ForceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 3
m_BuildTarget: Android
m_MaxTextureSize: 2048
m_ResizeAlgorithm: 0
m_TextureFormat: 50
m_TextureCompression: 1
m_CompressionQuality: 100
m_CrunchedCompression: 0
m_AllowsAlphaSplitting: 0
m_Overridden: 1
m_AndroidETC2FallbackOverride: 0
m_ForceMaximumCompressionQuality_BC6H_BC7: 0
- serializedVersion: 3
m_BuildTarget: WebGL
m_MaxTextureSize: 2048
m_ResizeAlgorithm: 0
m_TextureFormat: 50
m_TextureCompression: 1
m_CompressionQuality: 50
m_CrunchedCompression: 0
m_AllowsAlphaSplitting: 0
m_Overridden: 1
m_AndroidETC2FallbackOverride: 0
m_ForceMaximumCompressionQuality_BC6H_BC7: 0
packingSettings:
serializedVersion: 2
padding: 2
@@ -50,6 +73,19 @@ SpriteAtlasAsset:
- {fileID: 21300000, guid: d623a2b7e069a4c4592d3da48f476189, type: 3}
- {fileID: 21300000, guid: 57e4117f4cd6ae54284898652e70d553, type: 3}
bindAsDefault: 1
isAtlasV2: 1
isAtlasV2: 0
cachedData: {fileID: 0}
m_MasterAtlas: {fileID: 0}
m_PackedSprites:
- {fileID: 21300000, guid: 2761fc23b4aa7e34187ac5ffbc3fad9b, type: 3}
- {fileID: 21300000, guid: f9a06e163014f4f46b14f4499d3e7240, type: 3}
- {fileID: 21300000, guid: d623a2b7e069a4c4592d3da48f476189, type: 3}
- {fileID: 21300000, guid: 57e4117f4cd6ae54284898652e70d553, type: 3}
m_PackedSpriteNamesToIndex:
- red_button
- blue_button
- white_background
- white_button
m_RenderDataMap: {}
m_Tag: UIRaw_Atlas_Common
m_IsVariant: 0

View File

@@ -1,8 +1,8 @@
fileFormatVersion: 2
guid: b763f43bfb633944aa8955535b965c1f
guid: c91b064c2cd7a34448ae0d6d7ee58e7f
NativeFormatImporter:
externalObjects: {}
mainObjectFileID: 11400000
mainObjectFileID: 4343727234628468602
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -1,7 +0,0 @@
fileFormatVersion: 2
guid: b9eaf6bdacd0683468b1dd697e3d2bce
SpriteAtlasImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -1,16 +0,0 @@
[
{
"ResPath": "Assets/AssetRaw/Effects",
"CacheTime": 300,
"MaxPoolCnt": 30,
"PoolGoFreeTime": 300,
"MinPoolCnt": 0
},
{
"ResPath": "Assets/AssetRaw/PoolObjects/",
"CacheTime": 300,
"MaxPoolCnt": 30,
"PoolGoFreeTime": 300,
"MinPoolCnt": 0
}
]

View File

@@ -1,5 +1,5 @@
fileFormatVersion: 2
guid: f0e67891bd0f0c7449b345c622ed6b0e
guid: 3b549395c8849674b9cafbbf4c694e57
folderAsset: yes
DefaultImporter:
externalObjects: {}

View File

@@ -1,5 +1,5 @@
fileFormatVersion: 2
guid: d7f738dc5a266e94d9e9870fc76009c2
guid: 4c9eb26aee01e8643bd4e6dc965d3366
folderAsset: yes
DefaultImporter:
externalObjects: {}

View File

@@ -0,0 +1,40 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!114 &11400000
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 0}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 2f0b0c553be8edd4682e9180fdd13e37, type: 3}
m_Name: I2Languages
m_EditorClassIdentifier:
mSource:
UserAgreesToHaveItOnTheScene: 0
UserAgreesToHaveItInsideThePluginsFolder: 0
GoogleLiveSyncIsUptoDate: 1
mTerms: []
CaseInsensitiveTerms: 0
OnMissingTranslation: 1
mTerm_AppName:
mLanguages: []
IgnoreDeviceLanguage: 0
_AllowUnloadingLanguages: 0
Google_WebServiceURL:
Google_SpreadsheetKey:
Google_SpreadsheetName:
Google_LastUpdatedVersion:
Google_Password: change_this
GoogleUpdateFrequency: 3
GoogleInEditorCheckFrequency: 2
GoogleUpdateSynchronization: 1
GoogleUpdateDelay: 0
Assets: []
Spreadsheet_LocalFileName:
Spreadsheet_LocalCSVSeparator: ','
Spreadsheet_LocalCSVEncoding: utf-8
Spreadsheet_SpecializationAsRows: 1
Spreadsheet_SortRows: 1

View File

@@ -1,5 +1,5 @@
fileFormatVersion: 2
guid: a363de58f5d6e9e438b2b9a692187f6e
guid: f069f2f03dfa55843a74dedc551eefb2
NativeFormatImporter:
externalObjects: {}
mainObjectFileID: 11400000

View File

@@ -1,40 +0,0 @@
using TEngine;
namespace GameBase
{
/// <summary>
/// 用于检测耗时。
/// </summary>
public class GameTickWatcher
{
private long _startTick;
public GameTickWatcher()
{
Refresh();
}
public void Refresh()
{
_startTick = System.DateTime.Now.Ticks;
}
/// <summary>
/// 获取用时。
/// </summary>
/// <returns></returns>
public float ElapseTime()
{
long endTick = System.DateTime.Now.Ticks;
return (float)((endTick - _startTick) / 10000) / 1000.0f;
}
/// <summary>
/// 输出用时。
/// </summary>
public void LogUsedTime()
{
Log.Info($"Used Time: {this.ElapseTime()}");
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 7320165f7aa147a998a30fe2f7a5a5c2
timeCreated: 1681989139

View File

@@ -1,14 +1,14 @@
using TEngine;
using System.Diagnostics;
namespace GameBase
{
/// <summary>
/// 通用单例
/// 全局对象必须继承于此
/// </summary>
/// <typeparam name="T">泛型T。</typeparam>
public class Singleton<T> where T : new()
/// <typeparam name="T">子类类型。</typeparam>
public abstract class Singleton<T> : ISingleton where T : Singleton<T>, new()
{
private static T _instance;
protected static T _instance = default(T);
public static T Instance
{
@@ -17,11 +17,43 @@ namespace GameBase
if (null == _instance)
{
_instance = new T();
Log.Assert(_instance != null);
_instance.Init();
SingletonSystem.Retain(_instance);
}
return _instance;
}
}
public static bool IsValid => _instance != null;
protected Singleton()
{
#if UNITY_EDITOR
string st = new StackTrace().ToString();
// using const string to compare simply
if (!st.Contains("GameBase.Singleton`1[T].get_Instance"))
{
UnityEngine.Debug.LogError($"请必须通过Instance方法来实例化{typeof(T).FullName}类");
}
#endif
}
protected virtual void Init()
{
}
public virtual void Active()
{
}
public virtual void Release()
{
if (_instance != null)
{
SingletonSystem.Release(_instance);
_instance = null;
}
}
}
}

View File

@@ -0,0 +1,111 @@
using TEngine;
using UnityEngine;
namespace GameBase
{
/// <summary>
/// 全局MonoBehavior必须继承于此
/// </summary>
/// <typeparam name="T">子类类型</typeparam>
public class SingletonBehaviour<T> : MonoBehaviour where T : SingletonBehaviour<T>
{
private static T _instance;
private void Awake()
{
if (CheckInstance())
{
OnLoad();
}
}
private bool CheckInstance()
{
if (this == Instance)
{
return true;
}
Object.Destroy(gameObject);
return false;
}
protected virtual void OnLoad()
{
}
protected virtual void OnDestroy()
{
if (this == _instance)
{
Release();
}
}
/// <summary>
/// 判断对象是否有效
/// </summary>
public static bool IsValid
{
get
{
return _instance != null;
}
}
public static T Active()
{
return Instance;
}
public static void Release()
{
if (_instance != null)
{
SingletonSystem.Release(_instance.gameObject);
_instance = null;
}
}
/// <summary>
/// 实例
/// </summary>
public static T Instance
{
get
{
if (_instance == null)
{
System.Type thisType = typeof(T);
string instName = thisType.Name;
GameObject go = SingletonSystem.GetGameObject(instName);
if (go == null)
{
go = GameObject.Find($"/{instName}");
if (go == null)
{
go = new GameObject(instName);
go.transform.position = Vector3.zero;
}
SingletonSystem.Retain(go);
}
if (go != null)
{
_instance = go.GetComponent<T>();
if (_instance == null)
{
_instance = go.AddComponent<T>();
}
}
if (_instance == null)
{
Log.Error($"Can't create SingletonBehaviour<{typeof(T)}>");
}
}
return _instance;
}
}
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: bc365e281d234e61891bf9f922a0897a
timeCreated: 1715574965

View File

@@ -0,0 +1,141 @@
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.SceneManagement;
namespace GameBase
{
public interface ISingleton
{
/// <summary>
/// 激活接口,通常用于在某个时机手动实例化
/// </summary>
void Active();
/// <summary>
/// 释放接口
/// </summary>
void Release();
}
/// <summary>
/// 框架中的全局对象与Unity场景依赖相关的DontDestroyOnLoad需要统一管理方便重启游戏时清除工作
/// </summary>
public static class SingletonSystem
{
private static List<ISingleton> _singletons;
private static Dictionary<string, GameObject> _gameObjects;
public static void Retain(ISingleton go)
{
if (_singletons == null)
{
_singletons = new List<ISingleton>();
}
_singletons.Add(go);
}
public static void Retain(GameObject go)
{
if (_gameObjects == null)
{
_gameObjects = new Dictionary<string, GameObject>();
}
if (_gameObjects.TryAdd(go.name, go))
{
if (Application.isPlaying)
{
Object.DontDestroyOnLoad(go);
}
}
}
public static void Release(GameObject go)
{
if (_gameObjects != null && _gameObjects.ContainsKey(go.name))
{
_gameObjects.Remove(go.name);
Object.Destroy(go);
}
}
public static void Release(ISingleton go)
{
if (_singletons != null && _singletons.Contains(go))
{
_singletons.Remove(go);
}
}
public static void Release()
{
if (_gameObjects != null)
{
foreach (var item in _gameObjects)
{
Object.Destroy(item.Value);
}
_gameObjects.Clear();
}
if (_singletons != null)
{
for (int i = _singletons.Count -1; i >= 0; i--)
{
_singletons[i].Release();
}
_singletons.Clear();
}
Resources.UnloadUnusedAssets();
}
public static GameObject GetGameObject(string name)
{
GameObject go = null;
if (_gameObjects != null)
{
_gameObjects.TryGetValue(name, out go);
}
return go;
}
internal static bool ContainsKey(string name)
{
if (_gameObjects != null)
{
return _gameObjects.ContainsKey(name);
}
return false;
}
public static void Restart()
{
if (Camera.main != null)
{
Camera.main.gameObject.SetActive(false);
}
Release();
SceneManager.LoadScene(0);
}
internal static ISingleton GetSingleton(string name)
{
for (int i = 0; i < _singletons.Count; ++i)
{
if (_singletons[i].ToString() == name)
{
return _singletons[i];
}
}
return null;
}
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 4ad00b596d0743a4b04591fe52087d0f
timeCreated: 1715574577

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 6dd993a020654e8bbcc4e70ea0029447
timeCreated: 1695289810

View File

@@ -1,189 +0,0 @@
using System;
using System.Collections.Generic;
using TEngine;
using UnityEngine;
using UnityEngine.UI;
namespace GameLogic
{
/// <summary>
/// 红点个体行为。
/// </summary>
public class RedNoteBehaviour : UIWidget
{
public Action<bool> HaveRedNoteAction;
//当前红点类型
public RedNoteNotify RedNoteNotifyType { get; private set; }
//启用时当作标记解决带有ID创建多个类似条目的情况
public readonly List<ulong> IdParamList = new List<ulong>();
private readonly List<ulong> _tmpIdParam = new List<ulong>();
private Image _image;
private Image Image
{
get
{
if (_image == null && gameObject != null)
{
_image = gameObject.GetComponent<Image>();
}
return _image;
}
}
private Text _text;
private Text Text
{
get
{
if (_text == null && gameObject != null)
{
_text = FindChildComponent<Text>(rectTransform, "Text");
}
return _text;
}
}
private bool _state = false;
/// <summary>
/// 当前红点状态。
/// </summary>
public bool CurState
{
private set
{
_state = value;
if (Image == null)
{
gameObject.SetActive(_state);
return;
}
Color c = Image.color;
c.a = _state ? 1f : 0.01f;
Image.color = c;
if (HaveRedNoteAction != null)
{
HaveRedNoteAction(_state);
}
}
get => _state;
}
//设置显示状态
public void SetRedNoteState(bool state)
{
CurState = state;
}
// 设置红点类型
public void SetNotifyType(RedNoteNotify notifyType)
{
_tmpIdParam.Clear();
SetNotifyType(notifyType, _tmpIdParam);
}
#region
public void SetNotifyType(RedNoteNotify notifyType, ulong param1)
{
_tmpIdParam.Clear();
_tmpIdParam.Add(param1);
SetNotifyType(notifyType, _tmpIdParam);
}
public void SetNotifyType(RedNoteNotify notifyType, ulong param1, ulong param2)
{
_tmpIdParam.Clear();
_tmpIdParam.Add(param1);
_tmpIdParam.Add(param2);
SetNotifyType(notifyType, _tmpIdParam);
}
public void SetNotifyType(RedNoteNotify notifyType, ulong param1, ulong param2, ulong param3)
{
_tmpIdParam.Clear();
_tmpIdParam.Add(param1);
_tmpIdParam.Add(param2);
_tmpIdParam.Add(param3);
SetNotifyType(notifyType, _tmpIdParam);
}
public void SetNotifyType(RedNoteNotify notifyType, params ulong[] param)
{
_tmpIdParam.Clear();
for (int i = 0; i < param.Length; i++)
{
_tmpIdParam.Add(param[i]);
}
SetNotifyType(notifyType, _tmpIdParam);
}
#endregion
public void SetNotifyType(RedNoteNotify notifyType, List<ulong> paramList)
{
RemoveNotifyBind();
if (notifyType == RedNoteNotify.None) return;
IdParamList.Clear();
IdParamList.AddRange(paramList);
SetRedNoteNotifyProcess(notifyType);
}
private void SetRedNoteNotifyProcess(RedNoteNotify notifyType)
{
// 移除红点通知的绑定
if (Image != null)
{
Image.rectTransform.SetAsLastSibling();
}
RedNoteNotifyType = notifyType;
RedNoteMgr.Instance.RegisterNotify(RedNoteNotifyType, this);
if (!RedNoteMgr.Instance.IsNumType(notifyType, IdParamList))
{
CurState = RedNoteMgr.Instance.GetNotifyValue(RedNoteNotifyType, IdParamList);
}
else
{
SetRedNotePointNum(RedNoteMgr.Instance.GetNotifyPointNum(RedNoteNotifyType, IdParamList));
}
}
/// <summary>
/// 移除红点通知的绑定。
/// </summary>
public void RemoveNotifyBind()
{
if (RedNoteNotifyType != RedNoteNotify.None)
{
RedNoteMgr.Instance.UnRegisterNotify(RedNoteNotifyType, this);
}
CurState = false;
}
public override void OnDestroy()
{
RemoveNotifyBind();
}
public void SetRedNotePointNum(int pointNum)
{
if (Text != null)
{
Text.text = pointNum > 0 ? pointNum.ToString() : string.Empty;
CurState = pointNum > 0;
}
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: dba30ea267ff4b988310dec14c0df1c3
timeCreated: 1687263893

View File

@@ -1,85 +0,0 @@
using System.Collections.Generic;
namespace GameLogic
{
/// <summary> 红点关联 </summary>
public class RedNoteCheckMgr
{
public string m_ownerStr;
public List<string> m_childList { get; private set; }
public RedNoteCheckMgr(RedNoteNotify ower, List<RedNoteNotify> childList)
{
m_ownerStr = ower.ToString();
m_childList = new List<string>();
for (int i = 0; i < childList.Count; i++)
{
var value = childList[i];
m_childList.Add(value.ToString());
}
}
public RedNoteCheckMgr(string paramKey)
{
m_ownerStr = paramKey;
}
public bool AddChild(string childKey)
{
if (m_childList == null)
{
m_childList = new List<string>();
}
if (!m_childList.Contains(childKey))
{
m_childList.Add(childKey);
return true;
}
return false;
}
public void CheckChildRedNote()
{
var valueItem = RedNoteMgr.Instance.GetNotifyValueItem(m_ownerStr);
bool childHaveRed = false;
int childNotePointNum = 0;
int count = m_childList.Count;
for (var index = 0; index < count; index++)
{
var child = m_childList[index];
var childItem = RedNoteMgr.Instance.GetNotifyValueItem(child);
if (childItem.GetRedNoteType() == RedNoteType.Simple)
{
if (RedNoteMgr.Instance.GetNotifyValue(child))
{
childHaveRed = true;
childNotePointNum++;
}
}
else
{
childNotePointNum += childItem.GetRedNotePointNum();
}
}
if (valueItem.GetRedNoteType() == RedNoteType.Simple)
{
RedNoteMgr.Instance.SetNotifyKeyValue(m_ownerStr, childHaveRed);
}
else
{
RedNoteMgr.Instance.SetNotifyKeyPointNum(m_ownerStr, childNotePointNum);
}
}
public bool CheckChild(string childKey)
{
bool red = RedNoteMgr.Instance.GetNotifyValue(childKey);
return red;
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 3dd181174bbf408e9932a6f9484e41a5
timeCreated: 1687263893

View File

@@ -1,669 +0,0 @@
using System;
using System.Collections.Generic;
using System.Text;
using GameBase;
using GameLogic;
using TEngine;
using UnityEngine;
namespace GameLogic
{
#region
/// 1增加RedNoteNotify定义加入新的红点枚举。
/// 2添加红点关联关联定义在InitRelation查看当前有的关联关系确定是增加还是重新创建
/// 3把RedNoteBehaviour挂在红点图片上红点图片一般放置在需要显示红点的按钮/页签上,设置脚本上的枚举类型
/// 4如果是带参数的红点类型在红点所在的UI声明红点对象对参数进行设置参数统一为uint一般用一个可以唯一区分的ID。
/// 有多个参数时,每后一个参数节点都是前一个参数的子节点。 无参数为该层级的根节点。
/// 5红点激活/隐藏
/// 在对应模块数据管理类中检测达到红点激活条件或红点消失条件调用SetNotifyValue激活/隐藏红点
#endregion
public enum RedNoteNotify
{
None = 0,
CharacterMain,
ShopMain,
BagMain,
BagUseType,
ExploreMain,
HomeUI,
}
/// <summary>
/// 红点指引
/// </summary>
public class RedNoteMgr : Singleton<RedNoteMgr>
{
//红点状态记录
private Dictionary<string, RedNoteValueItem> _notifyMap;
//红点关联
private readonly Dictionary<string, RedNoteCheckMgr> _checkDic = new Dictionary<string, RedNoteCheckMgr>();
/// <summary>
/// child to parent list
/// </summary>
private readonly Dictionary<string, List<string>> _checkOwnDic = new Dictionary<string, List<string>>();
private readonly Dictionary<string, RedNoteKeyStruct> _keyConvertDic = new Dictionary<string, RedNoteKeyStruct>();
private readonly Dictionary<string, RedNoteStructDic> _keyDic = new Dictionary<string, RedNoteStructDic>();
/// <summary>
/// 红点映射
/// key => 红点名称
/// val => 对应的红点类型
/// </summary>
private Dictionary<string, RedNoteNotify> _dicRedNoteMap;
private Dictionary<int, string> _notifyStringMap;
public void Init()
{
InitState();
InitRedNoteConfig();
InitRelation();
InitRedNoteTween();
}
/// <summary>
/// 全局缓动缩放
/// </summary>
public Vector3 GlobalTwScale { get; protected set; }
/// <summary>
/// 初始化红点缓动
/// </summary>
private void InitRedNoteTween()
{
// LeanTween.value(LeanTween.tweenEmpty, OnRedNoteTween, 1f, 0.75f, 0.5f).setLoopPingPong();
}
/// <summary>
/// 缓动
/// </summary>
/// <param name="value"></param>
private void OnRedNoteTween(float value)
{
GlobalTwScale = value * Vector3.one;
}
//注册红点通知
public void RegisterNotify(RedNoteNotify notify, RedNoteBehaviour redNote)
{
RedNoteValueItem redNoteValueItem = GetOrNewNotifyValueItem(notify, redNote.IdParamList);
redNoteValueItem.AddRedNote(redNote);
}
//销毁红点通知
public void UnRegisterNotify(RedNoteNotify notify, RedNoteBehaviour redNote)
{
RedNoteValueItem redNoteValueItem = GetOrNewNotifyValueItem(notify, redNote.IdParamList);
if (redNoteValueItem == null)
{
return;
}
redNoteValueItem.RemoveRedNote(redNote);
}
private readonly List<ulong> _tmpRedNoteParams = new List<ulong>();
/// <summary>
/// 设置红点状态。
/// </summary>
/// <param name="notify"></param>
/// <param name="value"></param>
public void SetNotifyValue(RedNoteNotify notify, bool value)
{
_tmpRedNoteParams.Clear();
SetNotifyValue(notify, value, _tmpRedNoteParams);
}
#region bool
public void SetNotifyValue(RedNoteNotify notify, bool value, ulong param1)
{
_tmpRedNoteParams.Clear();
_tmpRedNoteParams.Add(param1);
SetNotifyValue(notify, value, _tmpRedNoteParams);
}
public void SetNotifyValue(RedNoteNotify notify, bool value, ulong param1, ulong param2)
{
_tmpRedNoteParams.Clear();
_tmpRedNoteParams.Add(param1);
_tmpRedNoteParams.Add(param2);
SetNotifyValue(notify, value, _tmpRedNoteParams);
}
public void SetNotifyValue(RedNoteNotify notify, bool value, params ulong[] param)
{
_tmpRedNoteParams.Clear();
for (var i = 0; i < param.Length; i++)
{
_tmpRedNoteParams.Add(param[i]);
}
SetNotifyValue(notify, value, _tmpRedNoteParams);
}
#endregion
public void SetNotifyValue(RedNoteNotify notify, bool value, List<ulong> redNoteParamList)
{
var key = BuildKey(notify, redNoteParamList);
if (!value && !_notifyMap.TryGetValue(key, out var redNoteValueItem))
{
return;
}
GetOrNewNotifyValueItem(notify, redNoteParamList);
MarkNotifyKeyValueDirty(key, value);
}
public void MarkNotifyKeyValueDirty(string key, bool value)
{
if (!_notifyMap.TryGetValue(key, out var redNoteValueItem))
{
return;
}
redNoteValueItem.SetStateDirty(value);
}
/// <summary>
/// 设置红点状态。
/// </summary>
/// <param name="key"></param>
/// <param name="value"></param>
public void SetNotifyKeyValue(string key, bool value)
{
if (!_notifyMap.TryGetValue(key, out var redNoteValueItem))
{
return;
}
//设置红点状态
if (redNoteValueItem.SetRedNoteState(value))
{
//设置红点关联状态
CalcRedNoteRelation(key);
}
}
//设置红点状态数量
public void SetNotifyKeyPointNum(string key, int pointNum)
{
if (!_notifyMap.TryGetValue(key, out var redNoteValueItem))
{
return;
}
if (redNoteValueItem.SetRedNotePoint(pointNum))
{
//设置红点关联状态
CalcRedNoteRelation(key);
}
}
public bool GetNotifyValue(RedNoteNotify notify, ulong param1)
{
_tmpRedNoteParams.Clear();
_tmpRedNoteParams.Add(param1);
return GetNotifyValue(notify, _tmpRedNoteParams);
}
public bool GetNotifyValue(RedNoteNotify notify, ulong param1, ulong param2)
{
_tmpRedNoteParams.Clear();
_tmpRedNoteParams.Add(param1);
_tmpRedNoteParams.Add(param2);
return GetNotifyValue(notify, _tmpRedNoteParams);
}
/// <summary>
/// 获取红点状态。
/// </summary>
/// <param name="notify"></param>
/// <param name="param"></param>
/// <returns></returns>
public bool GetNotifyValue(RedNoteNotify notify, List<ulong> param = null)
{
if (notify == (uint)RedNoteNotify.None)
return false;
RedNoteValueItem item = GetOrNewNotifyValueItem(notify, param);
return item.GetRedNoteState();
}
/// <summary>
/// 获取红点数量。
/// </summary>
/// <param name="notify"></param>
/// <param name="param"></param>
/// <returns></returns>
public int GetNotifyPointNum(RedNoteNotify notify, List<ulong> param)
{
if (notify == (uint)RedNoteNotify.None)
return 0;
RedNoteValueItem item = GetOrNewNotifyValueItem(notify, param);
return item.GetRedNotePointNum();
}
public bool GetNotifyValue(string paramKey)
{
if (_notifyMap.TryGetValue(paramKey, out var redNoteValueItem))
{
return redNoteValueItem.GetRedNoteState();
}
return false;
}
/// <summary>
/// 清理红点状态.
/// </summary>
/// <param name="notify"></param>
public void ClearNotifyValue(RedNoteNotify notify)
{
var notifyStr = NotifyTypeToString(notify);
RecursiveClearNotifyKeyValue(notifyStr);
RedNoteValueItem redNoteValueItem = GetNotifyValueItem(notifyStr);
redNoteValueItem.ClearRedNoteState(false);
CalcRedNoteRelation(notifyStr);
}
public void RecursiveClearNotifyKeyValue(string key)
{
if (!_checkDic.TryGetValue(key, out var checkMgr))
{
return;
}
var childList = checkMgr.m_childList;
foreach (var childKey in childList)
{
RedNoteValueItem redNoteValueItem = GetNotifyValueItem(childKey);
redNoteValueItem.ClearRedNoteState(false);
RecursiveClearNotifyKeyValue(childKey);
}
}
/// <summary>
/// 清理数据。
/// </summary>
public void OnRoleLogout()
{
var enumerator = _notifyMap.GetEnumerator();
while (enumerator.MoveNext())
{
enumerator.Current.Value.ClearRedNoteState(true);
}
enumerator.Dispose();
}
public string NotifyTypeToString(RedNoteNotify notify)
{
_notifyStringMap.TryGetValue((int)notify, out var str);
return str;
}
public string BuildKey(RedNoteNotify notifyType, List<ulong> paramList)
{
var notifyStr = NotifyTypeToString(notifyType);
if (notifyStr == null)
{
Log.Error("RedNoteNotifyId :{0} Not Exit! Please Check", notifyType.ToString());
return string.Empty;
}
if (!_keyDic.TryGetValue(notifyStr, out var dicData))
{
dicData = new RedNoteStructDic();
_keyDic[notifyStr] = dicData;
}
var key = dicData.TryGetKey(notifyStr, paramList);
return key;
}
public static string GetKeyString(string notify, List<ulong> paramList)
{
if (paramList == null || paramList.Count == 0)
{
return notify;
}
string key;
if (paramList.Count <= 1)
{
key = $"{notify}-{paramList[0]}";
}
else if (paramList.Count <= 2)
{
key = $"{notify}-{paramList[0]}-{paramList[1]}";
}
else if (paramList.Count <= 3)
{
key = $"{notify}-{paramList[0]}-{paramList[1]}-{paramList[2]}";
}
else
{
StringBuilder s = new StringBuilder();
s.Append(notify + "-");
for (var i = 0; i < paramList.Count; i++)
{
s.Append(paramList[i]);
if (i != paramList.Count - 1)
s.Append("-");
}
key = s.ToString();
}
return key;
}
public void SetKeyConvertDic(string key, RedNoteKeyStruct keyStruct)
{
_keyConvertDic[key] = keyStruct;
}
private readonly List<ulong> _tmpParamList = new List<ulong>();
/// <summary>
/// 计算红点关联.
/// </summary>
/// <param name="notifyKey"></param>
private void CalcRedNoteRelation(string notifyKey)
{
var key = notifyKey;
if (_checkOwnDic.TryGetValue(key, out var ownerList))
{
foreach (var owner in ownerList)
{
if (_checkDic.TryGetValue(owner, out var checker))
{
checker.CheckChildRedNote();
}
}
}
}
/// <summary>
/// 初始化红点状态.
/// </summary>
private void InitState()
{
var array = (RedNoteNotify[])Enum.GetValues(typeof(RedNoteNotify));
var redNoteCnt = array.Length;
_notifyMap = new Dictionary<string, RedNoteValueItem>();
_dicRedNoteMap = new Dictionary<string, RedNoteNotify>(redNoteCnt);
_notifyStringMap = new Dictionary<int, string>(redNoteCnt);
foreach (var redNoteNotify in array)
{
var redNoteStr = redNoteNotify.ToString();
_dicRedNoteMap.Add(redNoteStr, redNoteNotify);
_notifyStringMap.Add((int)redNoteNotify, redNoteStr);
var key = BuildKey(redNoteNotify, _tmpParamList);
var redNoteValueItem = new RedNoteValueItem();
bool isNumType = IsNumType(redNoteNotify, null);
redNoteValueItem.Init(key, isNumType ? RedNoteType.WithNum : RedNoteType.Simple);
_notifyMap.Add(key, redNoteValueItem);
}
}
public RedNoteValueItem GetNotifyValueItem(string key)
{
_notifyMap.TryGetValue(key, out var redNoteValueItem);
return redNoteValueItem;
}
private RedNoteValueItem GetOrNewNotifyValueItem(RedNoteNotify notify, List<ulong> paramList)
{
var key = BuildKey(notify, paramList);
var redNoteValueItem = GetNotifyValueItem(key);
if (redNoteValueItem == null)
{
List<ulong> tmpParamList = new List<ulong>(paramList);
//从后往前创建item如(A, 1, 2)会创建A-1-2A-1A。
string lastChildKey = string.Empty;
int paramIndex = paramList.Count;
while (paramIndex >= 0)
{
var keyStr = BuildKey(notify, tmpParamList);
if (!_notifyMap.ContainsKey(keyStr))
{
RedNoteValueItem noteValueItem = new RedNoteValueItem();
bool isNumType = IsNumType(notify, paramList);
noteValueItem.Init(keyStr, isNumType ? RedNoteType.WithNum : RedNoteType.Simple);
_notifyMap.Add(keyStr, noteValueItem);
}
//叶子节点跳过(因为他没有子节点)
if (tmpParamList.Count < paramList.Count)
{
bool addedChild;
if (!_checkDic.TryGetValue(keyStr, out var checkMgr))
{
checkMgr = new RedNoteCheckMgr(keyStr);
addedChild = checkMgr.AddChild(lastChildKey);
}
else
{
addedChild = checkMgr.AddChild(lastChildKey);
}
if (addedChild)
{
AddDic(checkMgr); //重新生成父子关系
}
}
lastChildKey = keyStr;
paramIndex--;
if (paramIndex < tmpParamList.Count && tmpParamList.Count > 0)
{
tmpParamList.RemoveAt(paramIndex);
}
}
redNoteValueItem = _notifyMap[key];
}
return redNoteValueItem;
}
public void AddDic(RedNoteNotify owner, List<RedNoteNotify> childList)
{
AddDic(new RedNoteCheckMgr(owner, childList));
}
private void AddDic(RedNoteCheckMgr checker)
{
var owner = checker.m_ownerStr;
_checkDic[owner] = checker;
var childList = checker.m_childList;
int count = childList.Count;
for (int i = 0; i < count; i++)
{
var child = childList[i];
if (!_checkOwnDic.TryGetValue(child, out var ownerList))
{
ownerList = new List<string>();
_checkOwnDic[child] = ownerList;
}
if (!ownerList.Contains(owner))
{
ownerList.Add(owner);
}
}
}
public bool IsNumType(RedNoteNotify noteNotify, List<ulong> paramList)
{
if (paramList is { Count: > 0 })
{
return false;
}
return false;
}
// 通过名字获取红点类型
public static RedNoteNotify GetRedNoteByName(string redNoteName)
{
Instance._dicRedNoteMap.TryGetValue(redNoteName, out var redNote);
return redNote;
}
public void OnUpdate()
{
foreach (var redNoteValueItem in _notifyMap)
{
redNoteValueItem.Value.CheckDirty();
}
}
#region
/// <summary>
/// 初始化红点配置表
/// </summary>
private void InitRedNoteConfig()
{
// ResDictionaryList<uint, RedNoteConfig> cfgs = new ResDictionaryList<uint, RedNoteConfig>();
// cfgs.Init(val => val.RedNoteParentID);
// List<RedNoteNotify> list = new List<RedNoteNotify>();
// foreach (var kv in cfgs.Data)
// {
// list.Clear();
// foreach (var cfg in kv.Value)
// {
// list.Add((RedNoteNotify)cfg.RedNoteID);
// }
//
// AddDic((RedNoteNotify)kv.Key, list);
// }
}
//初始化红点关联
private void InitRelation()
{
}
#endregion
}
}
public class RedNoteStructDic
{
private readonly List<RedNoteKeyStruct> _keyStructList = new List<RedNoteKeyStruct>();
public string TryGetKey(string notify, List<ulong> paramList)
{
string key = string.Empty;
List<RedNoteKeyStruct> list = _keyStructList;
{
int count = list.Count;
for (int i = 0; i < count; i++)
{
var keyStruct = list[i];
if (keyStruct.IsSame(notify, paramList))
{
key = keyStruct.Key;
break;
}
}
}
if (string.IsNullOrEmpty(key))
{
var keyStruct = new RedNoteKeyStruct(notify, paramList);
key = keyStruct.Key;
RedNoteMgr.Instance.SetKeyConvertDic(key, keyStruct);
list.Add(keyStruct);
}
return key;
}
}
public class RedNoteKeyStruct
{
public string Notify;
public List<ulong> ParamList;
public RedNoteKeyStruct(string notify, List<ulong> paramList)
{
Notify = notify;
if (paramList != null)
{
ParamList = new List<ulong>(paramList);
}
else
{
ParamList = new List<ulong>();
}
}
private string _key;
public string Key
{
get
{
if (string.IsNullOrEmpty(_key))
{
_key = RedNoteMgr.GetKeyString(Notify, ParamList);
}
return _key;
}
}
public bool IsSame(string notify, List<ulong> paramList)
{
if (notify != Notify)
{
return false;
}
var list1 = paramList;
var list2 = ParamList;
int cnt1 = list1?.Count ?? 0;
int cnt2 = list2?.Count ?? 0;
if (cnt1 != cnt2)
{
return false;
}
if (cnt1 == 0)
{
return true;
}
for (int i = 0; i < cnt1; i++)
{
// ReSharper disable PossibleNullReferenceException
if (list1[i] != list2[i])
{
return false;
}
}
return true;
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 66ededab0a1e409588f150be58193032
timeCreated: 1687263893

View File

@@ -1,159 +0,0 @@
using System.Collections.Generic;
namespace GameLogic
{
public class RedNoteValueItem
{
public string m_key;
//所有关联的红点UI
private HashSet<RedNoteBehaviour> m_redNoteDic = new HashSet<RedNoteBehaviour>();
private bool m_state;
private int m_pointNum;
private RedNoteType m_noteType;
private bool m_dirty;
private bool m_tmpState;
public void Init(string keyStr, RedNoteType noteType)
{
m_key = keyStr;
m_noteType = noteType;
}
//添加红点对象
public void AddRedNote(RedNoteBehaviour redNote)
{
m_redNoteDic.Add(redNote);
}
//移除对象
public void RemoveRedNote(RedNoteBehaviour redNote)
{
m_redNoteDic.Remove(redNote);
}
//获取具体对象的状态
public bool GetRedNoteState()
{
if (m_dirty)
{
return m_tmpState;
}
return m_state;
}
//获取具体对象的红点数
public int GetRedNotePointNum()
{
return m_pointNum;
}
public RedNoteType GetRedNoteType()
{
return m_noteType;
}
public void SetStateDirty(bool state)
{
m_dirty = m_state != state;
m_tmpState = state;
}
//设置对象状态
public bool SetRedNoteState(bool state)
{
bool chg = state != m_state;
m_state = state;
if (chg)
{
SetBehaviourState(state);
}
return chg;
}
public bool SetRedNotePoint(int num)
{
if (m_pointNum != num)
{
m_pointNum = num;
SetBehaviourPoint(num);
return true;
}
return false;
}
private void SetBehaviourState(bool state)
{
//检查是否注册过具体对象
foreach (var redNote in m_redNoteDic)
{
if (redNote == null || redNote.gameObject == null)
continue;
redNote.SetRedNoteState(state);
}
// 移除空的红点
ClearTheNullRedNote();
}
private void SetBehaviourPoint(int pointNum)
{
foreach (var redNote in m_redNoteDic)
{
if (redNote == null || redNote.gameObject == null)
continue;
redNote.SetRedNotePointNum(pointNum);
}
// 移除空的红点
ClearTheNullRedNote();
}
// 移除空的红点
private void ClearTheNullRedNote()
{
m_redNoteDic.RemoveWhere(redNote => redNote == null || redNote.gameObject == null);
}
//清理状态
public void ClearRedNoteState(bool clearBehavior)
{
foreach (var redNote in m_redNoteDic)
{
if (redNote != null)
{
redNote.SetRedNoteState(false);
}
}
if (clearBehavior)
{
m_redNoteDic.Clear();
}
m_state = false;
m_dirty = false;
m_tmpState = false;
}
public void CheckDirty()
{
if (m_dirty)
{
m_dirty = false;
RedNoteMgr.Instance.SetNotifyKeyValue(m_key, m_tmpState);
}
}
}
public enum RedNoteType
{
Simple,
WithNum,
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 3c29f4a552c34bd8ab9d2c64b5b2b49d
timeCreated: 1687263893

View File

@@ -1,57 +0,0 @@
using TEngine;
using UnityEngine;
using UnityEngine.UI;
namespace GameLogic
{
public class RedNoteWidget : UIWidget
{
#region
public override void ScriptGenerator()
{
}
#endregion
private Image m_image;
public RedNoteBehaviour m_redNote;
public override void OnCreate()
{
m_redNote = CreateWidget<RedNoteBehaviour>(gameObject);
m_image = gameObject.GetComponent<Image>();
rectTransform.anchoredPosition = Vector2.zero;
SetNotifyState(false);
}
public void SetNotifyType(RedNoteNotify notifyType)
{
m_redNote.SetNotifyType(notifyType);
}
public void SetNotifyType(RedNoteNotify notifyType, ulong param1)
{
m_redNote.SetNotifyType(notifyType, param1);
}
public void SetNotifyType(RedNoteNotify notifyType, ulong param1, ulong param2)
{
m_redNote.SetNotifyType(notifyType, param1, param2);
}
public void SetNotifyState(bool state)
{
m_redNote.SetRedNoteState(state);
}
public void SetSprite(string sprite)
{
m_image.SetSprite(sprite);
}
public override void OnUpdate()
{
/*if (!m_redNote.CurState)
{
return;
}
gameObject.transform.localScale = RedNoteMgr.Instance.GlobalTwScale;*/
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 2644c5700a07442a995008ee9fa8159d
timeCreated: 1695289825

View File

@@ -1,49 +0,0 @@
using UnityEngine;
namespace TEngine
{
/// <summary>
/// 封装一个角色可能用到的各种shader场景。
/// </summary>
class ActorShaderGroup
{
private readonly TShader[] _allShader = new TShader[(int)ActorShaderEnvType.EnvTypeMax];
/// <summary>
/// 增加Shader到角色Shader分组。
/// </summary>
/// <param name="shaderType">当前环境类型。</param>
/// <param name="shader">TShader。</param>
public void AddShader(ActorShaderEnvType shaderType, TShader shader)
{
_allShader[(int)shaderType] = shader;
}
/// <summary>
/// 根据当前环境获取Shader。
/// </summary>
/// <param name="type">当前环境类型。</param>
/// <returns>TShader。</returns>
public TShader GetShader(ActorShaderEnvType type)
{
return _allShader[(int)type];
}
/// <summary>
/// 判断是否符合shader集合。
/// </summary>
/// <param name="shader">Shader实例。</param>
/// <returns>是否符合。</returns>
public bool IsMatch(Shader shader)
{
foreach (var dodShader in _allShader)
{
if (dodShader != null && dodShader.Shader == shader)
{
return true;
}
}
return false;
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 79b6e5be73e14c929b6a3b4a980976ac
timeCreated: 1701916950

View File

@@ -1,117 +0,0 @@
using GameBase;
using UnityEngine;
namespace TEngine
{
enum ActorShaderGroupType
{
/// <summary>
/// 通用的角色shader
/// </summary>
Brdf = 0,
/// <summary>
/// 眼睛
/// </summary>
BrdfEye,
///可能后面扩展,比如特效的特殊角色材质
GroupMax,
}
enum ActorShaderEnvType
{
/// <summary>
/// 游戏内场景默认模型不带阴影不带xray不透明效果
/// </summary>
EnvNormal = 0,
/// <summary>
/// 展示场景
/// </summary>
EnvShow,
/// <summary>
/// 带阴影
/// </summary>
EnvShadow,
/// <summary>
/// 带xray默认也带Shadow
/// </summary>
EnvXRay,
/// <summary>
/// 透明渐隐效果
/// </summary>
EnvAlphaFade,
/// <summary>
/// 展示场景没shadow
/// </summary>
EnvShow_NoShadow,
EnvTypeMax
}
/// <summary>
/// 角色Shader管理器。
/// </summary>
class ActorShaderMgr : Singleton<ActorShaderMgr>
{
private readonly ActorShaderGroup[] _allShaderGroup = new ActorShaderGroup[(int)ActorShaderGroupType.GroupMax];
public ActorShaderMgr()
{
CreateBrdfShader();
}
/// <summary>
/// 根据当前Render查找角色的Shader分组。
/// </summary>
/// <param name="render">Render。</param>
/// <returns>角色的Shader分组。</returns>
public ActorShaderGroup FindShaderGroup(Renderer render)
{
var sharedMat = render.sharedMaterial;
if (sharedMat == null)
{
return null;
}
var shader = sharedMat.shader;
foreach (var group in _allShaderGroup)
{
if (group != null && group.IsMatch(shader))
{
return group;
}
}
return null;
}
private void CreateBrdfShader()
{
//通用的效果
var actorShader = new ActorShaderGroup();
actorShader.AddShader(ActorShaderEnvType.EnvNormal, new TShader("TEngine/Actor/ActorBrdf",shaderLocation:"ActorBrdf"));
actorShader.AddShader(ActorShaderEnvType.EnvShow, new TShader("TEngine/Actor/Show/ActorBrdf",shaderLocation:"ActorBrdf_Show"));
actorShader.AddShader(ActorShaderEnvType.EnvShow_NoShadow, new TShader("TEngine/Actor/Show/ActorBrdf_NoShadow",shaderLocation:"ActorBrdf_NoShadow"));
actorShader.AddShader(ActorShaderEnvType.EnvShadow, new TShader("TEngine/Actor/ActorBrdf",shaderLocation:"ActorBrdf_Normal"));
actorShader.AddShader(ActorShaderEnvType.EnvXRay, new TShader("TEngine/Actor/X-Ray",shaderLocation:"X-Ray"));
actorShader.AddShader(ActorShaderEnvType.EnvAlphaFade, new TShader("TEngine/Actor/Fade/ActorBrdf",shaderLocation:"ActorBrdf_Fade"));
_allShaderGroup[(int)ActorShaderGroupType.Brdf] = actorShader;
//眼睛效果
actorShader = new ActorShaderGroup();
actorShader.AddShader(ActorShaderEnvType.EnvNormal, new TShader("TEngine/Actor/ActorEye",shaderLocation:"ActorEye"));
actorShader.AddShader(ActorShaderEnvType.EnvShow, new TShader("TEngine/Actor/Show/ActorEye",shaderLocation:"ActorEye_Show", "MRT_DISABLE", "MRT_ENABLE"));
actorShader.AddShader(ActorShaderEnvType.EnvShadow, new TShader("TEngine/Actor/ActorEye",shaderLocation:"ActorEye"));
actorShader.AddShader(ActorShaderEnvType.EnvXRay, new TShader("TEngine/Actor/ActorEye",shaderLocation:"ActorEye"));
actorShader.AddShader(ActorShaderEnvType.EnvAlphaFade, new TShader("TEngine/Actor/Fade/ActorEye",shaderLocation:"ActorEye_Fade"));
_allShaderGroup[(int)ActorShaderGroupType.BrdfEye] = actorShader;
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 5a38b9b4bee84fabb1ef8db5292a6db6
timeCreated: 1701916853

View File

@@ -1,154 +0,0 @@
using System.Collections.Generic;
using UnityEngine;
namespace TEngine
{
/// <summary>
/// TShader scripts used for all rendering.
/// <remarks>统一封装对shader的管理。</remarks>
/// </summary>
public class TShader
{
private bool _loaded;
private Shader _shader;
private readonly string _shaderName;
private readonly string _shaderLocation;
private readonly List<string> _keywordOn = new List<string>();
private readonly List<string> _keywordOff = new List<string>();
/// <summary>
/// Shader scripts used for all rendering.
/// </summary>
public Shader Shader
{
get
{
if (!_loaded)
{
_loaded = true;
_shader = FindShader(_shaderLocation,_shaderName);
if (_shader == null)
{
Log.Error($"invalid shader path: {_shaderLocation}, shader name {_shaderName}");
}
}
return _shader;
}
}
/// <summary>
/// 查找Shader。
/// </summary>
/// <param name="shaderLocation">Shader定位地址。</param>
/// <param name="shaderName">Shader名称。</param>
/// <returns>Shader实例。</returns>
public static Shader FindShader(string shaderLocation,string shaderName)
{
Shader shader = GameModule.Resource.LoadAsset<Shader>(shaderLocation);
if (shader != null)
{
return shader;
}
return Shader.Find(shaderName);
}
/// <summary>
/// TShader构造函数。
/// </summary>
/// <param name="shaderName">shader名称。</param>
/// <param name="shaderLocation">shader路径。</param>
public TShader(string shaderName, string shaderLocation)
{
_shaderName = shaderName;
_shaderLocation = shaderLocation;
_shader = null;
}
/// <summary>
/// TShader构造函数。
/// </summary>
/// <param name="shaderName">shader名称。</param>
/// <param name="shaderLocation">shader路径。</param>
/// <param name="keywordOn">开启选项。</param>
/// <param name="keywordOff">关闭选项。</param>
public TShader(string shaderName, string shaderLocation, string keywordOn, string keywordOff)
{
_shaderName = shaderName;
_shaderLocation = shaderLocation;
_shader = null;
_keywordOn.Add(keywordOn);
_keywordOff.Add(keywordOff);
}
/// <summary>
/// TShader构造函数。
/// </summary>
/// <param name="shaderName">shader名称。</param>
/// <param name="shaderLocation">shader路径。</param>
/// <param name="keywordOn">开启选项。</param>
/// <param name="keywordOff">关闭选项。</param>
public TShader(string shaderName, string shaderLocation, string[] keywordOn, string[] keywordOff)
{
_shaderName = shaderName;
_shaderLocation = shaderLocation;
_shader = null;
_keywordOn.AddRange(keywordOn);
_keywordOff.AddRange(keywordOff);
}
/// <summary>
/// 设置Shader效果。
/// </summary>
/// <param name="render">渲染对象。</param>
public void ApplyRender(Renderer render)
{
var sharedMat = render.sharedMaterial;
if (sharedMat != null)
{
//copy一份材质
sharedMat = render.material;
sharedMat.shader = Shader;
foreach (var keyword in _keywordOff)
{
sharedMat.DisableKeyword(keyword);
}
foreach (var keyword in _keywordOn)
{
sharedMat.EnableKeyword(keyword);
}
}
}
/// <summary>
/// 清除shader。
/// </summary>
/// <param name="render">渲染对象。</param>
public void ClearRender(Renderer render)
{
if (_keywordOff.Count <= 0 && _keywordOn.Count <= 0)
{
return;
}
var sharedMat = render.sharedMaterial;
if (sharedMat != null)
{
//copy一份材质。
sharedMat = render.material;
for (int k = 0; k < _keywordOn.Count; k++)
{
sharedMat.DisableKeyword(_keywordOn[k]);
}
for (int k = 0; k < _keywordOff.Count; k++)
{
sharedMat.EnableKeyword(_keywordOff[k]);
}
}
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: e219233984c14f7d97bc744c07fe13d0
timeCreated: 1698115491

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 8a214e54975b4d7da2d804f869524801
timeCreated: 1695289293

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 0615e8b32d534bc48a60e42c973053ad
timeCreated: 1695289443

View File

@@ -1,84 +0,0 @@
using UnityEngine;
using UnityEngine.EventSystems;
namespace GameLogic
{
public class ClickEventListener : MonoBehaviour, IPointerClickHandler, IPointerDownHandler, IPointerUpHandler
{
public static ClickEventListener Get(GameObject obj)
{
ClickEventListener listener = obj.GetComponent<ClickEventListener>();
if (listener == null)
{
listener = obj.AddComponent<ClickEventListener>();
}
return listener;
}
private System.Action<GameObject> _clickedHandler = null;
private System.Action<GameObject> _doubleClickedHandler = null;
private System.Action<GameObject> _onPointerDownHandler = null;
private System.Action<GameObject> _onPointerUpHandler = null;
bool _isPressed = false;
public bool IsPressed => _isPressed;
public void OnPointerClick(PointerEventData eventData)
{
if (eventData.clickCount == 2)
{
if (_doubleClickedHandler != null)
{
_doubleClickedHandler(gameObject);
}
}
else
{
if (_clickedHandler != null)
{
_clickedHandler(gameObject);
}
}
}
public void SetClickEventHandler(System.Action<GameObject> handler)
{
_clickedHandler = handler;
}
public void SetDoubleClickEventHandler(System.Action<GameObject> handler)
{
_doubleClickedHandler = handler;
}
public void SetPointerDownHandler(System.Action<GameObject> handler)
{
_onPointerDownHandler = handler;
}
public void SetPointerUpHandler(System.Action<GameObject> handler)
{
_onPointerUpHandler = handler;
}
public void OnPointerDown(PointerEventData eventData)
{
_isPressed = true;
if (_onPointerDownHandler != null)
{
_onPointerDownHandler(gameObject);
}
}
public void OnPointerUp(PointerEventData eventData)
{
_isPressed = false;
if (_onPointerUpHandler != null)
{
_onPointerUpHandler(gameObject);
}
}
}
}

View File

@@ -1,86 +0,0 @@
using System;
using System.Collections.Generic;
namespace GameLogic
{
public enum SnapStatus
{
NoTargetSet = 0,
TargetHasSet = 1,
SnapMoving = 2,
SnapMoveFinish = 3
}
public enum ItemCornerEnum
{
LeftBottom = 0,
LeftTop,
RightTop,
RightBottom,
}
public enum ListItemArrangeType
{
TopToBottom = 0,
BottomToTop,
LeftToRight,
RightToLeft,
}
public enum GridItemArrangeType
{
TopLeftToBottomRight = 0,
BottomLeftToTopRight,
TopRightToBottomLeft,
BottomRightToTopLeft,
}
public enum GridFixedType
{
ColumnCountFixed = 0,
RowCountFixed,
}
public struct RowColumnPair
{
public RowColumnPair(int row1, int column1)
{
mRow = row1;
mColumn = column1;
}
public bool Equals(RowColumnPair other)
{
return this.mRow == other.mRow && this.mColumn == other.mColumn;
}
public static bool operator ==(RowColumnPair a, RowColumnPair b)
{
return (a.mRow == b.mRow)&&(a.mColumn == b.mColumn);
}
public static bool operator !=(RowColumnPair a, RowColumnPair b)
{
return (a.mRow != b.mRow) || (a.mColumn != b.mColumn); ;
}
public override int GetHashCode()
{
return 0;
}
public override bool Equals(object obj)
{
if (ReferenceEquals(null, obj))
{
return false;
}
return (obj is RowColumnPair) && Equals((RowColumnPair)obj);
}
public int mRow;
public int mColumn;
}
}

View File

@@ -1,326 +0,0 @@
using System;
using System.Collections.Generic;
namespace GameLogic
{
public class ItemSizeGroup
{
public float[] ItemSizeArray = null;
public float[] ItemStartPosArray = null;
public int ItemCount = 0;
private int _dirtyBeginIndex = ItemPosMgr.ItemMaxCountPerGroup;
public float GroupSize = 0;
public float GroupStartPos = 0;
public float GroupEndPos = 0;
public int GroupIndex = 0;
public float ItemDefaultSize = 0;
public ItemSizeGroup(int index, float itemDefaultSize)
{
GroupIndex = index;
ItemDefaultSize = itemDefaultSize;
Init();
}
public void Init()
{
ItemSizeArray = new float[ItemPosMgr.ItemMaxCountPerGroup];
if (ItemDefaultSize != 0)
{
for (int i = 0; i < ItemSizeArray.Length; ++i)
{
ItemSizeArray[i] = ItemDefaultSize;
}
}
ItemStartPosArray = new float[ItemPosMgr.ItemMaxCountPerGroup];
ItemStartPosArray[0] = 0;
ItemCount = ItemPosMgr.ItemMaxCountPerGroup;
GroupSize = ItemDefaultSize * ItemSizeArray.Length;
if (ItemDefaultSize != 0)
{
_dirtyBeginIndex = 0;
}
else
{
_dirtyBeginIndex = ItemPosMgr.ItemMaxCountPerGroup;
}
}
public float GetItemStartPos(int index)
{
return GroupStartPos + ItemStartPosArray[index];
}
public bool IsDirty
{
get { return (_dirtyBeginIndex < ItemCount); }
}
public float SetItemSize(int index, float size)
{
float old = ItemSizeArray[index];
if (Math.Abs(old - size) < 0.001f)
{
return 0;
}
ItemSizeArray[index] = size;
if (index < _dirtyBeginIndex)
{
_dirtyBeginIndex = index;
}
float ds = size - old;
GroupSize = GroupSize + ds;
return ds;
}
public void SetItemCount(int count)
{
if (ItemCount == count)
{
return;
}
ItemCount = count;
RecalcGroupSize();
}
public void RecalcGroupSize()
{
GroupSize = 0;
for (int i = 0; i < ItemCount; ++i)
{
GroupSize += ItemSizeArray[i];
}
}
public int GetItemIndexByPos(float pos)
{
if (ItemCount == 0)
{
return -1;
}
int low = 0;
int high = ItemCount - 1;
while (low <= high)
{
int mid = (low + high) / 2;
float startPos = ItemStartPosArray[mid];
float endPos = startPos + ItemSizeArray[mid];
if (startPos <= pos && endPos >= pos)
{
return mid;
}
else if (pos > endPos)
{
low = mid + 1;
}
else
{
high = mid - 1;
}
}
return -1;
}
public void UpdateAllItemStartPos()
{
if (_dirtyBeginIndex >= ItemCount)
{
return;
}
int startIndex = (_dirtyBeginIndex < 1) ? 1 : _dirtyBeginIndex;
for (int i = startIndex; i < ItemCount; ++i)
{
ItemStartPosArray[i] = ItemStartPosArray[i - 1] + ItemSizeArray[i - 1];
}
_dirtyBeginIndex = ItemCount;
}
}
public class ItemPosMgr
{
public const int ItemMaxCountPerGroup = 100;
readonly List<ItemSizeGroup> _itemSizeGroupList = new List<ItemSizeGroup>();
public int _dirtyBeginIndex = int.MaxValue;
public float TotalSize = 0;
public float ItemDefaultSize = 20;
public ItemPosMgr(float itemDefaultSize)
{
ItemDefaultSize = itemDefaultSize;
}
public void SetItemMaxCount(int maxCount)
{
_dirtyBeginIndex = 0;
TotalSize = 0;
int st = maxCount % ItemMaxCountPerGroup;
int lastGroupItemCount = st;
int needMaxGroupCount = maxCount / ItemMaxCountPerGroup;
if (st > 0)
{
needMaxGroupCount++;
}
else
{
lastGroupItemCount = ItemMaxCountPerGroup;
}
int count = _itemSizeGroupList.Count;
if (count > needMaxGroupCount)
{
int d = count - needMaxGroupCount;
_itemSizeGroupList.RemoveRange(needMaxGroupCount, d);
}
else if (count < needMaxGroupCount)
{
int d = needMaxGroupCount - count;
for (int i = 0; i < d; ++i)
{
ItemSizeGroup tGroup = new ItemSizeGroup(count + i, ItemDefaultSize);
_itemSizeGroupList.Add(tGroup);
}
}
count = _itemSizeGroupList.Count;
if (count == 0)
{
return;
}
for (int i = 0; i < count - 1; ++i)
{
_itemSizeGroupList[i].SetItemCount(ItemMaxCountPerGroup);
}
_itemSizeGroupList[count - 1].SetItemCount(lastGroupItemCount);
for (int i = 0; i < count; ++i)
{
TotalSize = TotalSize + _itemSizeGroupList[i].GroupSize;
}
}
public void SetItemSize(int itemIndex, float size)
{
int groupIndex = itemIndex / ItemMaxCountPerGroup;
int indexInGroup = itemIndex % ItemMaxCountPerGroup;
ItemSizeGroup tGroup = _itemSizeGroupList[groupIndex];
float changedSize = tGroup.SetItemSize(indexInGroup, size);
if (changedSize != 0f)
{
if (groupIndex < _dirtyBeginIndex)
{
_dirtyBeginIndex = groupIndex;
}
}
TotalSize += changedSize;
}
public float GetItemPos(int itemIndex)
{
Update(true);
int groupIndex = itemIndex / ItemMaxCountPerGroup;
int indexInGroup = itemIndex % ItemMaxCountPerGroup;
return _itemSizeGroupList[groupIndex].GetItemStartPos(indexInGroup);
}
public void GetItemIndexAndPosAtGivenPos(float pos, ref int index, ref float itemPos)
{
Update(true);
index = 0;
itemPos = 0f;
int count = _itemSizeGroupList.Count;
if (count == 0)
{
return;
}
ItemSizeGroup hitGroup = null;
int low = 0;
int high = count - 1;
while (low <= high)
{
int mid = (low + high) / 2;
ItemSizeGroup tGroup = _itemSizeGroupList[mid];
if (tGroup.GroupStartPos <= pos && tGroup.GroupEndPos >= pos)
{
hitGroup = tGroup;
break;
}
else if (pos > tGroup.GroupEndPos)
{
low = mid + 1;
}
else
{
high = mid - 1;
}
}
int hitIndex = -1;
if (hitGroup != null)
{
hitIndex = hitGroup.GetItemIndexByPos(pos - hitGroup.GroupStartPos);
}
else
{
return;
}
if (hitIndex < 0)
{
return;
}
index = hitIndex + hitGroup.GroupIndex * ItemMaxCountPerGroup;
itemPos = hitGroup.GetItemStartPos(hitIndex);
}
public void Update(bool updateAll)
{
int count = _itemSizeGroupList.Count;
if (count == 0)
{
return;
}
if (_dirtyBeginIndex >= count)
{
return;
}
int loopCount = 0;
for (int i = _dirtyBeginIndex; i < count; ++i)
{
loopCount++;
ItemSizeGroup tGroup = _itemSizeGroupList[i];
_dirtyBeginIndex++;
tGroup.UpdateAllItemStartPos();
if (i == 0)
{
tGroup.GroupStartPos = 0;
tGroup.GroupEndPos = tGroup.GroupSize;
}
else
{
tGroup.GroupStartPos = _itemSizeGroupList[i - 1].GroupEndPos;
tGroup.GroupEndPos = tGroup.GroupStartPos + tGroup.GroupSize;
}
if (!updateAll && loopCount > 1)
{
return;
}
}
}
}
}

View File

@@ -1,173 +0,0 @@
namespace GameLogic
{
//if GridFixedType is GridFixedType.ColumnCountFixed, then the GridItemGroup is one row of the gridview
//if GridFixedType is GridFixedType.RowCountFixed, then the GridItemGroup is one column of the gridview
public class GridItemGroup
{
private int _count = 0;
private int _groupIndex = -1;//the row index or the column index of this group
private LoopGridViewItem _first = null;
private LoopGridViewItem _last = null;
public int Count => _count;
public LoopGridViewItem First => _first;
public LoopGridViewItem Last => _last;
public int GroupIndex
{
get => _groupIndex;
set => _groupIndex = value;
}
public LoopGridViewItem GetItemByColumn(int column)
{
LoopGridViewItem cur = _first;
while(cur != null)
{
if(cur.Column == column)
{
return cur;
}
cur = cur.NextItem;
}
return null;
}
public LoopGridViewItem GetItemByRow(int row)
{
LoopGridViewItem cur = _first;
while (cur != null)
{
if (cur.Row == row)
{
return cur;
}
cur = cur.NextItem;
}
return null;
}
public void ReplaceItem(LoopGridViewItem curItem,LoopGridViewItem newItem)
{
newItem.PrevItem = curItem.PrevItem;
newItem.NextItem = curItem.NextItem;
if(newItem.PrevItem != null)
{
newItem.PrevItem.NextItem = newItem;
}
if(newItem.NextItem != null)
{
newItem.NextItem.PrevItem = newItem;
}
if(_first == curItem)
{
_first = newItem;
}
if(_last == curItem)
{
_last = newItem;
}
}
public void AddFirst(LoopGridViewItem newItem)
{
newItem.PrevItem = null;
newItem.NextItem = null;
if (_first == null)
{
_first = newItem;
_last = newItem;
_first.PrevItem = null;
_first.NextItem = null;
_count++;
}
else
{
_first.PrevItem = newItem;
newItem.PrevItem = null;
newItem.NextItem = _first;
_first = newItem;
_count++;
}
}
public void AddLast(LoopGridViewItem newItem)
{
newItem.PrevItem = null;
newItem.NextItem = null;
if (_first == null)
{
_first = newItem;
_last = newItem;
_first.PrevItem = null;
_first.NextItem = null;
_count++;
}
else
{
_last.NextItem = newItem;
newItem.PrevItem = _last;
newItem.NextItem = null;
_last = newItem;
_count++;
}
}
public LoopGridViewItem RemoveFirst()
{
LoopGridViewItem ret = _first;
if (_first == null)
{
return ret;
}
if(_first == _last)
{
_first = null;
_last = null;
--_count;
return ret;
}
_first = _first.NextItem;
_first.PrevItem = null;
--_count;
return ret;
}
public LoopGridViewItem RemoveLast()
{
LoopGridViewItem ret = _last;
if (_first == null)
{
return ret;
}
if (_first == _last)
{
_first = null;
_last = null;
--_count;
return ret;
}
_last = _last.PrevItem;
_last.NextItem = null;
--_count;
return ret;
}
public void Clear()
{
LoopGridViewItem current = _first;
while (current != null)
{
current.PrevItem = null;
current.NextItem = null;
current = current.NextItem;
}
_first = null;
_last = null;
_count = 0;
}
}
}

View File

@@ -1,113 +0,0 @@
using System;
using System.Collections.Generic;
using UnityEngine;
namespace GameLogic
{
public class GridItemPool
{
private GameObject _prefabObj;
private string _prefabName;
private int _initCreateCount = 1;
private readonly List<LoopGridViewItem> _tmpPooledItemList = new List<LoopGridViewItem>();
private readonly List<LoopGridViewItem> _pooledItemList = new List<LoopGridViewItem>();
private static int _curItemIdCount = 0;
private RectTransform _itemParent = null;
public GridItemPool()
{
}
public void Init(GameObject prefabObj, int createCount, RectTransform parent)
{
_prefabObj = prefabObj;
_prefabName = _prefabObj.name;
_initCreateCount = createCount;
_itemParent = parent;
_prefabObj.SetActive(false);
for (int i = 0; i < _initCreateCount; ++i)
{
LoopGridViewItem tViewItem = CreateItem();
RecycleItemReal(tViewItem);
}
}
public LoopGridViewItem GetItem()
{
_curItemIdCount++;
LoopGridViewItem tItem = null;
if (_tmpPooledItemList.Count > 0)
{
int count = _tmpPooledItemList.Count;
tItem = _tmpPooledItemList[count - 1];
_tmpPooledItemList.RemoveAt(count - 1);
tItem.gameObject.SetActive(true);
}
else
{
int count = _pooledItemList.Count;
if (count == 0)
{
tItem = CreateItem();
}
else
{
tItem = _pooledItemList[count - 1];
_pooledItemList.RemoveAt(count - 1);
tItem.gameObject.SetActive(true);
}
}
tItem.ItemId = _curItemIdCount;
return tItem;
}
public void DestroyAllItem()
{
ClearTmpRecycledItem();
int count = _pooledItemList.Count;
for (int i = 0; i < count; ++i)
{
GameObject.DestroyImmediate(_pooledItemList[i].gameObject);
}
_pooledItemList.Clear();
}
public LoopGridViewItem CreateItem()
{
GameObject go = GameObject.Instantiate<GameObject>(_prefabObj, Vector3.zero, Quaternion.identity, _itemParent);
go.SetActive(true);
RectTransform rf = go.GetComponent<RectTransform>();
rf.localScale = Vector3.one;
rf.anchoredPosition3D = Vector3.zero;
rf.localEulerAngles = Vector3.zero;
LoopGridViewItem tViewItem = go.GetComponent<LoopGridViewItem>();
tViewItem.ItemPrefabName = _prefabName;
tViewItem.GoId = go.GetHashCode();
return tViewItem;
}
void RecycleItemReal(LoopGridViewItem item)
{
item.gameObject.SetActive(false);
_pooledItemList.Add(item);
}
public void RecycleItem(LoopGridViewItem item)
{
item.PrevItem = null;
item.NextItem = null;
_tmpPooledItemList.Add(item);
}
public void ClearTmpRecycledItem()
{
int count = _tmpPooledItemList.Count;
if (count == 0)
{
return;
}
for (int i = 0; i < count; ++i)
{
RecycleItemReal(_tmpPooledItemList[i]);
}
_tmpPooledItemList.Clear();
}
}
}

View File

@@ -1,184 +0,0 @@
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
namespace GameLogic
{
public class LoopGridViewItem : MonoBehaviour
{
// indicates the items index in the list the mItemIndex can only be from 0 to itemTotalCount -1.
int mItemIndex = -1;
// the row index, the item is in. starting from 0.
int mRow = -1;
// the column index, the item is in. starting from 0.
int mColumn = -1;
//indicates the items id.
//This property is set when the item is created or fetched from pool,
//and will no longer change until the item is recycled back to pool.
int mItemId = -1;
private int _goId = 0;
public int GoId
{
set => _goId = value;
get => _goId;
}
LoopGridView mParentGridView = null;
bool mIsInitHandlerCalled = false;
string mItemPrefabName;
RectTransform mCachedRectTransform;
int mItemCreatedCheckFrameCount = 0;
object mUserObjectData = null;
int mUserIntData1 = 0;
int mUserIntData2 = 0;
string mUserStringData1 = null;
string mUserStringData2 = null;
LoopGridViewItem mPrevItem;
LoopGridViewItem mNextItem;
public object UserObjectData
{
get { return mUserObjectData; }
set { mUserObjectData = value; }
}
public int UserIntData1
{
get { return mUserIntData1; }
set { mUserIntData1 = value; }
}
public int UserIntData2
{
get { return mUserIntData2; }
set { mUserIntData2 = value; }
}
public string UserStringData1
{
get { return mUserStringData1; }
set { mUserStringData1 = value; }
}
public string UserStringData2
{
get { return mUserStringData2; }
set { mUserStringData2 = value; }
}
public int ItemCreatedCheckFrameCount
{
get { return mItemCreatedCheckFrameCount; }
set { mItemCreatedCheckFrameCount = value; }
}
public RectTransform CachedRectTransform
{
get
{
if (mCachedRectTransform == null)
{
mCachedRectTransform = gameObject.GetComponent<RectTransform>();
}
return mCachedRectTransform;
}
}
public string ItemPrefabName
{
get
{
return mItemPrefabName;
}
set
{
mItemPrefabName = value;
}
}
public int Row
{
get
{
return mRow;
}
set
{
mRow = value;
}
}
public int Column
{
get
{
return mColumn;
}
set
{
mColumn = value;
}
}
public int ItemIndex
{
get
{
return mItemIndex;
}
set
{
mItemIndex = value;
}
}
public int ItemId
{
get
{
return mItemId;
}
set
{
mItemId = value;
}
}
public bool IsInitHandlerCalled
{
get
{
return mIsInitHandlerCalled;
}
set
{
mIsInitHandlerCalled = value;
}
}
public LoopGridView ParentGridView
{
get
{
return mParentGridView;
}
set
{
mParentGridView = value;
}
}
public LoopGridViewItem PrevItem
{
get { return mPrevItem; }
set { mPrevItem = value; }
}
public LoopGridViewItem NextItem
{
get { return mNextItem; }
set { mNextItem = value; }
}
}
}

View File

@@ -1,12 +0,0 @@
fileFormatVersion: 2
guid: ec0432517adfcb84bb6163d7a44ab8c1
timeCreated: 1554538573
licenseType: Store
MonoImporter:
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -1,8 +0,0 @@
fileFormatVersion: 2
guid: e9bbd48a4abc45c46a92b92d0df3ae07
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -1,216 +0,0 @@
using UnityEngine;
namespace GameLogic
{
public class LoopListViewItem : MonoBehaviour
{
public float Padding;
private int _itemIndex = -1;
private int _itemId = -1;
private LoopListView _parentListView = null;
private bool _isInitHandlerCalled = false;
private string _itemPrefabName;
private RectTransform _cachedRectTransform;
private float _padding;
private float _distanceWithViewPortSnapCenter = 0;
private int _itemCreatedCheckFrameCount = 0;
private float _startPosOffset = 0;
private object _userObjectData = null;
private int _userIntData1 = 0;
private int _userIntData2 = 0;
private string _userStringData1 = null;
private string _userStringData2 = null;
private int _goId = 0;
public int GoId
{
set => _goId = value;
get => _goId;
}
public object UserObjectData
{
get => _userObjectData;
set => _userObjectData = value;
}
public int UserIntData1
{
get => _userIntData1;
set => _userIntData1 = value;
}
public int UserIntData2
{
get => _userIntData2;
set => _userIntData2 = value;
}
public string UserStringData1
{
get => _userStringData1;
set => _userStringData1 = value;
}
public string UserStringData2
{
get => _userStringData2;
set => _userStringData2 = value;
}
public float DistanceWithViewPortSnapCenter
{
get => _distanceWithViewPortSnapCenter;
set => _distanceWithViewPortSnapCenter = value;
}
public float StartPosOffset
{
get => _startPosOffset;
set => _startPosOffset = value;
}
public int ItemCreatedCheckFrameCount
{
get => _itemCreatedCheckFrameCount;
set => _itemCreatedCheckFrameCount = value;
}
public RectTransform CachedRectTransform
{
get
{
if (_cachedRectTransform == null)
{
_cachedRectTransform = gameObject.GetComponent<RectTransform>();
}
return _cachedRectTransform;
}
}
public string ItemPrefabName
{
get => _itemPrefabName;
set => _itemPrefabName = value;
}
public int ItemIndex
{
get => _itemIndex;
set => _itemIndex = value;
}
public int ItemId
{
get => _itemId;
set => _itemId = value;
}
public bool IsInitHandlerCalled
{
get => _isInitHandlerCalled;
set => _isInitHandlerCalled = value;
}
public LoopListView ParentListView
{
get => _parentListView;
set => _parentListView = value;
}
public float TopY
{
get
{
ListItemArrangeType arrageType = ParentListView.ArrangeType;
if (arrageType == ListItemArrangeType.TopToBottom)
{
return CachedRectTransform.localPosition.y;
}
else if (arrageType == ListItemArrangeType.BottomToTop)
{
return CachedRectTransform.localPosition.y + CachedRectTransform.rect.height;
}
return 0;
}
}
public float BottomY
{
get
{
ListItemArrangeType arrageType = ParentListView.ArrangeType;
if (arrageType == ListItemArrangeType.TopToBottom)
{
return CachedRectTransform.localPosition.y - CachedRectTransform.rect.height;
}
else if (arrageType == ListItemArrangeType.BottomToTop)
{
return CachedRectTransform.localPosition.y;
}
return 0;
}
}
public float LeftX
{
get
{
ListItemArrangeType arrageType = ParentListView.ArrangeType;
if (arrageType == ListItemArrangeType.LeftToRight)
{
return CachedRectTransform.localPosition.x;
}
else if (arrageType == ListItemArrangeType.RightToLeft)
{
return CachedRectTransform.localPosition.x - CachedRectTransform.rect.width;
}
return 0;
}
}
public float RightX
{
get
{
ListItemArrangeType arrageType = ParentListView.ArrangeType;
if (arrageType == ListItemArrangeType.LeftToRight)
{
return CachedRectTransform.localPosition.x + CachedRectTransform.rect.width;
}
else if (arrageType == ListItemArrangeType.RightToLeft)
{
return CachedRectTransform.localPosition.x;
}
return 0;
}
}
public float ItemSize
{
get
{
if (ParentListView.IsVertList)
{
return CachedRectTransform.rect.height;
}
else
{
return CachedRectTransform.rect.width;
}
}
}
public float ItemSizeWithPadding => ItemSize + _padding;
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 4f3fbd5ce2514056b72986a6dea2aec2
timeCreated: 1695289443

View File

@@ -1,71 +0,0 @@
using TEngine;
namespace GameLogic
{
/// <summary>
/// 子界面之间共享的数据。
/// </summary>
public class ChildPageSharData
{
private object[] m_arrParams = new object[3]; // 共享参数列表
public object Param1 { get { return m_arrParams[0]; } }
public object Param2 { get { return m_arrParams[1]; } }
public object Param3 { get { return m_arrParams[2]; } }
/// <summary>
/// 设置指定索引的参数。
/// </summary>
/// <param name="paramIdx"></param>
/// <param name="param"></param>
public void SetParam(int paramIdx, object param)
{
if (paramIdx >= m_arrParams.Length)
return;
m_arrParams[paramIdx] = param;
}
}
public class ChildPageBase : UIWidget
{
protected ChildPageSharData m_shareObjData; // 共享数据
// 初始化数据
public void InitData(ChildPageSharData shareObjData)
{
m_shareObjData = shareObjData;
}
public virtual void OnPageShowed(int oldShowType, int newShowType)
{
}
// 无参数刷新当前子界面
// 收到那些数据变动的消息的时候使用
public virtual void RefreshPage()
{
}
public object ShareData1
{
get => m_shareObjData.Param1;
set => m_shareObjData.SetParam(0, value);
}
public object ShareData2
{
get => m_shareObjData.Param2;
set => m_shareObjData.SetParam(1, value);
}
public object ShareData3
{
get => m_shareObjData.Param3;
set => m_shareObjData.SetParam(2, value);
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: e4b742d9af72478b9d6f7ebd2fa493a0
timeCreated: 1687859782

View File

@@ -1,457 +0,0 @@
using System;
using System.Collections.Generic;
using TEngine;
using UnityEngine;
namespace GameLogic
{
public class SwitchPageMgr
{
private event Action<int, int> SwitchTabAction;
public delegate bool SwitchTabCondition(int selectId);
private SwitchTabCondition _switchTabCondition;
/// <summary>
/// 页签Grid。
/// </summary>
protected Transform m_tabGrid;
/// <summary>
/// 子UI父节点。
/// </summary>
public Transform ChildPageParent;
/// <summary>
/// 存储子UI。
/// </summary>
private readonly Dictionary<int, List<string>> _switchPageDic = new Dictionary<int, List<string>>();
/// <summary>
/// 子页签名字。
/// </summary>
private readonly List<string> _childPageNames = new List<string>();
/// <summary>
/// 子页签字典。
/// </summary>
private readonly Dictionary<string, ChildPageBase> _childPageDic = new Dictionary<string, ChildPageBase>();
/// <summary>
/// 存储页签。
/// </summary>
private readonly Dictionary<int, SwitchTabItem> _tabDic = new Dictionary<int, SwitchTabItem>();
private readonly Dictionary<int, string> _tabName = new Dictionary<int, string>();
protected readonly List<int> IDList = new List<int>();
private readonly UIBase _owner;
protected int CurrentChildID = -100;
/// <summary>
/// 需要设置显示隐藏。
/// </summary>
private readonly bool _needSetActive;
/// <summary>
/// 子界面的共享数据。
/// </summary>
private readonly ChildPageSharData _shareData = new ChildPageSharData();
public object ShareData1 => _shareData.Param1;
public object ShareData2 => _shareData.Param2;
public object ShareData3 => _shareData.Param3;
public SwitchPageMgr(Transform grid, Transform childPageParent, UIBase owner, bool needSetActive = true)
{
m_tabGrid = grid;
ChildPageParent = childPageParent;
_owner = owner;
_needSetActive = needSetActive;
}
public void AddSwitchAction(Action<int, int> action)
{
SwitchTabAction += action;
}
public void RemoveSwitchAction(Action<int, int> action)
{
SwitchTabAction -= action;
}
public void AddSwitchCondition(SwitchTabCondition action)
{
_switchTabCondition = action;
}
public void BindChildPage<T>(int childID) where T : ChildPageBase, new()
{
BindChildPage<T>(childID, string.Empty);
}
public void BindChildPage<T>(int childID, string tabName) where T : ChildPageBase, new()
{
var pageName = typeof(T).Name;
if (IDList.IndexOf(childID) < 0)
{
IDList.Add(childID);
}
if (!_childPageDic.ContainsKey(pageName))
{
_childPageDic[pageName] = new T();
_childPageNames.Add(pageName);
}
if (!_switchPageDic.ContainsKey(childID))
{
_switchPageDic[childID] = new List<string>();
}
if (_switchPageDic[childID].IndexOf(pageName) < 0)
{
_switchPageDic[childID].Add(pageName);
}
_tabName[childID] = tabName;
}
public T CreatTab<T>(int initChildID, GameObject tabTemp = null) where T : SwitchTabItem, new()
{
T tab = null;
for (var index = 0; index < IDList.Count; index++)
{
var childID = IDList[index];
if (!_tabDic.ContainsKey(childID))
{
if (tabTemp != null)
{
tab = _owner.CreateWidgetByPrefab<T>(tabTemp, m_tabGrid);
}
else
{
tab = _owner.CreateWidgetByType<T>(m_tabGrid);
}
tab.UpdateTabName(_tabName[childID]);
tab.BindClickEvent(TabOnClick, childID);
_tabDic[childID] = tab;
break;
}
}
SwitchPage(initChildID);
return tab;
}
public void CreatTabByItem<T>(int initChildID, GameObject go) where T : SwitchTabItem, new()
{
if (!_tabDic.ContainsKey(initChildID))
{
T tab = _owner.CreateWidgetByPrefab<T>(go, m_tabGrid);
tab.UpdateTabName(_tabName[initChildID]);
tab.BindClickEvent(TabOnClick, initChildID);
_tabDic[initChildID] = tab;
}
}
// 设置页签的自定义点击行为
public void SetCustomTabClickAction(int tabIdx, Action<SwitchTabItem> clickAction, object param1 = null,
object param2 = null, object param3 = null)
{
_tabDic[tabIdx].BindClickEvent(clickAction, param1, param2, param3);
}
public int TabCount => _tabDic.Count;
public void SetTabRedNode(int tabId, bool isShow)
{
if (_tabDic.TryGetValue(tabId, out var value))
{
value.SetRedNote(isShow);
}
}
public void SetTabFontSize(int fontSize)
{
for (int i = 0; i < IDList.Count; i++)
{
var tabId = IDList[i];
_tabDic[tabId].SetITabTextFontSize(fontSize);
}
}
private void TabOnClick(SwitchTabItem tab)
{
var childID = (int)tab.EventParam1;
SwitchPage(childID);
}
public virtual void SwitchPage(int selectID)
{
if (_switchTabCondition != null && !_switchTabCondition(selectID))
{
return;
}
if (CurrentChildID != selectID)
{
if (_switchPageDic.TryGetValue(selectID, out var pageLs))
{
for (int i = 0; i < pageLs.Count; i++)
{
var pageName = pageLs[i];
ChildPageBase page = GetChildPageByName(pageName);
if (page != null && page.gameObject == null)
{
page.CreateByPath(pageName, _owner, ChildPageParent);
page.InitData(_shareData);
}
}
for (int i = 0; i < _childPageNames.Count; i++)
{
string pageName = _childPageNames[i];
ChildPageBase page = GetChildPageByName(pageName);
bool beShow = pageLs.IndexOf(pageName) >= 0;
if (page != null && page.gameObject != null)
{
if (_needSetActive)
{
//page.Show(beShow);
if (beShow)
{
page.gameObject.SetActive(true);
// page.Visible = true;
}
else
{
page.gameObject.SetActive(false);
// page.Visible = false;
}
}
}
// if (page != null && beShow)
if (page != null)
{
page.OnPageShowed(CurrentChildID, selectID);
}
}
}
for (var index = 0; index < IDList.Count; index++)
{
var childID = IDList[index];
SwitchTabItem tab;
if (_tabDic.TryGetValue(childID, out tab))
{
tab.SetState(selectID == childID);
}
}
}
var oldID = CurrentChildID;
CurrentChildID = selectID;
if (SwitchTabAction != null)
{
SwitchTabAction(oldID, selectID);
}
}
public virtual void ShowPage(int selectID)
{
if (_switchPageDic.TryGetValue(selectID, out var pageLs))
{
for (int i = 0; i < pageLs.Count; i++)
{
var pageName = pageLs[i];
ChildPageBase page = GetChildPageByName(pageName);
if (page != null && page.gameObject == null)
{
page.CreateByPath(pageName, _owner, ChildPageParent);
page.InitData(_shareData);
}
}
for (int i = 0; i < _childPageNames.Count; i++)
{
string pageName = _childPageNames[i];
ChildPageBase page = GetChildPageByName(pageName);
bool beShow = pageLs.IndexOf(pageName) >= 0;
if (page != null && page.gameObject != null)
{
if (beShow)
{
page.gameObject.SetActive(true);
// page.Visible = true;
}
else
{
page.gameObject.SetActive(false);
// page.Visible = false;
}
}
}
}
for (var index = 0; index < IDList.Count; index++)
{
var childID = IDList[index];
SwitchTabItem tab;
if (_tabDic.TryGetValue(childID, out tab))
{
tab.SetState(selectID == childID);
}
}
}
public void RefreshCurrentChildPage()
{
if (_switchPageDic.TryGetValue(CurrentChildID, out var pageNames))
{
for (int i = 0; i < pageNames.Count; i++)
{
ChildPageBase page = GetChildPageByName(pageNames[i]);
if (page != null && page.gameObject != null)
{
page.RefreshPage();
}
}
}
}
public void RefreshChildPage(int childID)
{
if (_switchPageDic.TryGetValue(childID, out var pageNames))
{
for (int i = 0; i < pageNames.Count; i++)
{
ChildPageBase page = GetChildPageByName(pageNames[i]);
if (page != null && page.gameObject != null)
{
page.RefreshPage();
}
}
}
}
public bool TryGetChildPage<T>(out T t) where T : ChildPageBase
{
t = GetChildPage<T>();
return t != null;
}
public int GetCurShowType()
{
return CurrentChildID;
}
public void ReductionShowType()
{
CurrentChildID = -100;
}
#region ChildPagem_switchTabAction来处理切页事件()
public SwitchTabItem GetTabItem(int childId)
{
_tabDic.TryGetValue(childId, out var item);
return item;
}
public void CreateJumpTab<T>(int initChildID, string tabName, GameObject tabTemp = null)
where T : SwitchTabItem, new()
{
if (IDList.IndexOf(initChildID) < 0)
{
IDList.Add(initChildID);
}
_tabName[initChildID] = tabName;
for (var index = 0; index < IDList.Count; index++)
{
var childID = IDList[index];
if (!_tabDic.ContainsKey(childID))
{
T tab;
if (tabTemp != null)
{
tab = _owner.CreateWidgetByPrefab<T>(tabTemp, m_tabGrid);
}
else
{
tab = _owner.CreateWidgetByType<T>(m_tabGrid);
}
tab.UpdateTabName(_tabName[childID]);
tab.BindClickEvent(TabOnClick, childID);
_tabDic[childID] = tab;
}
}
SwitchPage(initChildID);
}
#endregion
/// <summary>
/// 设置共享参数。
/// </summary>
/// <param name="paramIdx"></param>
/// <param name="param"></param>
public void SetShareParam(int paramIdx, object param)
{
_shareData.SetParam(paramIdx, param);
}
public T GetChildPage<T>() where T : ChildPageBase
{
var pageName = typeof(T).Name;
_childPageDic.TryGetValue(pageName, out var page);
return page as T;
}
public ChildPageBase GetChildPageByName(string pageName)
{
_childPageDic.TryGetValue(pageName, out var page);
return page;
}
public void BindChildPage<T, U>(int childID, string tabName)
where T : ChildPageBase, new()
where U : ChildPageBase, new()
{
BindChildPage<T>(childID, tabName);
BindChildPage<U>(childID, tabName);
}
public void BindChildPage<T, U, V>(int childID, string tabName)
where T : ChildPageBase, new()
where U : ChildPageBase, new()
where V : ChildPageBase, new()
{
BindChildPage<T>(childID, tabName);
BindChildPage<U>(childID, tabName);
BindChildPage<V>(childID, tabName);
}
public void BindChildPage<T, U, V, W>(int childID, string tabName)
where T : ChildPageBase, new()
where U : ChildPageBase, new()
where V : ChildPageBase, new()
where W : ChildPageBase, new()
{
BindChildPage<T>(childID, tabName);
BindChildPage<U>(childID, tabName);
BindChildPage<V>(childID, tabName);
BindChildPage<W>(childID, tabName);
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: e04155ae1ce3448587a5e322477d0076
timeCreated: 1687859725

View File

@@ -1,263 +0,0 @@
using System;
using TMPro;
using UnityEngine;
using UnityEngine.UI;
namespace GameLogic
{
public class SwitchTabItem : UIEventItem<SwitchTabItem>
{
//选中时的文本
protected TextMeshProUGUI m_selectText;
//未选中时的文本
protected TextMeshProUGUI m_noSelectText;
//选中时的图片
protected Image m_selectImage;
//未选中时的图片
protected Image m_noSelectImage;
//选中时的节点
protected Transform m_selectNode;
//未选中时的节点
protected Transform m_noSelectNode;
//选中时的Icon
protected Image m_selectIcon;
//未选中时的Icon
protected Image m_noSelectIcon;
protected GameObject m_goRedNote;
//是否选中
public bool IsSelect
{
get { return m_isSelect; }
set { SetState(value); }
}
protected bool m_isSelect = false;
//private RedNoteBehaviour m_redNote;
public RedNoteWidget m_redNote { get; private set; }
public virtual Vector2 SelectRedPointPos
{
get
{
return Vector2.zero;
}
}
public virtual Vector2 NoSelectRedPointPos
{
get
{
return Vector2.zero;
}
}
public override void BindMemberProperty()
{
m_selectNode = FindChild("SelectNode");
m_noSelectNode = FindChild("NoSelectNode");
if (m_selectNode != null)
{
m_selectText = FindChildComponent<TextMeshProUGUI>(m_selectNode, "SelectText");
m_selectImage = FindChildComponent<Image>(m_selectNode, "SelectImage");
m_selectIcon = FindChildComponent<Image>(m_selectNode, "SelectIcon");
}
if (m_noSelectNode != null)
{
m_noSelectText = FindChildComponent<TextMeshProUGUI>(m_noSelectNode, "NoSelectText");
m_noSelectImage = FindChildComponent<Image>(m_noSelectNode, "NoSelectImage");
m_noSelectIcon = FindChildComponent<Image>(m_noSelectNode, "NoSelectIcon");
}
var tf = FindChild("m_goRedNote");
if (tf != null)
{
m_goRedNote = tf.gameObject;
m_redNote = CreateWidgetByType<RedNoteWidget>(tf);
m_redNote.rectTransform.anchoredPosition = Vector2.zero;
SetRedNote(false);
//CreateDefaultRedNote();
}
}
#region
public void SetRedNoteType(RedNoteNotify type)
{
if (m_redNote != null)
{
m_redNote.m_redNote.SetNotifyType(type);
}
SetRedNote(true);
}
public void SetRedNoteType(RedNoteNotify type, ulong param1)
{
if (m_redNote != null)
{
m_redNote.m_redNote.SetNotifyType(type, param1);
}
SetRedNote(true);
}
public void SetRedNoteType(RedNoteNotify type, ulong param1, ulong param2)
{
if (m_redNote != null)
{
m_redNote.m_redNote.SetNotifyType(type, param1, param2);
}
SetRedNote(true);
}
public void SetRedNoteType(RedNoteNotify type, ulong param1, ulong param2, ulong param3)
{
if (m_redNote != null)
{
m_redNote.m_redNote.SetNotifyType(type, param1, param2, param3);
}
SetRedNote(true);
}
public void SetRedNoteState(bool state)
{
if (m_redNote != null)
{
m_redNote.m_redNote.SetRedNoteState(state);
}
SetRedNote(state);
}
#endregion
public void UpdateTabName(string tabName)
{
if (m_selectText != null)
{
m_selectText.text = tabName;
m_selectText.rectTransform.sizeDelta = new Vector2(m_selectText.preferredWidth, m_selectText.rectTransform.sizeDelta.y);
}
if (m_noSelectText != null)
{
m_noSelectText.text = tabName;
m_noSelectText.rectTransform.sizeDelta = new Vector2(m_noSelectText.preferredWidth, m_noSelectText
.rectTransform.sizeDelta.y);
}
}
// public void UpdateTabImage(string selectImageName,string noSelectImageName)
// {
// if (m_selectImage != null)
// {
// UISpriteHelper.Instance.SetSprite(m_selectImage, selectImageName);
// }
// if (m_noSelectImage != null)
// {
// UISpriteHelper.Instance.SetSprite(m_noSelectImage, noSelectImageName);
// }
// }
//
// public void UpdateIcon(string selectIconName, string noSelectIconName)
// {
// if (m_selectIcon != null)
// {
// DUISpriteHelper.Instance.SetSprite(m_selectIcon, selectIconName, true);
// }
// if (m_noSelectIcon != null)
// {
// DUISpriteHelper.Instance.SetSprite(m_noSelectIcon, noSelectIconName, true);
// }
// }
//
// public virtual void CreateDefaultRedNote()
// {
// if (m_goRedNote != null)
// {
// UIEffectHelper.CreateUIEffectGoById((uint)CommonEffectID.EffectRedPoint, m_goRedNote.transform);
// }
// }
public void SetRedNote(bool show)
{
if (m_goRedNote != null)
{
m_goRedNote.SetActive(show);
}
}
public virtual void SetState(bool select)
{
m_isSelect = select;
if (m_selectNode != null)
{
m_selectNode.gameObject.SetActive(select);
}
if (m_noSelectNode != null)
{
m_noSelectNode.gameObject.SetActive(!select);
}
if (m_goRedNote != null)
{
if (select)
{
if (SelectRedPointPos != Vector2.zero)
{
((RectTransform)m_goRedNote.transform).anchoredPosition = SelectRedPointPos;
}
}
else
{
if (NoSelectRedPointPos != Vector2.zero)
{
((RectTransform)m_goRedNote.transform).anchoredPosition = NoSelectRedPointPos;
}
}
}
}
public void SetITabTextFontSize(int fontSize)
{
if (m_selectText != null)
{
m_selectText.fontSize = fontSize;
}
if (m_noSelectText != null)
{
m_noSelectText.fontSize = fontSize;
}
}
#region UI-ID
/// <summary>
/// UI-ID
/// </summary>
public uint uiID;
/// <summary>
/// UI标识
/// </summary>
protected string m_uiFlag;
/// <summary>
/// 检查方法
/// </summary>
protected Func<bool> m_funcCheck;
/// <summary>
/// 页签索引
/// </summary>
public int tabIndex = -1;
/// <summary>
/// UI标识
/// </summary>
/// <returns></returns>
public virtual string GetUiFlag()
{
return string.IsNullOrEmpty(m_uiFlag) ? uiID.ToString() : m_uiFlag;
}
#endregion
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 498417b8785d47249da952f77d069c33
timeCreated: 1687667780

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: b50cf85b0f0d4e43b12cb694f6c07979
timeCreated: 1695289335

View File

@@ -1,18 +0,0 @@
using UnityEngine.UI;
public class EmptyGraph : Graphic
{
public bool m_debug = false;
protected override void OnPopulateMesh(VertexHelper vbo)
{
vbo.Clear();
#if UNITY_EDITOR
if (m_debug)
{
base.OnPopulateMesh(vbo);
}
#endif
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 21df3dfa358b498e8da3d169d736df58
timeCreated: 1695289370

View File

@@ -1,138 +0,0 @@
using System;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;
namespace GameLogic
{
[AddComponentMenu("UI/TScrollRect Rect", 37)]
[SelectionBase]
[ExecuteAlways]
[DisallowMultipleComponent]
[RequireComponent(typeof (RectTransform))]
public class TScrollRect : ScrollRect
{
private event Action ActionBeginDrag;
private event Action ActionOnDrag;
private event Action ActionEndDrag;
public List<ScrollRect> parentScrollRectList;
protected override void Awake()
{
base.Awake();
if (parentScrollRectList != null && parentScrollRectList.Count > 0)
{
for (int i = 0; i < parentScrollRectList.Count; i++)
{
AddParentScrollRect(parentScrollRectList[i]);
}
}
}
private List<ScrollRect> m_listParentScrollRect;
public void AddParentScrollRect(ScrollRect parentScrollRect)
{
if (parentScrollRect == null)
{
return;
}
if (m_listParentScrollRect == null)
{
m_listParentScrollRect = new List<ScrollRect>();
}
if (!m_listParentScrollRect.Contains(parentScrollRect))
{
m_listParentScrollRect.Add(parentScrollRect);
}
}
public void AddBeginDragListener(Action action)
{
ActionBeginDrag += action;
}
public void RemoveBeginDragListener(Action action)
{
ActionBeginDrag -= action;
}
public void AddOnDragListener(Action action)
{
ActionOnDrag += action;
}
public void RemoveOnDragListener(Action action)
{
ActionOnDrag -= action;
}
public void AddEndDragListener(Action action)
{
ActionEndDrag += action;
}
public void RemoveEndDragListener(Action action)
{
ActionEndDrag -= action;
}
public override void OnBeginDrag(PointerEventData eventData)
{
base.OnBeginDrag(eventData);
if (ActionBeginDrag != null)
{
ActionBeginDrag();
}
if (m_listParentScrollRect != null)
{
for (int i = 0; i < m_listParentScrollRect.Count; i++)
{
var parentScrollRect = m_listParentScrollRect[i];
parentScrollRect.OnBeginDrag(eventData);
}
}
}
public override void OnDrag(PointerEventData eventData)
{
base.OnDrag(eventData);
if (ActionOnDrag != null)
{
ActionOnDrag();
}
if (m_listParentScrollRect != null)
{
for (int i = 0; i < m_listParentScrollRect.Count; i++)
{
var parentScrollRect = m_listParentScrollRect[i];
parentScrollRect.OnDrag(eventData);
}
}
}
public override void OnEndDrag(PointerEventData eventData)
{
base.OnEndDrag(eventData);
if (ActionEndDrag != null)
{
ActionEndDrag();
}
if (m_listParentScrollRect != null)
{
for (int i = 0; i < m_listParentScrollRect.Count; i++)
{
var parentScrollRect = m_listParentScrollRect[i];
parentScrollRect.OnEndDrag(eventData);
}
}
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: d322e77e03014f65a9ec277d50bd12f8
timeCreated: 1695289370

View File

@@ -1,26 +0,0 @@
using System;
using UnityEngine;
using UnityEngine.EventSystems;
namespace GameLogic
{
public class UIButtonSound : MonoBehaviour, IPointerClickHandler
{
private static Action<int> _playSoundAction = null;
public int clickSound = 2;
public void OnPointerClick(PointerEventData eventData)
{
if (_playSoundAction != null)
{
_playSoundAction(clickSound);
}
}
public static void AddPlaySoundAction(Action<int> onClick)
{
_playSoundAction += onClick;
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: bb272eb1eec94625884e6e83889daa9a
timeCreated: 1695289370

View File

@@ -1,226 +0,0 @@
using System;
using TEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;
namespace GameLogic
{
public class UIEventItem<T> : UIWidget where T : UIEventItem<T>
{
private object m_eventParam1;
private object m_eventParam2;
private object m_eventParam3;
public object EventParam1 => m_eventParam1;
public object EventParam2 => m_eventParam2;
public object EventParam3 => m_eventParam3;
private Action<T> m_clickAction;
private Action<T, bool> m_pressAction;
private Action<T, PointerEventData> m_beginDragAction;
private Action<T, PointerEventData> m_dragAction;
private Action<T, PointerEventData> m_endDragAction;
public void BindClickEvent(Action<T> clickAction, object eParam1 = null, object eParam2 = null, object eParam3 = null,
Selectable.Transition transition = Selectable.Transition.ColorTint)
{
if (m_clickAction != null)
{
m_clickAction = clickAction;
}
else
{
m_clickAction = clickAction;
var button = gameObject.GetOrAddComponent<Button>();
button.transition = transition;
button.onClick.AddListener(() =>
{
if (m_clickAction != null)
{
m_clickAction(this as T);
}
});
}
SetEventParam(eParam1, eParam2, eParam3);
}
public void BindClickEventEx(Action<T> clickAction, object eParam1 = null, object eParam2 = null, object eParam3 = null)
{
if (m_clickAction != null)
{
m_clickAction = clickAction;
}
else
{
m_clickAction = clickAction;
var button = gameObject.GetOrAddComponent<Button>();
button.onClick.AddListener(() =>
{
if (m_clickAction != null)
{
m_clickAction(this as T);
}
});
}
SetEventParam(eParam1, eParam2, eParam3);
}
public void BindBeginDragEvent(Action<T, PointerEventData> dragAction, object eParam1 = null, object eParam2 = null, object eParam3 = null)
{
if (m_beginDragAction != null)
{
m_beginDragAction = dragAction;
}
else
{
m_beginDragAction = dragAction;
var trigger = gameObject.GetOrAddComponent<EventTrigger>();
EventTrigger.Entry entry = new EventTrigger.Entry();
entry.eventID = EventTriggerType.BeginDrag;
entry.callback = new EventTrigger.TriggerEvent();
entry.callback.AddListener((data) =>
{
var pointerEventData = (PointerEventData)data;
if (m_beginDragAction != null)
{
m_beginDragAction(this as T, pointerEventData);
}
});
trigger.triggers.Add(entry);
}
SetEventParam(eParam1, eParam2, eParam3);
}
public void BindDragEvent(Action<T, PointerEventData> dragAction, object eParam1 = null, object eParam2 = null, object eParam3 = null)
{
if (m_dragAction != null)
{
m_dragAction = dragAction;
}
else
{
m_dragAction = dragAction;
var trigger = gameObject.GetOrAddComponent<EventTrigger>();
EventTrigger.Entry entry = new EventTrigger.Entry();
entry.eventID = EventTriggerType.Drag;
entry.callback = new EventTrigger.TriggerEvent();
entry.callback.AddListener((data) =>
{
var pointerEventData = (PointerEventData)data;
if (m_dragAction != null)
{
m_dragAction(this as T, pointerEventData);
}
});
trigger.triggers.Add(entry);
}
SetEventParam(eParam1, eParam2, eParam3);
}
public void BindEndDragEvent(Action<T, PointerEventData> dragendAction, object eParam1 = null, object eParam2 = null, object eParam3 = null)
{
if (m_endDragAction != null)
{
m_endDragAction = dragendAction;
}
else
{
m_endDragAction = dragendAction;
var trigger = gameObject.GetOrAddComponent<EventTrigger>();
EventTrigger.Entry entry = new EventTrigger.Entry();
entry.eventID = EventTriggerType.EndDrag;
entry.callback = new EventTrigger.TriggerEvent();
entry.callback.AddListener((data) =>
{
if (m_endDragAction != null)
{
m_endDragAction(this as T, (PointerEventData)data);
}
});
trigger.triggers.Add(entry);
}
SetEventParam(eParam1, eParam2, eParam3);
}
public void BindPressEvent(Action<T, bool> pressAction, object eParam1 = null, object eParam2 = null, object eParam3 = null)
{
if (m_pressAction != null)
{
m_pressAction = pressAction;
}
else
{
m_pressAction = pressAction;
var trigger = gameObject.GetOrAddComponent<EventTrigger>();
EventTrigger.Entry entry = new EventTrigger.Entry();
entry.eventID = EventTriggerType.PointerDown;
entry.callback = new EventTrigger.TriggerEvent();
entry.callback.AddListener((data) =>
{
if (m_pressAction != null)
{
m_pressAction(this as T, true);
}
});
trigger.triggers.Add(entry);
entry = new EventTrigger.Entry();
entry.eventID = EventTriggerType.PointerUp;
entry.callback = new EventTrigger.TriggerEvent();
entry.callback.AddListener((data) =>
{
if (m_pressAction != null)
{
m_pressAction(this as T, false);
}
});
trigger.triggers.Add(entry);
}
SetEventParam(eParam1, eParam2, eParam3);
}
public void BindPressEventEx(Action<T, bool> pressAction, object eParam1 = null, object eParam2 = null, object eParam3 = null,
float durationThreshold = 1)
{
if (m_pressAction != null)
{
m_pressAction = pressAction;
}
else
{
m_pressAction = pressAction;
var button = gameObject.GetOrAddComponent<UIButtonSuper>();
button.m_LongPressDurationTime = durationThreshold;
button.onPress.AddListener(() =>
{
if (m_pressAction != null)
{
m_pressAction(this as T, true);
}
});
}
SetEventParam(eParam1, eParam2, eParam3);
}
public void SetEventParam(object eParam1, object eParam2 = null, object eParam3 = null)
{
m_eventParam1 = eParam1;
m_eventParam2 = eParam2;
m_eventParam3 = eParam3;
}
public void OnTriggerBtnEvent()
{
if (m_clickAction != null)
{
m_clickAction(this as T);
}
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: c9972ff1d1514807bbd21d6bc4c035f4
timeCreated: 1695289504

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 2d3f2e9ab868464da947f3d52aa9c3f6
timeCreated: 1695289443

View File

@@ -1,349 +0,0 @@
using System;
using System.Collections.Generic;
using TEngine;
using UnityEngine;
using UnityEngine.UI;
namespace GameLogic
{
/// <summary>
/// UI列表Item
/// </summary>
/// <typeparam name="TData"></typeparam>
public interface IListDataItem<in TData>
{
void SetItemData(TData d);
}
/// <summary>
/// UI列表Item
/// </summary>
public interface IListSelectItem
{
/// <summary>
/// 获取索引。
/// </summary>
/// <returns></returns>
int GetItemIndex();
/// <summary>
/// 设置索引。
/// </summary>
/// <param name="i"></param>
void SetItemIndex(int i);
/// <summary>
/// 是否被选中。
/// </summary>
/// <returns></returns>
bool IsSelected();
/// <summary>
/// 设置是否选中。
/// </summary>
/// <param name="v"></param>
void SetSelected(bool v);
}
public class SelectItemBase : UIEventItem<SelectItemBase>, IListSelectItem
{
/// <summary>
/// 索引。
/// </summary>
protected int m_itemIndex;
public int GetItemIndex()
{
return m_itemIndex;
}
public void SetItemIndex(int i)
{
m_itemIndex = i;
}
/// <summary>
/// 是否被选中。
/// </summary>
protected bool m_isSelected;
public virtual bool IsSelected()
{
return m_isSelected;
}
public virtual void SetSelected(bool v)
{
if (m_isSelected == v) return;
m_isSelected = v;
UpdateSelect();
}
/// <summary>
/// 刷新选中状态。
/// </summary>
public virtual void UpdateSelect()
{
}
public override void RegisterEvent()
{
base.RegisterEvent();
AddSelectEvt();
}
/// <summary>
/// 监听选中事件。
/// </summary>
protected virtual void AddSelectEvt()
{
if (Parent == null || !(Parent is IUISelectList)) return;
var btn = gameObject.GetOrAddComponent<Button>();
if (btn != null)
{
btn.onClick.AddListener(OnSelectClick);
}
}
/// <summary>
/// 选中点击
/// </summary>
protected virtual void OnSelectClick()
{
var p = Parent as IUISelectList;
if (p != null)
{
p.OnItemClick(this, GetItemIndex());
}
}
}
interface IUISelectList
{
void OnItemClick(object item, int i);
}
/// <summary>
/// UI列表
/// </summary>
public class UIListBase<ItemT, DataT> : UIWidget, IUISelectList where ItemT : UIWidget, new()
{
/// <summary>
/// item模板
/// </summary>
public GameObject itemBase;
/// <summary>
/// 数据列表
/// </summary>
protected List<DataT> m_datas;
/// <summary>
/// 数据列表
/// </summary>
public List<DataT> datas => m_datas;
/// <summary>
/// 数据数量
/// </summary>
public int DataNum => m_datas?.Count ?? 0;
/// <summary>
/// 数量
/// </summary>
protected int m_num;
/// <summary>
/// 数量
/// </summary>
public int num => m_num;
/// <summary>
/// 设置数据数量
/// </summary>
/// <param name="n"></param>
/// <param name="funcItem"></param>
public void SetDataNum(int n, Action<ItemT, int> funcItem = null)
{
AdjustItemNum(n, null, funcItem);
}
/// <summary>
/// 数据起始索引
/// </summary>
public int dataStartOffset = 0;
/// <summary>
/// 设置数据
/// </summary>
/// <param name="dataList"></param>
/// <param name="n"></param>
public void SetDatas(List<DataT> dataList, int n = -1)
{
AdjustItemNum(Mathf.Max(0, n >= 0 ? n : (dataList == null ? 0 : (dataList.Count - dataStartOffset))), dataList);
}
/// <summary>
/// 设置显示数据
/// </summary>
/// <param name="n"></param>
/// <param name="datas"></param>
/// <param name="funcItem"></param>
protected virtual void AdjustItemNum(int n, List<DataT> datas = null, Action<ItemT, int> funcItem = null)
{
m_num = n;
m_datas = datas;
if (itemBase != null)
{
itemBase.SetActive(false);
}
}
/// <summary>
/// 刷新列表ITEM
/// </summary>
/// <param name="item"></param>
/// <param name="i"></param>
/// <param name="func"></param>
protected virtual void UpdateListItem(ItemT item, int i, Action<ItemT, int> func)
{
if (item == null) return;
if (func != null)
{
func.Invoke(item, i);
return;
}
if (item is IListDataItem<DataT> listDataItem)
{
listDataItem.SetItemData(GetData(i));
}
}
/// <summary>
/// 选中索引
/// </summary>
protected int m_selectIndex = -1;
/// <summary>
/// Item点击
/// </summary>
public Action<int> funcOnItemClick;
/// <summary>
/// 选中变化回调函数
/// </summary>
public Action funcOnSelectChange;
/// <summary>
/// 点击无选中变化回调
/// </summary>
public Action funcNoSelectChange;
/// <summary>
/// 选中索引
/// </summary>
public int selectIndex
{
get => m_selectIndex;
set => SetSelectIndex(value);
}
/// <summary>
/// 设置选中索引
/// </summary>
/// <param name="i"></param>
/// <param name="forceUpdate"></param>
/// <param name="triggerEvt"></param>
public void SetSelectIndex(int i, bool forceUpdate = false, bool triggerEvt = true)
{
if (!forceUpdate && m_selectIndex == i)
{
if (funcNoSelectChange != null)
{
funcNoSelectChange.Invoke();
}
return;
}
var preIndex = selectIndex;
m_selectIndex = i;
if (GetItem(preIndex) is IListSelectItem item)
{
item.SetSelected(false);
}
item = GetItem(selectIndex) as IListSelectItem;
if (item != null)
{
item.SetSelected(true);
}
UpdateSnapTargetItem();
if (triggerEvt && funcOnSelectChange != null)
{
funcOnSelectChange.Invoke();
}
}
/// <summary>
/// 刷新Snap
/// </summary>
protected virtual void UpdateSnapTargetItem()
{
}
/// <summary>
/// 获取当前选中的数据
/// </summary>
/// <returns></returns>
public DataT GetSelectData()
{
return GetData(selectIndex);
}
/// <summary>
/// 获取数据
/// </summary>
/// <param name="i"></param>
/// <returns></returns>
public DataT GetData(int i)
{
i += dataStartOffset;
return m_datas == null || i < 0 || i >= m_datas.Count ? default(DataT) : m_datas[i];
}
/// <summary>
/// 获取item
/// </summary>
/// <param name="i"></param>
/// <returns></returns>
public virtual ItemT GetItem(int i)
{
return null;
}
/// <summary>
/// 点击选择
/// </summary>
public bool SelectByClick = true;
/// <summary>
/// item被点击
/// </summary>
/// <param name="item"></param>
/// <param name="i"></param>
public void OnItemClick(object item, int i)
{
if (funcOnItemClick != null)
{
funcOnItemClick.Invoke(i);
}
if (SelectByClick)
{
selectIndex = i;
}
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 9d3742a744bb4934a4848b54bb6910a2
timeCreated: 1691679426

View File

@@ -1,57 +0,0 @@
using System;
using System.Collections.Generic;
using TEngine;
namespace GameLogic
{
/// <summary>
/// 普通UI列表。
/// </summary>
public class UIListWidget<TItem, TData> : UIListBase<TItem, TData> where TItem : UIWidget, new()
{
/// <summary>
/// item列表。
/// </summary>
protected List<TItem> m_items = new List<TItem>();
/// <summary>
/// item列表。
/// </summary>
public List<TItem> items => m_items;
/// <summary>
/// 设置显示数据。
/// </summary>
/// <param name="n"></param>
/// <param name="datas"></param>
/// <param name="funcItem"></param>
protected override void AdjustItemNum(int n, List<TData> datas = null, Action<TItem, int> funcItem = null)
{
base.AdjustItemNum(n, datas, funcItem);
AdjustIconNum(m_items, n, gameObject.transform, itemBase);
UpdateList(funcItem);
}
/// <summary>
/// 刷新列表。
/// </summary>
/// <param name="funcItem"></param>
protected void UpdateList(Action<TItem, int> funcItem = null)
{
for (var i = 0; i < m_items.Count; i++)
{
UpdateListItem(m_items[i], i, funcItem);
}
}
/// <summary>
/// 获取item
/// </summary>
/// <param name="i"></param>
/// <returns></returns>
public override TItem GetItem(int i)
{
return i >= 0 && i < m_items.Count ? m_items[i] : null;
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 96f732d895e94fbc99c904d66ca844ca
timeCreated: 1701844130

View File

@@ -1,14 +0,0 @@
namespace GameLogic
{
public class UILoopGridItemWidget: SelectItemBase
{
public LoopGridViewItem LoopItem { set; get; }
public int Index { private set; get; }
public virtual void UpdateItem(int index)
{
Index = index;
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 47ee457a0d7549b3a3b5d23f4ac048cd
timeCreated: 1692346002

View File

@@ -1,208 +0,0 @@
using System;
using System.Collections.Generic;
using TEngine;
using UnityEngine;
namespace GameLogic
{
/// <summary>
/// UI列表。
/// </summary>
public class UILoopGridWidget<TItem, TData> : UIListBase<TItem, TData> where TItem : UILoopGridItemWidget, new()
{
/// <summary>
/// LoopRectView
/// </summary>
public LoopGridView LoopRectView { private set; get; }
/// <summary>
/// Item字典
/// </summary>
private GameFrameworkDictionary<int, TItem> m_itemCache = new GameFrameworkDictionary<int, TItem>();
/// <summary>
/// 计算偏差后的ItemList
/// </summary>
private List<TItem> m_items = new List<TItem>();
/// <summary>
/// 计算偏差后的ItemList
/// </summary>
public List<TItem> items => m_items;
public override void BindMemberProperty()
{
base.BindMemberProperty();
LoopRectView = rectTransform.GetComponent<LoopGridView>();
}
public override void OnCreate()
{
base.OnCreate();
LoopRectView.InitGridView(0, OnGetItemByIndex);
}
public override void OnDestroy()
{
base.OnDestroy();
m_itemCache.Clear();
}
/// <summary>
/// Item回调函数
/// </summary>
protected Action<TItem, int> m_tpFuncItem;
/// <summary>
/// 设置显示数据
/// </summary>
/// <param name="n"></param>
/// <param name="datas"></param>
/// <param name="funcItem"></param>
protected override void AdjustItemNum(int n, List<TData> datas = null, Action<TItem, int> funcItem = null)
{
base.AdjustItemNum(n, datas, funcItem);
m_tpFuncItem = funcItem;
LoopRectView.SetListItemCount(n);
LoopRectView.RefreshAllShownItem();
m_tpFuncItem = null;
UpdateAllItemSelect();
}
/// <summary>
/// 获取Item
/// </summary>
/// <param name="listView"></param>
/// <param name="itemIndex"></param>
/// <param name="row"></param>
/// <param name="column"></param>
/// <returns></returns>
protected LoopGridViewItem OnGetItemByIndex(LoopGridView listView, int itemIndex,int row,int column)
{
if (itemIndex < 0 || itemIndex >= num) return null;
var item = itemBase == null ? CreateItem() : CreateItem(itemBase);
if (item == null) return null;
item.SetItemIndex(itemIndex);
UpdateListItem(item, itemIndex, m_tpFuncItem);
return item.LoopItem;
}
/// <summary>
/// 创建Item
/// </summary>
/// <returns></returns>
public TItem CreateItem()
{
return CreateItem(typeof(TItem).Name);
}
/// <summary>
/// 创建Item
/// </summary>
/// <param name="itemName"></param>
/// <returns></returns>
public TItem CreateItem(string itemName)
{
TItem widget = null;
LoopGridViewItem item = LoopRectView.AllocOrNewListViewItem(itemName);
if (item != null)
{
widget = CreateItem(item);
}
return widget;
}
/// <summary>
/// 创建Item
/// </summary>
/// <param name="prefab"></param>
/// <returns></returns>
public TItem CreateItem(GameObject prefab)
{
TItem widget = null;
LoopGridViewItem item = LoopRectView.AllocOrNewListViewItem(prefab);
if (item != null)
{
widget = CreateItem(item);
}
return widget;
}
/// <summary>
/// 创建Item
/// </summary>
/// <param name="item"></param>
/// <returns></returns>
private TItem CreateItem(LoopGridViewItem item)
{
TItem widget;
if (!m_itemCache.TryGetValue(item.GoId, out widget))
{
widget = CreateWidget<TItem>(item.gameObject);
widget.LoopItem = item;
m_itemCache.Add(item.GoId, widget);
}
return widget;
}
/// <summary>
/// 获取item
/// </summary>
/// <param name="index"></param>
/// <returns></returns>
public override TItem GetItem(int index)
{
for (var i = 0; i < m_itemCache.Count; i++)
{
var item = m_itemCache.GetValueByIndex(i);
if (item.GetItemIndex() == index)
{
return item;
}
}
return null;
}
/// <summary>
/// 获取itemList
/// </summary>
/// <returns></returns>
public List<TItem> GetItemList()
{
m_items.Clear();
for (int i = 0; i < m_itemCache.Count; i++)
{
m_items.Add(m_itemCache.GetValueByIndex(i));
}
return m_items;
}
/// <summary>
/// 获取Item。
/// </summary>
/// <param name="index">索引。</param>
/// <returns>TItem。</returns>
public TItem GetItemByIndex(int index)
{
return m_itemCache.GetValueByIndex(index);
}
/// <summary>
/// 刷新所有item选中状态
/// </summary>
/// <returns></returns>
public void UpdateAllItemSelect()
{
var index = selectIndex;
for (var i = 0; i < m_itemCache.Count; i++)
{
if (m_itemCache.GetValueByIndex(i) is IListSelectItem item)
{
item.SetSelected(item.GetItemIndex() == index);
}
}
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 0930448d067145dfb0428b248f1086ae
timeCreated: 1692346037

View File

@@ -1,14 +0,0 @@
namespace GameLogic
{
public class UILoopItemWidget : SelectItemBase
{
public LoopListViewItem LoopItem { set; get; }
public int Index { private set; get; }
public virtual void UpdateItem(int index)
{
Index = index;
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: b39b2f052eec4a4a97256e5aeee9e7dc
timeCreated: 1691679577

View File

@@ -1,94 +0,0 @@
using System.Collections.Generic;
using TEngine;
using UnityEngine;
namespace GameLogic
{
public class UILoopListViewWidget<T> : UIWidget where T : UILoopItemWidget, new()
{
public LoopListView LoopRectView { private set; get; }
private GameFrameworkDictionary<int, T> m_itemCache = new GameFrameworkDictionary<int, T>();
public override void BindMemberProperty()
{
base.BindMemberProperty();
LoopRectView = this.rectTransform.GetComponent<LoopListView>();
}
public override void OnDestroy()
{
base.OnDestroy();
m_itemCache.Clear();
}
public T CreateItem()
{
string typeName = typeof(T).Name;
return CreateItem(typeName);
;
}
public T CreateItem(string itemName)
{
T widget = null;
var item = LoopRectView.AllocOrNewListViewItem(itemName);
if (item != null)
{
widget = CreateItem(item);
}
return widget;
}
public T CreateItem(GameObject prefab)
{
T widget = null;
var item = LoopRectView.AllocOrNewListViewItem(prefab);
if (item != null)
{
widget = CreateItem(item);
}
return widget;
}
private T CreateItem(LoopListViewItem item)
{
T widget;
if (!m_itemCache.TryGetValue(item.GoId, out widget))
{
widget = CreateWidget<T>(item.gameObject);
widget.LoopItem = item;
m_itemCache.Add(item.GoId, widget);
}
return widget;
}
public List<T> GetItemList()
{
List<T> list = new List<T>();
for (int i = 0; i < m_itemCache.Count; i++)
{
list.Add(m_itemCache.GetValueByIndex(i));
}
return list;
}
public int GetItemCount()
{
return m_itemCache.Count;
}
/// <summary>
/// 获取Item。
/// </summary>
/// <param name="index">索引。</param>
/// <returns>TItem。</returns>
public T GetItemByIndex(int index)
{
return m_itemCache.GetValueByIndex(index);
}
}
}

View File

@@ -1,3 +0,0 @@
fileFormatVersion: 2
guid: 9b87126ba47740708bc82eb0bb9e414e
timeCreated: 1691679617

View File

@@ -1,225 +0,0 @@
using System;
using System.Collections.Generic;
using TEngine;
using UnityEngine;
namespace GameLogic
{
/// <summary>
/// UI列表。
/// </summary>
public class UILoopListWidget<TItem, TData> : UIListBase<TItem, TData> where TItem : UILoopItemWidget, new()
{
/// <summary>
/// LoopRectView
/// </summary>
public LoopListView LoopRectView { private set; get; }
/// <summary>
/// Item字典
/// <remarks>Key => GameObjectHashCode | Value => TItem.</remarks>
/// </summary>
private GameFrameworkDictionary<int, TItem> m_itemCache = new GameFrameworkDictionary<int, TItem>();
/// <summary>
/// 计算偏差后的ItemList
/// </summary>
private List<TItem> m_items = new List<TItem>();
/// <summary>
/// 计算偏差后的ItemList
/// </summary>
public List<TItem> items => m_items;
public override void BindMemberProperty()
{
base.BindMemberProperty();
LoopRectView = rectTransform.GetComponent<LoopListView>();
}
public override void OnCreate()
{
base.OnCreate();
LoopRectView.InitListView(0, OnGetItemByIndex);
}
public override void OnDestroy()
{
base.OnDestroy();
m_itemCache.Clear();
}
/// <summary>
/// Item回调函数
/// </summary>
protected Action<TItem, int> m_tpFuncItem;
/// <summary>
/// 设置显示数据
/// </summary>
/// <param name="n"></param>
/// <param name="datas"></param>
/// <param name="funcItem"></param>
protected override void AdjustItemNum(int n, List<TData> datas = null, Action<TItem, int> funcItem = null)
{
base.AdjustItemNum(n, datas, funcItem);
m_tpFuncItem = funcItem;
LoopRectView.SetListItemCount(n);
LoopRectView.RefreshAllShownItem();
m_tpFuncItem = null;
UpdateAllItemSelect();
}
/// <summary>
/// 获取Item
/// </summary>
/// <param name="listView"></param>
/// <param name="index"></param>
/// <returns></returns>
protected LoopListViewItem OnGetItemByIndex(LoopListView listView, int index)
{
if (index < 0 || index >= num) return null;
var item = itemBase == null ? CreateItem() : CreateItem(itemBase);
if (item == null) return null;
item.SetItemIndex(index);
UpdateListItem(item, index, m_tpFuncItem);
return item.LoopItem;
}
/// <summary>
/// 创建Item
/// </summary>
/// <returns></returns>
public TItem CreateItem()
{
return CreateItem(typeof(TItem).Name);
}
/// <summary>
/// 创建Item
/// </summary>
/// <param name="itemName"></param>
/// <returns></returns>
public TItem CreateItem(string itemName)
{
TItem widget = null;
LoopListViewItem item = LoopRectView.AllocOrNewListViewItem(itemName);
if (item != null)
{
widget = CreateItem(item);
}
return widget;
}
/// <summary>
/// 创建Item
/// </summary>
/// <param name="prefab"></param>
/// <returns></returns>
public TItem CreateItem(GameObject prefab)
{
TItem widget = null;
LoopListViewItem item = LoopRectView.AllocOrNewListViewItem(prefab);
if (item != null)
{
widget = CreateItem(item);
}
return widget;
}
/// <summary>
/// 创建Item
/// </summary>
/// <param name="item"></param>
/// <returns></returns>
private TItem CreateItem(LoopListViewItem item)
{
TItem widget;
if (!m_itemCache.TryGetValue(item.GoId, out widget))
{
widget = CreateWidget<TItem>(item.gameObject);
widget.LoopItem = item;
m_itemCache.Add(item.GoId, widget);
}
return widget;
}
/// <summary>
/// 获取item
/// </summary>
/// <param name="index"></param>
/// <returns></returns>
public override TItem GetItem(int index)
{
for (var i = 0; i < m_itemCache.Count; i++)
{
var item = m_itemCache.GetValueByIndex(i);
if (item.GetItemIndex() == index)
{
return item;
}
}
return null;
}
/// <summary>
/// 获取itemList
/// </summary>
/// <returns></returns>
public List<TItem> GetItemList()
{
m_items.Clear();
for (int i = 0; i < m_itemCache.Count; i++)
{
m_items.Add(m_itemCache.GetValueByIndex(i));
}
return m_items;
}
/// <summary>
/// 获取当前起始索引
/// </summary>
/// <returns></returns>
public int GetItemStartIndex()
{
return LoopRectView.GetItemStartIndex();
}
/// <summary>
/// 获取Item。
/// </summary>
/// <param name="index">索引。</param>
/// <returns>TItem。</returns>
public TItem GetItemByIndex(int index)
{
return m_itemCache.GetValueByIndex(index);
}
/// <summary>
/// 刷新所有item选中状态
/// </summary>
/// <returns></returns>
public void UpdateAllItemSelect()
{
var index = selectIndex;
for (var i = 0; i < m_itemCache.Count; i++)
{
if (m_itemCache.GetValueByIndex(i) is IListSelectItem item)
{
item.SetSelected(item.GetItemIndex() == index);
}
}
}
protected override void UpdateSnapTargetItem()
{
base.UpdateSnapTargetItem();
if (LoopRectView != null && LoopRectView.ItemSnapEnable)
{
LoopRectView.SetSnapTargetItemIndex(selectIndex);
}
}
}
}

Some files were not shown because too many files have changed in this diff Show More