(client) feat:实现右键菜单
This commit is contained in:
@ -16,66 +16,13 @@ namespace Prefab
|
||||
|
||||
public void Init(Data.PawnDef pawnDef)
|
||||
{
|
||||
entity.attributes = pawnDef.attributes.Clone();
|
||||
entity.aiTree = ConvertToAIBase(pawnDef.behaviorTree);
|
||||
entity.Init(pawnDef);
|
||||
|
||||
outline.Init();
|
||||
outline.Hide();
|
||||
}
|
||||
public static AIBase ConvertToAIBase(BehaviorTreeDef behaviorTreeDef)
|
||||
{
|
||||
if (behaviorTreeDef == null)
|
||||
return null;
|
||||
AIBase aiBase = CreateAIBaseInstance(behaviorTreeDef.className);
|
||||
if (behaviorTreeDef.childTree != null)
|
||||
{
|
||||
foreach (var child in behaviorTreeDef.childTree)
|
||||
{
|
||||
if (child != null)
|
||||
{
|
||||
aiBase.children.Add(ConvertToAIBase(child));
|
||||
}
|
||||
}
|
||||
}
|
||||
return aiBase;
|
||||
}
|
||||
|
||||
// 使用反射根据 className 创建具体的 AIBase 子类实例
|
||||
private static AIBase CreateAIBaseInstance(string className)
|
||||
{
|
||||
if (string.IsNullOrEmpty(className))
|
||||
throw new ArgumentException("className 不能为空");
|
||||
if (className.Equals("AIBase", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
return (AIBase)Activator.CreateInstance(typeof(AIBase));
|
||||
}
|
||||
// 定义可能的命名空间列表
|
||||
var possibleNamespaces = new[] { "AI"};
|
||||
|
||||
foreach (var ns in possibleNamespaces)
|
||||
{
|
||||
try
|
||||
{
|
||||
// 获取当前程序集
|
||||
var assembly = typeof(AIBase).Assembly;
|
||||
|
||||
// 尝试查找类型
|
||||
var type = assembly.GetType($"{ns}.{className}");
|
||||
|
||||
if (type != null && typeof(AIBase).IsAssignableFrom(type))
|
||||
{
|
||||
// 如果找到合适的类型,则创建实例并返回
|
||||
return (AIBase)Activator.CreateInstance(type);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
// 忽略单个命名空间的错误,继续尝试下一个命名空间
|
||||
}
|
||||
}
|
||||
|
||||
// 如果所有命名空间都未找到对应的类型,抛出异常
|
||||
throw new InvalidOperationException($"无法找到类型 {className} 或该类型不是 AIBase 的子类");
|
||||
}
|
||||
}
|
||||
}
|
89
Client/Assets/Scripts/Prefab/RightMenuPrefab.cs
Normal file
89
Client/Assets/Scripts/Prefab/RightMenuPrefab.cs
Normal file
@ -0,0 +1,89 @@
|
||||
using System.Collections.Generic;
|
||||
using UnityEngine;
|
||||
using UnityEngine.Events;
|
||||
using UnityEngine.EventSystems;
|
||||
|
||||
namespace Prefab
|
||||
{
|
||||
public class RightMenuPrefab: Utils.MonoSingleton<RightMenuPrefab>,IPointerExitHandler
|
||||
{
|
||||
public GameObject menu;
|
||||
public ButtonPrefab buttonPrefab;
|
||||
|
||||
public void Show()
|
||||
{
|
||||
gameObject.SetActive(true);
|
||||
}
|
||||
|
||||
public void Hide()
|
||||
{
|
||||
gameObject.SetActive(false);
|
||||
}
|
||||
|
||||
public void Init(List<(string name, UnityAction callback)> buttons)
|
||||
{
|
||||
if (menu == null || buttonPrefab == null)
|
||||
{
|
||||
Debug.LogError("Menu or ButtonPrefab is not assigned!");
|
||||
return;
|
||||
}
|
||||
|
||||
ClearMenu();
|
||||
foreach (var (label, callback) in buttons)
|
||||
{
|
||||
// 实例化按钮预制体
|
||||
var instantiatedButton = Instantiate(buttonPrefab.gameObject, menu.transform);
|
||||
var buttonInstance = instantiatedButton.GetComponent<ButtonPrefab>();
|
||||
|
||||
if (buttonInstance != null)
|
||||
{
|
||||
// 设置按钮文本
|
||||
buttonInstance.Label = label;
|
||||
|
||||
// 创建一个新的回调函数,包含原始回调和隐藏菜单的操作
|
||||
UnityAction wrappedCallback = () =>
|
||||
{
|
||||
try
|
||||
{
|
||||
// 执行原始回调
|
||||
callback?.Invoke();
|
||||
}
|
||||
catch (System.Exception e)
|
||||
{
|
||||
Debug.LogError($"Error executing callback for button '{label}': {e.Message}");
|
||||
}
|
||||
finally
|
||||
{
|
||||
// 隐藏菜单
|
||||
Hide();
|
||||
}
|
||||
};
|
||||
|
||||
// 添加包装后的回调
|
||||
buttonInstance.AddListener(wrappedCallback);
|
||||
}
|
||||
else
|
||||
{
|
||||
Debug.LogError("Failed to get ButtonPrefab component from instantiated object!");
|
||||
}
|
||||
}
|
||||
}
|
||||
public void ClearMenu()
|
||||
{
|
||||
// 遍历菜单下的所有子对象并销毁它们
|
||||
foreach (Transform child in menu.transform)
|
||||
{
|
||||
Destroy(child.gameObject);
|
||||
}
|
||||
}
|
||||
protected override void OnStart()
|
||||
{
|
||||
Hide();
|
||||
}
|
||||
|
||||
public void OnPointerExit(PointerEventData eventData)
|
||||
{
|
||||
Hide();
|
||||
}
|
||||
}
|
||||
}
|
3
Client/Assets/Scripts/Prefab/RightMenuPrefab.cs.meta
Normal file
3
Client/Assets/Scripts/Prefab/RightMenuPrefab.cs.meta
Normal file
@ -0,0 +1,3 @@
|
||||
fileFormatVersion: 2
|
||||
guid: e45cfe2f36eb4f589b6d8f331567974d
|
||||
timeCreated: 1753196238
|
Reference in New Issue
Block a user