# GameDesigner **Repository Path**: kurum/GameDesigner ## Basic Information - **Project Name**: GameDesigner - **Description**: Verxel(原GDNet)双端Rpc网络框架用于Unity3D,窗体程序和控制台项目开发, 高效稳定, 高性能高并发, 各种协议一键切换: gcp, udx, kcp, tcp, web, http 包含各种模块, AOI模块, Recast寻路模块, GameCore客户端框架等等 - **Primary Language**: C# - **License**: MIT - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 163 - **Created**: 2026-04-26 - **Last Updated**: 2026-04-27 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # 🎮 GameDesigner - 游戏开发框架
![Unity](https://img.shields.io/badge/Unity-2021.3+-black?style=for-the-badge&logo=unity) ![C#](https://img.shields.io/badge/C%23-10.0+-blue?style=for-the-badge&logo=c-sharp) ![License](https://img.shields.io/badge/License-MIT-green?style=for-the-badge) ![Platform](https://img.shields.io/badge/Platform-Multi--Platform-orange?style=for-the-badge) **一个功能强大的 Unity 游戏开发框架,提供完整的游戏开发解决方案** [📖 文档](#-文档) • [🚀 快速开始](#-快速开始) • [🔧 功能特性](#-功能特性) • [📁 模块介绍](#-模块介绍) • [💡 示例](#-示例)
--- ## ✨ 框架特色 GameDesigner 是一个基于 Unity 引擎的完整游戏开发框架,集成了网络通信、游戏逻辑、实体管理、状态机等核心功能模块。框架采用模块化设计,每个模块都可以独立使用,同时支持无缝集成。 ### 🎯 核心优势 - **⚡ 高性能**: 优化的网络通信和内存管理 - **🧩 模块化**: 独立的功能模块,灵活组合 - **🔧 易用性**: 简洁的 API 和丰富的示例 - **🎨 可视化**: 完整的编辑器支持和调试工具 - **🌐 跨平台**: 支持多平台部署 --- ## 🚀 快速开始 ### 环境要求 - **Unity**: 2021.3 LTS 或更高版本 - **.NET**: 4.x 或更高版本 - **操作系统**: Windows 10+, macOS 10.14+, Ubuntu 18.04+ ### 安装步骤 1. **克隆项目** ```bash git clone https://github.com/your-repo/GameDesigner.git cd GameDesigner ``` 2. **导入 Unity 项目** - 打开 Unity Hub - 选择 "Add Project From Disk" - 选择 GameDesigner 文件夹 3. **配置项目设置** - 打开 `Edit > Project Settings > Player` - 设置正确的 .NET 版本 - 配置脚本定义符号(如果需要) ### 第一个示例 ```csharp using UnityEngine; using GameDesigner.Core; using GameDesigner.Network; public class SimpleGame : MonoBehaviour { private void Start() { // 初始化游戏核心 Global.Initialize(); // 配置网络连接 NetworkManager.Instance.Initialize(new GameNetworkHandler()); NetworkManager.Instance.Connect("127.0.0.1", 8888); // 显示登录界面 UIManager.Instance.ShowPanel(); } } public class GameNetworkHandler : INetworkHandle { public void OnConnected() { Debug.Log("✅ 连接服务器成功"); } public void OnDisconnect() { Debug.Log("❌ 连接断开"); } } ``` --- ## 📁 模块详细介绍 GameDesigner 采用模块化设计,每个模块都专注于解决特定的游戏开发问题。以下是各个模块的详细功能介绍: ### 🌐 Network 网络模块 **高性能网络通信框架** **核心功能:** - 🚀 **多协议支持**: 同时支持 TCP 和 UDP 协议,可根据场景选择最优方案 - 🔄 **RPC 系统**: 完整的远程过程调用,支持客户端和服务器双向通信 - 📊 **同步变量**: 自动同步对象属性,支持自定义同步频率和条件 - 🛡️ **安全连接**: 内置连接验证、数据加密和防作弊机制 - 📈 **性能监控**: 实时网络流量统计和性能分析工具 - 🔧 **序列化优化**: 支持多种序列化方式,包括二进制、JSON、快速序列化 **使用案例:** ```csharp // 同步变量示例 [SyncVar(interval: 0.1f)] public Vector3 Position { get; set; } [SyncVar(hook = nameof(OnHealthChanged))] public int Health { get; set; } = 100; private void OnHealthChanged(int oldValue, int newValue) { // 血量变化时的处理逻辑 UpdateHealthBar(newValue); } // RPC 调用示例 [ServerRpc] public void CmdAttack(NetworkIdentity target) { // 服务器验证攻击逻辑 if (IsValidAttack(target)) { target.GetComponent().TakeDamage(10); RpcPlayAttackEffect(); } } [ClientRpc] public void RpcPlayAttackEffect() { // 在所有客户端播放攻击特效 Instantiate(attackEffect, transform.position, Quaternion.identity); } // 网络事件处理 public class GameNetworkHandler : INetworkHandle { public void OnConnected() { Debug.Log("连接服务器成功"); UIManager.Instance.HidePanel(); } public void OnDisconnect() { Debug.Log("网络连接断开"); UIManager.Instance.ShowMessage("网络连接已断开,正在尝试重连..."); } public void OnReconnect() { Debug.Log("重连成功"); UIManager.Instance.ShowMessage("重连成功!"); } } ``` ### 🎯 GameCore 游戏核心模块 **游戏基础设施框架** **核心功能:** - 🎨 **UI 管理系统**: 分层界面管理、界面栈、异步加载、界面动画 - 📦 **资源管理器**: AssetBundle 管理、异步加载、内存优化、依赖管理 - 🏞️ **场景管理器**: 场景切换、加载进度、场景预加载、场景卸载 - 🔊 **音频管理器**: 音效池、背景音乐、音量控制、3D 音效 - ⏰ **定时器系统**: 精确计时、循环任务、延迟执行、时间缩放 - 📋 **配置管理**: 游戏配置、用户设置、本地存储、云端同步 - 🔔 **事件系统**: 全局事件、局部事件、事件优先级、一次性事件 **使用案例:** ```csharp // UI 管理高级示例 public class GameUIManager : UIManager { public async void ShowBattleUI() { // 显示加载界面 await ShowPanelAsync(); // 异步加载战斗界面 var battlePanel = await OpenFormAsync( onBack: () => OnBattleEnd(), openMode: UIMode.CloseAllUI ); // 隐藏加载界面 HidePanel(); // 初始化战斗界面 battlePanel.InitializeBattle(); } private void OnBattleEnd() { // 战斗结束后的处理 ShowPanel(); } } // 资源管理示例 public class ResourceLoader : MonoBehaviour { public async void PreloadGameResources() { // 预加载常用资源 await ResourcesManager.Instance.PreloadAssetsAsync(new string[] { "Prefabs/Player", "Prefabs/Enemy", "Prefabs/Effects", "Audio/BGM", "UI/Battle" }); Debug.Log("资源预加载完成"); } public async void LoadSceneAsync(string sceneName) { // 显示加载进度 var loadingPanel = UIManager.Instance.ShowPanel(); // 异步加载场景 await SceneManager.Instance.LoadSceneAsync(sceneName, (progress) => { loadingPanel.UpdateProgress(progress); }); // 隐藏加载界面 UIManager.Instance.HidePanel(); } } // 定时器系统示例 public class SkillCoolDownManager { private Dictionary coolDownTimers = new Dictionary(); public void StartSkillCoolDown(string skillId, float duration) { if (coolDownTimers.ContainsKey(skillId)) { coolDownTimers[skillId].Stop(); } var timer = TimerManager.Instance.AddTimer(duration, () => { OnSkillCoolDownComplete(skillId); coolDownTimers.Remove(skillId); }); coolDownTimers[skillId] = timer; } public bool IsSkillReady(string skillId) { return !coolDownTimers.ContainsKey(skillId); } private void OnSkillCoolDownComplete(string skillId) { Debug.Log($"技能 {skillId} 冷却完成"); EventManager.Instance.DispatchEvent("SkillReady", skillId); } } ``` ### 🏗️ MVC 架构模块 **模型-视图-控制器框架** **核心功能:** - 🔗 **数据绑定**: 自动同步模型和视图,支持双向绑定 - 🎯 **视图管理**: 视图生命周期、视图状态、视图动画 - 📊 **模型管理**: 数据验证、数据持久化、数据变更通知 - 🎮 **控制器协调**: 业务逻辑处理、用户输入响应、模块间通信 - 🔧 **依赖注入**: 自动依赖解析、单例管理、服务定位 **使用案例:** ```csharp // 完整的 MVC 示例 public class PlayerModel : IDataModel { public string Name { get; private set; } public int Level { get; private set; } public int Experience { get; private set; } public int Health { get; private set; } public int MaxHealth { get; private set; } public event Action OnNameChanged; public event Action OnLevelChanged; public event Action OnHealthChanged; public void SetName(string name) { if (string.IsNullOrEmpty(name)) return; Name = name; OnNameChanged?.Invoke(name); } public void AddExperience(int exp) { Experience += exp; // 检查升级 int newLevel = CalculateLevel(Experience); if (newLevel > Level) { Level = newLevel; MaxHealth = CalculateMaxHealth(Level); Health = MaxHealth; // 升级回满血 OnLevelChanged?.Invoke(Level); OnHealthChanged?.Invoke(Health); } } public void TakeDamage(int damage) { Health = Mathf.Max(0, Health - damage); OnHealthChanged?.Invoke(Health); if (Health <= 0) { OnDeath?.Invoke(); } } } public class PlayerView : MonoBehaviour, IView { [ViewBind("NameText")] private Text nameText; [ViewBind("LevelText")] private Text levelText; [ViewBind("HealthBar")] private Slider healthBar; [ViewBind("ExpBar")] private Slider expBar; [ViewBind("DamageEffect")] private ParticleSystem damageEffect; private PlayerModel model; public void BindModel(PlayerModel playerModel) { model = playerModel; // 注册模型事件 model.OnNameChanged += UpdateName; model.OnLevelChanged += UpdateLevel; model.OnHealthChanged += UpdateHealth; // 初始化视图 UpdateName(model.Name); UpdateLevel(model.Level); UpdateHealth(model.Health); } private void UpdateName(string name) { nameText.text = name; } private void UpdateLevel(int level) { levelText.text = $"Lv.{level}"; // 播放升级特效 PlayLevelUpEffect(); } private void UpdateHealth(int health) { float healthPercent = (float)health / model.MaxHealth; healthBar.value = healthPercent; // 血量变化特效 if (healthPercent < 0.3f) { PlayLowHealthWarning(); } } public void OnDamageTaken() { damageEffect.Play(); // 屏幕震动效果 StartCoroutine(ShakeCamera()); } } public class PlayerController : IController { private PlayerModel model; private PlayerView view; public PlayerController(PlayerModel playerModel, PlayerView playerView) { model = playerModel; view = playerView; // 绑定视图和模型 view.BindModel(model); // 注册输入事件 InputManager.Instance.RegisterKey(KeyCode.Space, OnJump); InputManager.Instance.RegisterAxis("Horizontal", OnMove); } private void OnJump() { // 处理跳跃逻辑 if (CanJump()) { // 执行跳跃 PerformJump(); } } private void OnMove(float axis) { // 处理移动逻辑 MoveCharacter(axis); } public void Attack(EnemyController enemy) { // 攻击逻辑 int damage = CalculateDamage(); enemy.TakeDamage(damage); // 更新经验值 model.AddExperience(enemy.ExperienceReward); } } ``` ### 🗺️ AOI 兴趣区域模块 **视野管理和优化系统** **核心功能:** - 🌍 **网格化管理**: 将游戏世界划分为网格,优化对象管理 - 👁️ **动态视野**: 根据玩家位置动态计算可见对象 - 📡 **事件通知**: 对象进入/离开视野时触发相应事件 - 🔄 **网络优化**: 只同步视野内的对象,减少网络流量 - 🎯 **性能监控**: 网格负载均衡、对象分布统计 **使用案例:** ```csharp // AOI 管理器配置 public class GameAOIManager : AOIManager { public int GridSize = 10; // 每个网格的大小 public int ViewDistance = 3; // 视野距离(网格数) protected override void Awake() { base.Awake(); // 配置网格世界 GridWorld.Instance.Initialize(GridSize, ViewDistance); // 注册事件处理器 GridWorld.Instance.OnObjectEnter += OnObjectEnterView; GridWorld.Instance.OnObjectExit += OnObjectExitView; GridWorld.Instance.OnGridEnter += OnPlayerEnterGrid; GridWorld.Instance.OnGridExit += OnPlayerLeaveGrid; } private void OnObjectEnterView(IGridObject obj, IGridObject enterObj) { // 对象进入视野的处理 if (obj is Player player && enterObj is Monster monster) { player.OnMonsterEnterView(monster); } else if (obj is Player player && enterObj is Item item) { player.OnItemEnterView(item); } } private void OnObjectExitView(IGridObject obj, IGridObject exitObj) { // 对象离开视野的处理 if (obj is Player player && exitObj is Monster monster) { player.OnMonsterExitView(monster); } } private void OnPlayerEnterGrid(IGridObject obj, Grid grid) { if (obj is Player player) { Debug.Log($"玩家进入网格 [{grid.X}, {grid.Y}]"); // 加载网格资源 LoadGridResources(grid); // 激活网格内的NPC和怪物 ActivateGridObjects(grid); } } private void OnPlayerLeaveGrid(IGridObject obj, Grid grid) { if (obj is Player player) { Debug.Log($"玩家离开网格 [{grid.X}, {grid.Y}]"); // 卸载网格资源 UnloadGridResources(grid); // 停用网格内的对象 DeactivateGridObjects(grid); } } } // 玩家 AOI 实现 public class Player : MonoBehaviour, IGridActor { public Vector3 Position => transform.position; private List visibleMonsters = new List(); private List visibleItems = new List(); public void OnMonsterEnterView(Monster monster) { if (!visibleMonsters.Contains(monster)) { visibleMonsters.Add(monster); monster.SetVisible(true); // 更新小地图显示 MiniMapManager.Instance.AddMonsterMarker(monster); } } public void OnMonsterExitView(Monster monster) { if (visibleMonsters.Contains(monster)) { visibleMonsters.Remove(monster); monster.SetVisible(false); // 移除小地图标记 MiniMapManager.Instance.RemoveMonsterMarker(monster); } } public void OnItemEnterView(Item item) { if (!visibleItems.Contains(item)) { visibleItems.Add(item); item.Show(); // 显示物品提示 UIManager.Instance.ShowItemTooltip(item); } } public void Update() { // 更新视野内的对象状态 UpdateVisibleObjects(); } private void UpdateVisibleObjects() { // 处理视野内怪物的AI foreach (var monster in visibleMonsters) { monster.UpdateAI(this); } // 检查可交互物品 foreach (var item in visibleItems) { if (Vector3.Distance(transform.position, item.transform.position) < 2f) { item.ShowInteractPrompt(); } } } } // 网络同步优化示例 public class NetworkAOIOptimizer { public void OptimizeNetworkSync(Player player) { // 只同步视野内的对象 var visibleObjects = GridWorld.Instance.GetVisibleObjects(player); foreach (var obj in visibleObjects) { if (obj is INetworkSyncable syncable) { syncable.EnableSync(); } } // 禁用视野外对象的同步 var allObjects = GridWorld.Instance.GetAllObjects(); foreach (var obj in allObjects) { if (!visibleObjects.Contains(obj) && obj is INetworkSyncable syncable) { syncable.DisableSync(); } } } } ``` ### 🔄 Entities 实体系统模块 **实体-组件-系统架构实现** **核心功能:** - 🏗️ **ECS 架构**: 真正的实体-组件-系统架构,提高性能 - 🔧 **组件管理**: 动态添加/移除组件,组件依赖管理 - ⚡ **系统处理**: 基于组件的系统处理,优化CPU缓存 - 📊 **查询优化**: 快速实体查询,支持复杂条件筛选 - 🎯 **生命周期**: 完整的实体生命周期管理 **使用案例:** ```csharp // 实体定义示例 public class GameEntity : Entity { // 实体可以动态添加各种组件 } // 组件定义示例 public class TransformComponent : Component { public Vector3 Position { get; set; } public Quaternion Rotation { get; set; } public Vector3 Scale { get; set; } = Vector3.one; public void Translate(Vector3 translation) { Position += translation; } public void Rotate(Quaternion rotation) { Rotation *= rotation; } } public class HealthComponent : Component { public int MaxHealth { get; set; } = 100; public int CurrentHealth { get; set; } = 100; public bool IsAlive => CurrentHealth > 0; public event Action OnDamageTaken; public event Action OnHealed; public event Action OnDeath; public void TakeDamage(int damage) { if (!IsAlive) return; CurrentHealth = Mathf.Max(0, CurrentHealth - damage); OnDamageTaken?.Invoke(damage); if (CurrentHealth <= 0) { OnDeath?.Invoke(); } } public void Heal(int amount) { if (!IsAlive) return; CurrentHealth = Mathf.Min(MaxHealth, CurrentHealth + amount); OnHealed?.Invoke(amount); } } public class MovementComponent : Component { public Vector3 Velocity { get; set; } public float Speed { get; set; } = 5f; public bool IsGrounded { get; set; } public void Move(Vector3 direction) { Velocity = direction.normalized * Speed; } public void Stop() { Velocity = Vector3.zero; } } // 系统定义示例 public class MovementSystem : EntitySystem { protected override void OnUpdate() { // 查询所有拥有TransformComponent和MovementComponent的实体 var entities = World.Query(); foreach (var entity in entities) { var transform = entity.GetComponent(); var movement = entity.GetComponent(); // 更新位置 transform.Position += movement.Velocity * Time.deltaTime; } } } public class HealthSystem : EntitySystem { protected override void OnUpdate() { // 处理所有健康组件 var entities = World.Query(); foreach (var entity in entities) { var health = entity.GetComponent(); // 自动回血逻辑 if (health.CurrentHealth < health.MaxHealth) { health.Heal(1); // 每秒回1点血 } } } } // 世界管理器示例 public class GameWorld : World { private MovementSystem movementSystem; private HealthSystem healthSystem; private RenderSystem renderSystem; protected override void OnCreate() { base.OnCreate(); // 注册系统 movementSystem = CreateSystem(); healthSystem = CreateSystem(); renderSystem = CreateSystem(); } public Entity CreatePlayer(Vector3 position) { var player = CreateEntity("Player"); // 添加必要的组件 player.AddComponent().Position = position; player.AddComponent(); player.AddComponent(); player.AddComponent(); player.AddComponent(); return player; } public Entity CreateMonster(Vector3 position, MonsterType type) { var monster = CreateEntity($"Monster_{type}"); monster.AddComponent().Position = position; monster.AddComponent(); monster.AddComponent(); monster.AddComponent().SetBehavior(type); monster.AddComponent().Type = type; return monster; } public void DestroyEntity(Entity entity) { // 销毁前的清理工作 if (entity.HasComponent()) { entity.GetComponent().OnDestroy(); } // 销毁实体 base.DestroyEntity(entity); } } ``` ### 🔌 NetworkComponent 网络组件模块 **Unity 专用网络组件系统** **核心功能:** - 🎮 **网络行为**: 基于 Unity 的 NetworkBehaviour 组件 - 🔄 **变换同步**: 自动位置、旋转、缩放同步 - 📦 **预制体管理**: 网络预制体的生成和销毁 - 🎯 **权限管理**: 客户端和服务器权限控制 - 🔧 **自定义同步**: 支持自定义数据的网络同步 **使用案例:** ```csharp // 网络玩家组件 public class NetworkPlayer : NetworkBehaviour { [Header("玩家属性")] [SyncVar] public string PlayerName = "Player"; [SyncVar(hook = nameof(OnHealthChanged))] public int Health = 100; [SyncVar] public int Level = 1; [Header("网络设置")] public float positionSyncInterval = 0.1f; public float rotationSyncInterval = 0.2f; private CharacterController characterController; private NetworkTransform networkTransform; protected override void OnStart() { base.OnStart(); characterController = GetComponent(); networkTransform = GetComponent(); // 设置同步间隔 networkTransform.SyncInterval = positionSyncInterval; // 注册网络命令 RegisterCommand(NetworkCommand.Move, OnMoveCommand); RegisterCommand(NetworkCommand.Jump, OnJumpCommand); RegisterCommand(NetworkCommand.Attack, OnAttackCommand); if (isLocalPlayer) { // 本地玩家初始化 InitializeLocalPlayer(); } else { // 远程玩家初始化 InitializeRemotePlayer(); } } private void InitializeLocalPlayer() { // 启用本地输入 GetComponent().enabled = true; // 设置主摄像机跟随 Camera.main.GetComponent().Target = transform; // 显示本地玩家UI UIManager.Instance.ShowPanel(); } [ClientRpc] public void RpcTakeDamage(int damage, NetworkIdentity attacker) { Health = Mathf.Max(0, Health - damage); // 播放受伤特效 PlayDamageEffect(); if (Health <= 0) { RpcOnDeath(attacker); } } [ClientRpc] public void RpcOnDeath(NetworkIdentity killer) { // 死亡处理 PlayDeathAnimation(); if (isLocalPlayer) { // 显示死亡界面 UIManager.Instance.ShowPanel(); // 3秒后复活 StartCoroutine(RespawnAfterDelay(3f)); } } [ServerRpc] public void CmdMove(Vector3 direction) { // 服务器验证移动 if (IsValidMove(direction)) { // 应用移动 characterController.Move(direction * moveSpeed * Time.deltaTime); // 同步位置给其他客户端 RpcUpdatePosition(transform.position); } } [ServerRpc] public void CmdAttack(NetworkIdentity target) { // 服务器验证攻击 if (CanAttack(target)) { // 计算伤害 int damage = CalculateDamage(); // 对目标造成伤害 target.GetComponent().TakeDamage(damage, netId); // 同步攻击动作 RpcPlayAttackAnimation(); } } private void OnHealthChanged(int oldHealth, int newHealth) { // 更新血条UI UpdateHealthBar(newHealth); // 血量变化特效 if (newHealth < oldHealth) { PlayDamageFlash(); } } } // 网络物体生成器 public class NetworkSpawner : NetworkBehaviour { public GameObject playerPrefab; public GameObject[] monsterPrefabs; public GameObject[] itemPrefabs; private Dictionary spawnedObjects = new Dictionary(); [ServerRpc] public void CmdSpawnPlayer(Vector3 position, Quaternion rotation, string playerName) { var playerObj = Instantiate(playerPrefab, position, rotation); var networkObj = playerObj.GetComponent(); // 生成网络对象 NetworkServer.Spawn(networkObj); // 设置玩家名称 var player = playerObj.GetComponent(); player.PlayerName = playerName; // 记录生成的对象 spawnedObjects[networkObj.NetId] = networkObj; Debug.Log($"生成玩家: {playerName} at {position}"); } [ServerRpc] public void CmdSpawnMonster(MonsterType type, Vector3 position) { var prefab = monsterPrefabs[(int)type]; var monsterObj = Instantiate(prefab, position, Quaternion.identity); var networkObj = monsterObj.GetComponent(); NetworkServer.Spawn(networkObj); spawnedObjects[networkObj.NetId] = networkObj; } [ServerRpc] public void CmdDestroyObject(uint netId) { if (spawnedObjects.TryGetValue(netId, out var networkObj)) { NetworkServer.Destroy(networkObj.gameObject); spawnedObjects.Remove(netId); } } } // 自定义网络变换 public class SmoothNetworkTransform : NetworkTransform { public float interpolationSpeed = 5f; public float snapThreshold = 5f; private Vector3 targetPosition; private Quaternion targetRotation; protected override void OnUpdate() { if (!isLocalPlayer) { // 平滑插值到目标位置 if (Vector3.Distance(transform.position, targetPosition) > snapThreshold) { // 距离过大时直接瞬移 transform.position = targetPosition; transform.rotation = targetRotation; } else { // 平滑插值 transform.position = Vector3.Lerp(transform.position, targetPosition, Time.deltaTime * interpolationSpeed); transform.rotation = Quaternion.Lerp(transform.rotation, targetRotation, Time.deltaTime * interpolationSpeed); } } } [ClientRpc] public void RpcUpdatePosition(Vector3 position, Quaternion rotation) { targetPosition = position; targetRotation = rotation; } } ``` ### 🎭 ActorSystem 角色系统模块 **完整的角色管理框架** **核心功能:** - 👤 **角色基类**: 统一的角色基类,支持多种角色类型 - ⚔️ **技能系统**: 技能配置、冷却、效果、连招系统 - 🧪 **Buff系统**: 状态效果、持续时间、叠加规则 - 📊 **属性系统**: 基础属性、衍生属性、属性成长 - 🎯 **战斗系统**: 伤害计算、战斗状态、战斗事件 **使用案例:** ```csharp // 角色基类实现 public class RPGPlayer : ActorBase { public EquipmentSystem Equipment { get; private set; } public InventorySystem Inventory { get; private set; } public QuestSystem Quests { get; private set; } protected override void OnStart() { base.OnStart(); // 初始化子系统 Equipment = new EquipmentSystem(this); Inventory = new InventorySystem(this); Quests = new QuestSystem(this); // 注册事件 Property.OnLevelUp += OnLevelUp; Property.OnHealthChanged += OnHealthChanged; } public override void OnUpdate() { base.OnUpdate(); // 更新角色状态 UpdateState(); UpdateCombat(); UpdateInteraction(); } public void UseSkill(int skillIndex) { if (skillIndex < 0 || skillIndex >= Skills.Count) return; var skill = Skills[skillIndex]; if (skill.CanUse()) { skill.UseSkill(); // 触发技能使用事件 OnSkillUsed?.Invoke(skill); } } public void AddBuff(PlayerBuff buff) { buff.Target = this; Buffs.Add(buff); buff.OnStart(); // 更新属性 UpdateDerivedProperties(); } public void RemoveBuff(PlayerBuff buff) { if (Buffs.Contains(buff)) { buff.OnEnd(); Buffs.Remove(buff); // 更新属性 UpdateDerivedProperties(); } } private void OnLevelUp(int newLevel) { // 升级处理 Property.MaxHealth += 10; Property.Health = Property.MaxHealth; // 回满血 // 播放升级特效 PlayLevelUpEffect(); // 解锁新技能 UnlockNewSkills(newLevel); } private void UnlockNewSkills(int level) { // 根据等级解锁新技能 var unlockableSkills = SkillDatabase.GetSkillsUnlockedAtLevel(level); foreach (var skillData in unlockableSkills) { var newSkill = SkillFactory.CreateSkill(skillData); AddSkill(newSkill); } } } // 技能系统实现 public class FireballSkill : SkillBase { public float Damage { get; set; } = 50f; public float Cooldown { get; set; } = 3f; public float CastTime { get; set; } = 0.5f; public GameObject ProjectilePrefab; private bool isCasting = false; private float castTimer = 0f; public override bool CanUse() { return base.CanUse() && !isCasting && Self.Property.Mana >= ManaCost; } public override void UseSkill() { if (!CanUse()) return; // 开始施法 StartCasting(); } private void StartCasting() { isCasting = true; castTimer = 0f; // 播放施法动画 Self.PlayAnimation("CastSpell"); // 显示施法进度条 UIManager.Instance.ShowCastBar(this, CastTime); } public override void Update() { base.Update(); if (isCasting) { castTimer += Time.deltaTime; if (castTimer >= CastTime) { // 施法完成,发射火球 CastComplete(); } } } private void CastComplete() { isCasting = false; // 消耗魔法值 Self.Property.Mana -= ManaCost; // 创建火球 var fireball = Instantiate(ProjectilePrefab, Self.transform.position + Vector3.up, Quaternion.identity); var projectile = fireball.GetComponent(); projectile.Initialize(Self, Damage); // 开始冷却 StartCooldown(); } public override void OnInterrupted() { if (isCasting) { isCasting = false; // 中断施法 Self.PlayAnimation("Interrupt"); UIManager.Instance.HideCastBar(); } } } // Buff 系统实现 public class PoisonBuff : BuffBase { public float Duration { get; set; } = 5f; public float TickInterval { get; set; } = 1f; public int DamagePerTick { get; set; } = 10; public GameObject PoisonEffect; private float timer = 0f; private GameObject effectInstance; public override void OnStart() { base.OnStart(); // 显示中毒特效 if (PoisonEffect != null) { effectInstance = Instantiate(PoisonEffect, Target.transform); } // 应用中毒状态 Target.Status.Add(CharacterStatus.Poisoned); Debug.Log($"{Target.name} 中毒了!"); } public override bool OnUpdate() { timer += Time.deltaTime; // 定期造成伤害 if (timer >= TickInterval) { Target.TakeDamage(DamagePerTick, DamageType.Poison); timer = 0f; } // 检查持续时间 return Time.time - StartTime < Duration; } public override void OnEnd() { // 移除中毒特效 if (effectInstance != null) { Destroy(effectInstance); } // 移除中毒状态 Target.Status.Remove(CharacterStatus.Poisoned); Debug.Log($"{Target.name} 中毒效果结束"); } public override void OnRefresh() { // 刷新持续时间 StartTime = Time.time; Debug.Log($"{Target.name} 中毒效果刷新"); } } // 属性系统实现 public class PlayerProperty : PropertyBase { // 基础属性 public int Strength { get; set; } = 10; public int Agility { get; set; } = 10; public int Intelligence { get; set; } = 10; public int Stamina { get; set; } = 10; // 衍生属性 public int AttackPower => Strength * 2; public int SpellPower => Intelligence * 2; public int CriticalChance => Agility / 10; public int MaxHealth => Stamina * 10 + 100; public int MaxMana => Intelligence * 5 + 50; // 当前状态 private int health; public int Health { get => health; set { var oldHealth = health; health = Mathf.Clamp(value, 0, MaxHealth); if (health != oldHealth) { OnHealthChanged?.Invoke(oldHealth, health); } } } private int mana; public int Mana { get => mana; set { mana = Mathf.Clamp(value, 0, MaxMana); } } private int level = 1; public int Level { get => level; set { var oldLevel = level; level = value; if (level > oldLevel) { OnLevelUp?.Invoke(level); } } } public int Experience { get; set; } public int ExperienceToNextLevel => Level * 100; // 事件 public event Action OnHealthChanged; public event Action OnLevelUp; public void AddExperience(int exp) { Experience += exp; // 检查升级 while (Experience >= ExperienceToNextLevel) { Experience -= ExperienceToNextLevel; Level++; } } public void TakeDamage(int damage, DamageType damageType = DamageType.Physical) { // 计算实际伤害(考虑抗性等) int actualDamage = CalculateActualDamage(damage, damageType); Health -= actualDamage; Debug.Log($"受到 {actualDamage} 点伤害,当前血量: {Health}"); } public void Heal(int amount) { Health += amount; Debug.Log($"恢复 {amount} 点生命值,当前血量: {Health}"); } } ``` ### 🌐 Distributed 分布式系统模块 **分布式游戏服务器架构** **核心功能:** - ⚖️ **负载均衡**: 自动分配玩家到最优服务器 - 🔄 **一致性哈希**: 稳定的服务器分配算法 - 🆔 **唯一ID生成**: 分布式环境下的唯一标识 - 🌍 **跨服通信**: 服务器间的数据同步和通信 - 📊 **集群管理**: 服务器集群的监控和管理 **使用案例:** ```csharp // 负载均衡器实现 public class GameLoadBalancer : LoadBalance { private Dictionary servers = new Dictionary(); private ConsistentHashing serverHashing = new ConsistentHashing(); public void RegisterServer(string serverId, GameServer server) { servers[serverId] = server; // 根据服务器容量添加权重 int weight = CalculateServerWeight(server); serverHashing.AddNode(serverId, weight); Debug.Log($"注册服务器: {serverId}, 权重: {weight}"); } public void UnregisterServer(string serverId) { if (servers.ContainsKey(serverId)) { servers.Remove(serverId); serverHashing.RemoveNode(serverId); Debug.Log($"移除服务器: {serverId}"); } } public string GetPlayerServer(string playerId) { // 使用一致性哈希分配服务器 string serverId = serverHashing.GetNode(playerId); if (servers.TryGetValue(serverId, out var server)) { if (server.CurrentPlayers < server.MaxPlayers) { return serverId; } else { // 服务器已满,选择下一个可用服务器 return GetNextAvailableServer(serverId); } } return null; } public void TransferPlayer(string playerId, string targetServerId) { string currentServerId = GetPlayerServer(playerId); if (currentServerId != targetServerId) { // 执行跨服转移 PerformServerTransfer(playerId, currentServerId, targetServerId); } } private int CalculateServerWeight(GameServer server) { // 根据服务器性能计算权重 int weight = server.MaxPlayers / 100; // 基础权重 // 考虑服务器负载 float loadFactor = (float)server.CurrentPlayers / server.MaxPlayers; weight = (int)(weight * (1 - loadFactor * 0.5f)); return Mathf.Max(1, weight); } } // 唯一ID生成器 public class DistributedIdGenerator : UniqueIdGenerator { private static DistributedIdGenerator instance; public static DistributedIdGenerator Instance => instance ??= new DistributedIdGenerator(); public DistributedIdGenerator() : base(1, 1) { } public long GeneratePlayerId() { return GenerateId(); } public long GenerateItemId() { return GenerateId(); } public long GenerateGuildId() { return GenerateId(); } } // 分布式服务管理 public class DistributedServiceManager { private Dictionary> services = new Dictionary>(); public void RegisterService(ServiceType type, ServiceEndpoint endpoint) { if (!services.ContainsKey(type)) { services[type] = new List(); } services[type].Add(endpoint); Debug.Log($"注册服务: {type} -> {endpoint.Address}:{endpoint.Port}"); } public ServiceEndpoint GetService(ServiceType type, string key = null) { if (services.TryGetValue(type, out var endpoints)) { if (endpoints.Count == 0) return null; if (string.IsNullOrEmpty(key)) { // 随机选择一个服务端点 return endpoints[Random.Range(0, endpoints.Count)]; } else { // 使用一致性哈希选择服务端点 var hashing = new ConsistentHashing(); foreach (var endpoint in endpoints) { hashing.AddNode(endpoint, 1); } return hashing.GetNode(key); } } return null; } public async Task CallServiceAsync(ServiceType type, string method, object parameters, string key = null) { var endpoint = GetService(type, key); if (endpoint == null) { throw new Exception($"未找到可用的服务: {type}"); } // 调用远程服务 return await endpoint.CallAsync(method, parameters); } } // 跨服通信示例 public class CrossServerCommunication { private DistributedServiceManager serviceManager; public async void SendGlobalMessage(string message) { // 获取所有聊天服务 var chatServices = serviceManager.GetAllServices(ServiceType.Chat); // 向所有聊天服务器广播消息 var tasks = chatServices.Select(service => serviceManager.CallServiceAsync(ServiceType.Chat, "BroadcastMessage", new { Message = message }) ).ToArray(); await Task.WhenAll(tasks); } public async void TransferPlayerData(string playerId, string fromServer, string toServer) { // 从源服务器获取玩家数据 var playerData = await serviceManager.CallServiceAsync( ServiceType.Game, "GetPlayerData", new { PlayerId = playerId }, fromServer); // 将玩家数据转移到目标服务器 await serviceManager.CallServiceAsync( ServiceType.Game, "ImportPlayerData", new { PlayerData = playerData }, toServer); // 从源服务器删除玩家数据 await serviceManager.CallServiceAsync( ServiceType.Game, "RemovePlayerData", new { PlayerId = playerId }, fromServer); Debug.Log($"玩家 {playerId} 已从 {fromServer} 转移到 {toServer}"); } } ``` ### ⚡ NonLockStep 非锁步同步模块 **灵活的帧同步替代方案** **核心功能:** - 🔄 **回滚系统**: 支持状态回滚和重新模拟 - 🎯 **输入预测**: 客户端输入预测和服务器验证 - 📊 **状态同步**: 高效的状态同步机制 - ⏰ **时间管理**: 精确的时间同步和管理 - 🔧 **物理同步**: 确定性物理模拟 **使用案例:** ```csharp // 非锁步玩家控制器 public class NonLockStepPlayer : NCharacterController { public float MoveSpeed = 5f; public float JumpForce = 10f; private NVector3 inputDirection; private bool wantsToJump; private bool isGrounded; public override void OnUpdate() { // 处理玩家输入 inputDirection = new NVector3( Input.GetAxis("Horizontal"), 0, Input.GetAxis("Vertical") ); wantsToJump = Input.GetButtonDown("Jump"); // 同步输入状态到服务器 if (IsLocalPlayer) { SyncInputState(); } } public override void OnFixedUpdate() { // 应用移动 if (inputDirection != NVector3.zero) { Velocity = inputDirection * MoveSpeed; } else { Velocity = NVector3.zero; } // 处理跳跃 if (wantsToJump && isGrounded) { Velocity.y = JumpForce; wantsToJump = false; // 播放跳跃动画 PlayJumpAnimation(); } // 应用重力 if (!isGrounded) { Velocity.y -= Gravity * Time.fixedDeltaTime; } base.OnFixedUpdate(); // 更新接地状态 UpdateGroundedState(); } private void SyncInputState() { // 发送输入状态到服务器 var inputState = new PlayerInputState { Direction = inputDirection, Jump = wantsToJump, Timestamp = NTime.Time, Frame = NTime.Frame }; NetworkManager.Instance.Send(inputState); } public void OnReceiveServerState(PlayerState serverState) { // 服务器状态修正 if (IsLocalPlayer) { // 比较本地预测和服务器状态 var discrepancy = Vector3.Distance(transform.position, serverState.Position); if (discrepancy > 0.1f) // 差异过大 { // 执行回滚和重新模拟 PerformRollback(serverState); } else { // 微小修正 transform.position = Vector3.Lerp(transform.position, serverState.Position, 0.1f); } } else { // 远程玩家直接应用服务器状态 transform.position = serverState.Position; transform.rotation = serverState.Rotation; } } } // 回滚系统实现 public class GameRollbackSystem : NRollback { private Dictionary stateHistory = new Dictionary(); private Dictionary> inputHistory = new Dictionary>(); public void SaveState(int frame, GameState state) { stateHistory[frame] = state.Clone(); // 清理旧的状态(保留最近100帧) var oldFrames = stateHistory.Keys.Where(f => f < frame - 100).ToArray(); foreach (var oldFrame in oldFrames) { stateHistory.Remove(oldFrame); } } public void RecordInput(int frame, PlayerInput input) { if (!inputHistory.ContainsKey(frame)) { inputHistory[frame] = new List(); } inputHistory[frame].Add(input); } public GameState RollbackToFrame(int targetFrame) { if (stateHistory.TryGetValue(targetFrame, out var state)) { // 回滚到指定帧的状态 ApplyState(state); // 重新模拟从目标帧到当前帧 ReplayFromFrame(targetFrame, NTime.Frame); return state; } return null; } public void ReplayFromFrame(int startFrame, int endFrame) { // 从起始帧开始重新模拟 var currentState = stateHistory[startFrame].Clone(); ApplyState(currentState); for (int frame = startFrame + 1; frame <= endFrame; frame++) { // 获取该帧的所有输入 if (inputHistory.TryGetValue(frame, out var inputs)) { // 应用输入并推进游戏状态 foreach (var input in inputs) { ApplyInput(input); } } // 模拟一帧 SimulateFrame(); // 保存状态(用于可能的后续回滚) SaveState(frame, currentState); } } private void SimulateFrame() { // 模拟游戏逻辑 UpdatePhysics(); UpdateEntities(); UpdateCollisions(); } } // 确定性物理系统 public class DeterministicPhysics : NPhysics { private List rigidbodies = new List(); private List colliders = new List(); public override void OnFixedUpdate() { // 确定性物理模拟 SimulatePhysics(Time.fixedDeltaTime); } private void SimulatePhysics(float deltaTime) { // 应用重力 foreach (var rb in rigidbodies) { if (rb.useGravity && !rb.isKinematic) { rb.velocity += Physics.gravity * deltaTime; } } // 更新位置 foreach (var rb in rigidbodies) { if (!rb.isKinematic) { rb.position += rb.velocity * deltaTime; } } // 碰撞检测和响应 DetectCollisions(); ResolveCollisions(); } private void DetectCollisions() { // 简单的碰撞检测(使用确定性算法) for (int i = 0; i < colliders.Count; i++) { for (int j = i + 1; j < colliders.Count; j++) { var col1 = colliders[i]; var col2 = colliders[j]; if (CheckCollision(col1, col2)) { // 处理碰撞 HandleCollision(col1, col2); } } } } public void RegisterRigidbody(Rigidbody rb) { if (!rigidbodies.Contains(rb)) { rigidbodies.Add(rb); } } public void UnregisterRigidbody(Rigidbody rb) { rigidbodies.Remove(rb); } } // 时间同步管理 public class NetworkTimeSync : NTime { private float serverTime; private float timeOffset; private float ping; public void SyncWithServer(float serverTimeStamp, float clientTimeStamp) { // 计算时间偏移 float currentTime = Time.realtimeSinceStartup; float roundTripTime = currentTime - clientTimeStamp; ping = roundTripTime / 2f; timeOffset = serverTimeStamp + ping - currentTime; Debug.Log($"时间同步: 偏移={timeOffset:F3}s, 延迟={ping*1000:F1}ms"); } public float GetNetworkTime() { return Time.realtimeSinceStartup + timeOffset; } public float GetServerTime() { return serverTime; } public void UpdateServerTime(float newServerTime) { serverTime = newServerTime; } } ``` --- ## 💡 示例项目 ### 多人游戏示例 ```csharp public class MultiplayerGame : MonoBehaviour { private void Start() { // 初始化网络 NetworkManager.Instance.Initialize(new GameNetworkHandler()); // 注册消息处理器 NetworkManager.Instance.RegisterHandler(OnPlayerJoin); NetworkManager.Instance.RegisterHandler(OnPlayerMove); // 连接服务器 NetworkManager.Instance.Connect("game.server.com", 8888); } private void OnPlayerJoin(PlayerJoinMessage message) { // 创建玩家角色 CreatePlayer(message.PlayerId, message.Position); } } ``` ### RPG 游戏示例 ```csharp public class RPGPlayer : ActorBase { public override void OnUpdate() { // 更新角色状态 UpdateSkills(); UpdateBuffs(); UpdateCombat(); } public void UseSkill(int skillIndex) { if (Skills.Count > skillIndex) { Skills[skillIndex].UseSkill(); } } } ``` --- ## 🔧 开发指南 ### 项目结构 ``` GameDesigner/ ├── GameDesigner/ # 主项目文件夹 │ ├── Core/ # 核心模块 │ ├── GameCore~/ # 游戏核心模块 │ ├── Network~/ # 网络模块 │ ├── ActorSystem~/ # 角色系统模块 │ ├── Entities~/ # 实体系统模块 │ └── ... # 其他模块 ├── Examples/ # 示例项目 ├── Documentation/ # 文档 └── README.md # 项目说明 ``` ### 最佳实践 1. **资源管理** ```csharp // 使用对象池管理频繁创建的对象 var bullet = ObjectPool.Get(); // ... 使用后回收 ObjectPool.Return(bullet); ``` 2. **网络优化** ```csharp // 合理设置同步频率 [SyncVar(interval: 0.1f)] public Vector3 Position { get; set; } ``` 3. **性能监控** ```csharp // 使用性能分析工具 Performance.StartTimer("GameUpdate"); // ... 游戏逻辑 Performance.EndTimer("GameUpdate"); ``` --- ## 📖 文档 ### 详细文档 - [API 文档](Documentation/API/) - 完整的 API 参考 - [教程指南](Documentation/Tutorials/) - 逐步学习指南 - [示例项目](Examples/) - 实际应用示例 - [性能优化](Documentation/Performance/) - 性能调优指南 ### 视频教程 - [入门教程](https://youtube.com/playlist?list=...) - 基础功能介绍 - [高级特性](https://youtube.com/playlist?list=...) - 深入功能讲解 - [实战项目](https://youtube.com/playlist?list=...) - 完整项目开发 --- ## 🤝 贡献指南 我们欢迎社区贡献!请参考以下指南: ### 报告问题 - 使用 [GitHub Issues](https://github.com/your-repo/GameDesigner/issues) 报告 bug - 提供详细的复现步骤和环境信息 - 包含错误日志和截图(如果适用) ### 提交代码 1. Fork 项目仓库 2. 创建功能分支 (`git checkout -b feature/AmazingFeature`) 3. 提交更改 (`git commit -m 'Add some AmazingFeature'`) 4. 推送到分支 (`git push origin feature/AmazingFeature`) 5. 创建 Pull Request ### 代码规范 - 遵循 C# 编码规范 - 添加必要的注释和文档 - 编写单元测试(如果适用) - 确保代码通过代码审查 --- ## 📄 许可证 本项目采用 MIT 许可证 - 查看 [LICENSE](LICENSE) 文件了解详情。 --- ## 🙏 致谢 感谢所有为这个项目做出贡献的开发者! ### 主要贡献者 - [贡献者1](https://github.com/contributor1) - 核心架构设计 - [贡献者2](https://github.com/contributor2) - 网络模块开发 - [贡献者3](https://github.com/contributor3) - 实体系统实现 ### 使用的第三方库 - [Unity Engine](https://unity.com/) - 游戏引擎 - [DOTween](http://dotween.demigiant.com/) - 动画系统 - [ExcelDataReader](https://github.com/ExcelDataReader/ExcelDataReader) - Excel 数据处理 --- ## 📞 联系我们 - **GitHub**: [https://github.com/your-repo/GameDesigner](https://github.com/your-repo/GameDesigner) - **文档**: [https://gamedesigner.readthedocs.io](https://gamedesigner.readthedocs.io) - **讨论区**: [GitHub Discussions](https://github.com/your-repo/GameDesigner/discussions) - **邮箱**: contact@gamedesigner.dev ---
**如果这个项目对你有帮助,请给个 ⭐️ 支持一下!** [⬆️ 返回顶部](#-gamedesigner---游戏开发框架)