Files
3d-bianpo/Assets/Scripts/Ui/PnlIcon.cs
2026-03-03 11:30:53 +08:00

342 lines
11 KiB
C#
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;
using Newtonsoft.Json;
public class IconDataHolder : MonoBehaviour
{
public IconData Data;
}
public class PnlIcon : ActionBase
{
private Dictionary<PageType, List<GameObject>> iconLists = new Dictionary<PageType, List<GameObject>>
{
{ PageType.Icon01, new List<GameObject>() },
{ PageType.Icon02, new List<GameObject>() },
{ PageType.Icon03, new List<GameObject>() },
{ PageType.Icon04, new List<GameObject>() },
// { PageType.Icon05, new List<GameObject>() }
};
private Dictionary<PageType, List<IconData>> appCacheLists;
private void InitializeAppCacheLists()
{
appCacheLists = new Dictionary<PageType, List<IconData>>
{
{ PageType.Icon01, AppCache.iconPointList01 },
{ PageType.Icon02, AppCache.iconPointList02 },
{ PageType.Icon03, AppCache.iconPointList03 },
{ PageType.Icon04, AppCache.iconPointList04 },
};
}
private Dictionary<PageType, string> textPrefixes = new Dictionary<PageType, string>
{
{ PageType.Icon01, "gnss监测" },
{ PageType.Icon02, "水位" },
{ PageType.Icon03, "雨量监测" },
{ PageType.Icon04, "渗压计监测" },
};
private Dictionary<PageType, string> prefabPaths = new Dictionary<PageType, string>
{
{ PageType.Icon01, "Icon2D/iconPrefab" },
{ PageType.Icon02, "Icon2D/iconPrefab" },
{ PageType.Icon03, "Icon2D/iconPrefab" },
{ PageType.Icon04, "Icon2D/iconPrefab" },
};
private static readonly Dictionary<PageType, string> IconMapping = new Dictionary<PageType, string>
{
{ PageType.Icon01, "MT014" },
{ PageType.Icon02, "MT011" },
{ PageType.Icon03, "MT002" },
{ PageType.Icon04, "MT032" }
};
private GameObject Player;
private CameraRover cameraRover;
void Awake()
{
Player = GameObject.Find("Player");
if (Player != null)
{
// 获取 Player 上挂载的 CameraRover 脚本实例
cameraRover = Player.GetComponent<CameraRover>();
}
}
void Update()
{
}
public override void Init()
{
gameObject.SetActive(true);
}
public override void RegisterAction()
{
GameEvent.OpenPage += Open;
GameEvent.ClosePage += Close;
}
public override void RemoveAction()
{
GameEvent.OpenPage -= Open;
GameEvent.ClosePage -= Close;
}
void Open(PageType type)
{
// Debug.Log(type);
OpenIcon(type);
}
void Close(PageType type)
{
CloseIcon(type);
}
// void OpenIcon(PageType type)
// { // 确保 AppCache 列表已初始化
// if (!IsAppCacheInitialized())
// {
// // Debug.LogError("AppCache 列表未初始化!");
// return;
// }
// // 确保 appCacheLists 已初始化
// if (appCacheLists == null)
// {
// InitializeAppCacheLists();
// }
// if (!appCacheLists.ContainsKey(type) || appCacheLists[type] == null)
// {
// // Debug.LogError($"类型 {type} 的列表为空或不存在!");
// return;
// }
// List<IconData> iconDataList = appCacheLists[type];
// string prefabPath = prefabPaths[type];
// string textPrefix = textPrefixes[type];
// // Debug.Log(IconMapping[type]);
// for (int i = 0; i < iconDataList.Count; i++)
// {
// IconData iconData = iconDataList[i];
// // 确保数据有效
// if (iconData == null || iconData.iconTransform == null)
// continue;
// // 预制体对象
// GameObject prefab = Resources.Load<GameObject>(prefabPath);
// GameObject icon = PoolManager.Instance.Spawn(prefab);
// // 使用 iconTransform 的 name 和 position
// icon.name = iconData.iconName;
// icon.transform.SetParent(transform);
// icon.transform.localScale = Vector3.one * 0.8f;
// icon.GetComponent<IconFollow2D>().targetPos = iconData.iconTransform.position;
// Transform txtMsgTransform = FindChildRecursive(icon.transform, "txtMsg");
// Text textComponent = txtMsgTransform.GetComponent<Text>();
// textComponent.text = icon.name;
// Transform iconBgTransform = FindChildRecursive(icon.transform, "iconBg");
// Image iconBgImage = iconBgTransform.GetComponent<Image>();
// Sprite sprite = Resources.Load<Sprite>($"icons/{IconMapping[type]}");
// iconBgImage.sprite = sprite;
// iconLists[type].Add(icon);
// EventListener.AddPointerClickListener(icon, (clickEventData) => OnIconClick(iconData)); ;
// }
// }
void OpenIcon(PageType type)
{
if (!IsAppCacheInitialized())
{
// Debug.LogError("AppCache 列表未初始化!");
return;
}
// 确保 appCacheLists 已初始化
if (appCacheLists == null)
{
InitializeAppCacheLists();
}
if (!appCacheLists.ContainsKey(type) || appCacheLists[type] == null)
{
// Debug.LogError($"类型 {type} 的列表为空或不存在!");
return;
}
List<IconData> iconDataList = appCacheLists[type];
string prefabPath = prefabPaths[type];
// 1. 提前加载预制体和精灵资源,避免重复加载
GameObject prefab = Resources.Load<GameObject>(prefabPath);
Sprite iconSprite = Resources.Load<Sprite>($"icons/{IconMapping[type]}");
// 检查资源是否成功加载
if (prefab == null || iconSprite == null)
{
Debug.LogError($"资源加载失败: Prefab={prefabPath}, Sprite=icons/{IconMapping[type]}");
return;
}
// 2. 初始化列表(如果需要)
if (iconLists[type] == null)
iconLists[type] = new List<GameObject>();
// 3. 使用协程分帧创建对象,减少单帧压力
StartCoroutine(CreateIconsOverTime(type, iconDataList, prefab, iconSprite));
}
IEnumerator CreateIconsOverTime(PageType type, List<IconData> iconDataList, GameObject prefab, Sprite iconSprite)
{
int batchSize = 5; // 每帧创建的对象数量
int framesBetweenBatches = 1; // 创建批次之间的帧数
for (int i = 0; i < iconDataList.Count; i++)
{
IconData iconData = iconDataList[i];
if (iconData == null || iconData.iconTransform == null)
continue;
// 从对象池生成图标
GameObject icon = PoolManager.Instance.Spawn(prefab);
SetupIcon(icon, iconData, iconSprite);
iconLists[type].Add(icon);
// 控制创建速率
if ((i + 1) % batchSize == 0)
{
// 每创建batchSize个对象后等待几帧
for (int f = 0; f < framesBetweenBatches; f++)
yield return null;
}
}
// 4. 加载完成后强制垃圾回收
yield return new WaitForSeconds(0.5f);
Resources.UnloadUnusedAssets();
System.GC.Collect();
}
void SetupIcon(GameObject icon, IconData iconData, Sprite iconSprite)
{
// 设置图标基本属性
icon.name = iconData.iconName;
icon.transform.SetParent(transform);
icon.transform.localScale = Vector3.one * 0.8f;
icon.GetComponent<IconFollow2D>().targetPos = iconData.iconTransform.position;
// 获取并设置文本组件
Transform txtMsgTransform = FindChildRecursive(icon.transform, "txtMsg");
Text textComponent = txtMsgTransform.GetComponent<Text>();
textComponent.text = icon.name;
// 设置图标背景
Transform iconBgTransform = FindChildRecursive(icon.transform, "iconBg");
Image iconBgImage = iconBgTransform.GetComponent<Image>();
iconBgImage.sprite = iconSprite;
// 添加点击事件
EventListener.AddPointerClickListener(icon, (clickEventData) => OnIconClick(iconData));
}
private bool IsAppCacheInitialized()
{
return AppCache.iconPointList01 != null &&
AppCache.iconPointList02 != null &&
AppCache.iconPointList03 != null &&
AppCache.iconPointList04 != null;
}
void CloseIcon(PageType type)
{
if (!iconLists.ContainsKey(type))
{
return;
}
for (int i = 0; i < iconLists[type].Count; i++)
{
PoolManager.Instance.Unspawn(iconLists[type][i]);
}
iconLists[type].Clear();
}
private Transform FindChildRecursive(Transform parent, string name)
{
foreach (Transform child in parent)
{
if (child.name == name)
return child;
// 递归查找子对象的子对象
Transform found = FindChildRecursive(child, name);
if (found != null)
return found;
}
return null;
}
void OnIconClick(IconData iconData)
{
if (iconData != null && cameraRover != null)
{
cameraRover.StartCoroutine(cameraRover.CallOpenItem(iconData.cameraTransform));
cameraRover.SetTargetPosition(iconData.iconTransform.position);
// Debug.Log($"点击的图标信息:");
// Debug.Log($"device_sn: {iconData.device_sn}");
// Debug.Log($"iconName: {iconData.iconName}");
// Debug.Log($"identifier: {iconData.identifier}");
// Debug.Log($"iconTransform: {iconData.iconTransform}");
// Debug.Log($"cameraName: {iconData.cameraName}");
// Debug.Log($"cameraTransform: {iconData.cameraTransform.position}");
// Debug.Log(iconData.iconTransform.position);
StartCoroutine(WaitForFlightCompletion(iconData));
cameraRover.StartCoroutine(cameraRover.CallOpenItem(iconData.cameraTransform));
}
else
{
Debug.LogWarning("点击的图标没有关联的 IconData");
}
}
private IEnumerator WaitForFlightCompletion(IconData iconData)
{
// 等待飞行结束
while (!cameraRover.isFlightCompleted)
{
yield return null;
}
// 飞行结束,执行网络请求和数据发送操作
string BASE_URL = "/api.php/Device/deviceDetail?device_sn=" + iconData.device_sn + "&identifier=" + iconData.identifier;
string url = WebService.IsRunningInWebGL() ? BASE_URL : AppCache.url + BASE_URL;
WebService.Instance.Get<JsonDetails>(url, delegate (JsonDetails details)
{
var dataToSend = new DataToSend
{
dataItem = details.result,
iconName = iconData.iconName
};
string jsonData = JsonConvert.SerializeObject(dataToSend);
// Debug.Log("序列化后的JSON: " + jsonData);
Application.ExternalCall("sendDataToVue", jsonData);
cameraRover.SetFlightCompleted(false);
});
}
}