From 9d5fccf39d45a1fa4efcf53b6fac0bbcb2aae6b6 Mon Sep 17 00:00:00 2001 From: Ding Yuntian <1491671119@qq.com> Date: Tue, 3 Mar 2026 21:44:57 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E6=96=B0=E5=A2=9E=20CablePanel=20?= =?UTF-8?q?=E7=94=B5=E7=BC=86=E9=9D=A2=E6=9D=BF=E7=BB=84=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Made-with: Cursor --- .../Screen System/FixPanel/CablePanel.cs | 294 ++++++++++++++++++ .../Screen System/FixPanel/CablePanel.cs.meta | 11 + 2 files changed, 305 insertions(+) create mode 100644 Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs create mode 100644 Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs.meta diff --git a/Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs b/Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs new file mode 100644 index 000000000..c5c272f4e --- /dev/null +++ b/Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs @@ -0,0 +1,294 @@ +using UnityEngine; +using DG.Tweening; +using AibisDream.Kit; +using AibisDream.Framework; + +namespace AibisDream.FixSystem +{ + public enum CableMode + { + None, // 都隐藏(收起状态) + Visual, // 使用 Cable(拖拽时) + Physic // 使用 PhysicCable(闲置时) + } + + public class CablePanel : MonoBehaviour, IOperatorPanel + { + private const string CableRetractedKey = "$global.cableRetracted"; + private const int SortingOrderRetracted = 41; + + #region 组件索引 + + [Header("其他索引")] + [SerializeField] private FixLightSystem fixLightSystem; + public FixLightSystem FixLightSystem => fixLightSystem; + + [Header("插线组件索引")] + [SerializeField] private Plug plugRef; + [SerializeField] private Cable cableRef; + [SerializeField] private PhysicCable physicCableRef; + [SerializeField] private Transform cableRootPos; + [SerializeField] private CableReel cableReelRef; + + public Plug PlugRef => plugRef; + public Cable CableRef => cableRef; + public PhysicCable PhysicCableRef => physicCableRef; + public Transform CableRootPos => cableRootPos; + public CableReel CableReelRef => cableReelRef; + + public BodyModuleSystem BodyModuleSystem { get; private set; } + + #endregion + + #region 系统状态 + public bool isCableRetracted = true; // 线缆是否收起 + + [SerializeField] private Transform retractedPos; // 收起位置 + + private ISocket curSocket; + + #endregion + + private void Start() + { + InitComponentRefs(); + + InitSystem(); + LoadCableState(); + } + + private void OnDestroy() + { + plugRef.OnInsertSocket -= OnInsertSocket; + plugRef.OnPullUpSocket -= OnPullUpSocket; + plugRef.OnPlugPointerDown -= OnPlugPoinerDown; + } + + private void InitComponentRefs() + { + BodyModuleSystem = FixSystemCenter.SystemDic.Get(); + } + + private void InitSystem() + { + plugRef.OnInsertSocket += OnInsertSocket; + plugRef.OnPullUpSocket += OnPullUpSocket; + plugRef.OnPlugPointerDown += OnPlugPoinerDown; + } + + private void LoadCableState() + { + // 从Prefab读取 + if (isCableRetracted) + { + SetRetractCable(); + } + else + { + PlugRef.ReturnToStartPosition(); + } + + // // 从存储系统读取 + // if (!StorageSystem.Instance.TryGetValue(CableRetractedKey, out bool savedRetractedState)) + // return; + + // if (savedRetractedState) + // { + // SetRetractCable(); + // } + // else + // { + // if (isCableRetracted) + // DropDownCable(); + // } + } + + private void SaveCableState() + { + Debug.Log("Save cableRetractedstate" + isCableRetracted); + StorageSystem.Instance.SetValue(CableRetractedKey, isCableRetracted); + } + + private void Update() + { + // 获取线缆方向并更新转盘旋转 + if (CableRef != null && CableReelRef != null) + { + CableReelRef.UpdateRotation(); + } + } + + public void ResetPlug() + { + // 不在初始插孔里,就从当前插孔拔出来,插回初始插孔 + PlugRef.PullUpSocket(); + BodyModuleSystem.CloseModuleSlots(null); + PlugRef.ReturnToStartPosition(); + AudioManager.Instance.PlaySfx("event:/ActionFB/mods_close"); + AudioManager.Instance.PlaySfx("event:/FollowInput/plugdrop"); + } + + // ------------------------------ 插头事件 ------------------------------ + private void OnInsertSocket(ISocket socket) + { + curSocket = socket; + CableRef.SetEndPos(socket.GetSocketPos()); + AudioManager.Instance.PlaySfx("event:/FollowInput/plugin"); + + if (socket is BodyModule bodyModule) + { + // 插入模块时触发插入事件 + EnumEventSystem.Global.Send(EventEnum.PlugIn); + } + } + + private void OnPullUpSocket() + { + // 修改线头位置 + CableRef.SetEndPos(PlugRef.PlugRoot); + + curSocket?.PlugOut(); + AudioManager.Instance.PlaySfx("event:/FollowInput/plugout"); + + // 如果是模块 + if (curSocket is BodyModule) + { + EnumEventSystem.Global.Send(EventEnum.PlugOut); + } + + curSocket = null; + } + + private void OnPlugPoinerDown() + { + if (IsPlugInSocket()) PlugRef.PullUpSocket(); + + // 点击时切换到视觉线缆 + SetCableMode(CableMode.Visual); + + // 打开插孔 + BodyModuleSystem.OpenModuleSlots(); + } + + // ------------------------------ 系统状态 ------------------------------ + public bool IsPlugInSocket() + { + return curSocket != null; + } + + // ------------------------------ 线缆操作 ------------------------------ + + /// + /// 设置线缆显示模式 + /// + /// 线缆模式 + /// PhysicCable跟随的目标,默认为Plug + public void SetCableMode(CableMode mode, Transform followTarget = null) + { + switch (mode) + { + case CableMode.None: + CableRef.HideCable(); + PhysicCableRef.HideCable(); + PhysicCableRef.SetTarget(null); + break; + + case CableMode.Visual: + CableRef.ShowCable(); + PhysicCableRef.HideCable(); + PhysicCableRef.SetTarget(null); + break; + + case CableMode.Physic: + CableRef.HideCable(); + PhysicCableRef.ShowCable(); + PhysicCableRef.Init(PlugRef.transform.position); + PhysicCableRef.SetTarget(followTarget != null ? followTarget : PlugRef.transform); + break; + } + } + + /// + /// 寻找最接近的Module + /// + /// 源位置 + /// 最近的Module + /// 是否能找到目标范围内的Module + public bool TryFindClosestModule(Vector3 sourcePos, out BodyModule targetModule) + { + var res = BodyModuleSystem.TryFindClosestModule(sourcePos, out targetModule); + BodyModuleSystem.CloseModuleSlots(targetModule); + return res; + } + + public void PullUpCable() + { + if (isCableRetracted) return; + + if (IsPlugInSocket()) + { + PlugRef.PullUpSocket(); + } + + BodyModuleSystem.CloseModuleSlots(null); + + PlugRef.transform.DOMove(retractedPos.position, 0.1f).OnComplete(() => + { + ApplyRetractedState(); + isCableRetracted = true; + SaveCableState(); + }); + + AudioManager.Instance.PlaySfx("event:/ActionFB/mods_close"); + AudioManager.Instance.PlaySfx("event:/FollowInput/plugdrop"); + } + + public void DropDownCable() + { + if (!isCableRetracted) return; + // 确保 Plug 已脱离 Socket(收起状态下通常已脱离,此处为防御性调用) + PlugRef.PullUpSocket(); + CableReelRef.ResetRotation(); + PlugRef.transform.DOMove(PlugRef.GetStartPos(), 0.1f).OnComplete(() => + { + SetCableMode(CableMode.Physic); + isCableRetracted = false; + SaveCableState(); + }); + } + + /// 应用收起状态的视觉与组件设置(不含动画、不含 isCableRetracted 更新) + private void ApplyRetractedState() + { + SetCableMode(CableMode.None); + + PlugRef.transform.position = retractedPos.position; + PlugRef.transform.rotation = retractedPos.rotation; + + var plugSprite = PlugRef.GetComponent(); + plugSprite.sortingLayerName = CableReelRef.GetComponent().sortingLayerName; + plugSprite.sortingOrder = SortingOrderRetracted; + } + + public void SetRetractCable() + { + ApplyRetractedState(); + isCableRetracted = true; + } + + public void Init() + { + + } + + public void Open() + { + + } + + public void Close() + { + + } + } +} \ No newline at end of file diff --git a/Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs.meta b/Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs.meta new file mode 100644 index 000000000..80d1e2e94 --- /dev/null +++ b/Assets/Scripts/FixSystemNew/Screen System/FixPanel/CablePanel.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 870725094d1affd4bbe0ca4723fe18ae +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: