2025-12-01 16:46:28 +08:00
|
|
|
|
#if UNITY_EDITOR
|
|
|
|
|
|
using UnityEditor;
|
|
|
|
|
|
using UnityEngine.UIElements;
|
|
|
|
|
|
using System.IO;
|
|
|
|
|
|
using UnityEngine;
|
|
|
|
|
|
using System;
|
|
|
|
|
|
|
2025-12-09 20:31:44 +08:00
|
|
|
|
namespace AlicizaX.UXTool
|
2025-12-01 16:46:28 +08:00
|
|
|
|
{
|
|
|
|
|
|
public class PrefabSingleTab : VisualElement
|
|
|
|
|
|
{
|
|
|
|
|
|
public Button visual;
|
|
|
|
|
|
private string m_guid;
|
|
|
|
|
|
private static int m_maxwidth = PrefabTabs.m_maxWidth;
|
|
|
|
|
|
private static int m_minwidth = PrefabTabs.m_minWidth;
|
|
|
|
|
|
private static int m_maxcharacters = PrefabTabs.m_maxCharacters;
|
|
|
|
|
|
private static int m_mincharacters = PrefabTabs.m_minCharacters;
|
|
|
|
|
|
|
|
|
|
|
|
public PrefabSingleTab(FileInfo info, string guid, int prefabcounts, bool isclose, int width)
|
|
|
|
|
|
{
|
|
|
|
|
|
// 计算每个 tab 的推荐宽度(防空)
|
|
|
|
|
|
SceneView sceneView = SceneView.lastActiveSceneView;
|
|
|
|
|
|
int prewidth = 100;
|
|
|
|
|
|
if (sceneView != null && prefabcounts > 0)
|
|
|
|
|
|
{
|
|
|
|
|
|
prewidth = Mathf.Max(1, (int)sceneView.position.width / Math.Max(1, prefabcounts));
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 根 Button(用于作为 tab 容器并响应 click)
|
|
|
|
|
|
visual = new Button();
|
|
|
|
|
|
visual.name = "Tab";
|
|
|
|
|
|
|
|
|
|
|
|
// 基本样式(尽量还原 UXML 的样式)
|
|
|
|
|
|
visual.style.height = 20;
|
|
|
|
|
|
visual.style.flexDirection = FlexDirection.Row;
|
|
|
|
|
|
visual.style.alignItems = Align.Center;
|
|
|
|
|
|
visual.style.justifyContent = Justify.FlexStart;
|
|
|
|
|
|
visual.style.unityTextAlign = TextAnchor.MiddleCenter;
|
|
|
|
|
|
visual.style.backgroundColor = new StyleColor(new Color(60f / 255f, 60f / 255f, 60f / 255f, 1f));
|
|
|
|
|
|
// margin、padding、border 等默认即可
|
|
|
|
|
|
|
|
|
|
|
|
// Label
|
|
|
|
|
|
Label label = new Label();
|
|
|
|
|
|
label.name = "Label";
|
|
|
|
|
|
label.style.paddingLeft = 5;
|
|
|
|
|
|
label.style.whiteSpace = WhiteSpace.NoWrap;
|
|
|
|
|
|
label.style.unityTextAlign = TextAnchor.MiddleCenter;
|
|
|
|
|
|
label.style.alignSelf = Align.Center;
|
|
|
|
|
|
// label 默认宽度稍后设置为 nowwidth
|
|
|
|
|
|
|
|
|
|
|
|
// 关闭按钮
|
|
|
|
|
|
Button close = new Button();
|
|
|
|
|
|
close.name = "Close";
|
|
|
|
|
|
close.style.width = 20;
|
|
|
|
|
|
close.style.height = 20;
|
|
|
|
|
|
close.style.alignSelf = Align.Center;
|
|
|
|
|
|
close.style.marginLeft = 3;
|
|
|
|
|
|
close.style.marginRight = 3;
|
|
|
|
|
|
|
|
|
|
|
|
close.style.backgroundImage = new StyleBackground(EditorGUIUtility.IconContent("d_winbtn_mac_close_a").image as Texture2D);
|
|
|
|
|
|
close.style.backgroundSize = new BackgroundSize(new Length(80, LengthUnit.Percent), new Length(80, LengthUnit.Percent));
|
|
|
|
|
|
close.style.backgroundColor = Color.clear;
|
|
|
|
|
|
close.style.borderLeftWidth = 0;
|
|
|
|
|
|
close.style.borderRightWidth = 0;
|
|
|
|
|
|
|
|
|
|
|
|
visual.Add(label);
|
|
|
|
|
|
visual.Add(close);
|
|
|
|
|
|
|
|
|
|
|
|
int nowwidth = m_maxwidth;
|
|
|
|
|
|
if (isclose)
|
|
|
|
|
|
{
|
|
|
|
|
|
label.style.width = width;
|
|
|
|
|
|
nowwidth = width;
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
int computed = Math.Min(Math.Max(m_minwidth, prewidth), m_maxwidth);
|
|
|
|
|
|
label.style.width = computed;
|
|
|
|
|
|
nowwidth = computed;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
int nowCharacterscounts = m_maxcharacters;
|
|
|
|
|
|
if (nowwidth < m_maxwidth)
|
|
|
|
|
|
nowCharacterscounts = Math.Max(m_maxcharacters - (int)((m_maxwidth - nowwidth) / 10), m_mincharacters);
|
|
|
|
|
|
|
|
|
|
|
|
m_guid = guid;
|
|
|
|
|
|
string fileName = Path.GetFileNameWithoutExtension(info.Name);
|
|
|
|
|
|
label.text = SetTextWithEllipsis(nowCharacterscounts, fileName);
|
|
|
|
|
|
|
|
|
|
|
|
// 事件绑定(与原逻辑一致)
|
|
|
|
|
|
close.clickable.activators.Add(new ManipulatorActivationFilter { button = MouseButton.LeftMouse });
|
|
|
|
|
|
close.clicked += OnClose;
|
|
|
|
|
|
close.RegisterCallback<MouseEnterEvent, VisualElement>(OnHoverClose, close);
|
|
|
|
|
|
close.RegisterCallback<MouseLeaveEvent, VisualElement>(OnHoverClose, close);
|
|
|
|
|
|
|
|
|
|
|
|
visual.RegisterCallback<MouseEnterEvent>(OnHoverChange);
|
|
|
|
|
|
visual.RegisterCallback<MouseLeaveEvent>(OnHoverChange);
|
|
|
|
|
|
|
|
|
|
|
|
visual.clickable.activators.Add(new ManipulatorActivationFilter { button = MouseButton.LeftMouse });
|
|
|
|
|
|
visual.clicked += OnClick;
|
|
|
|
|
|
visual.RegisterCallback<MouseDownEvent>(Callback);
|
|
|
|
|
|
|
|
|
|
|
|
// 将 visual 作为当前元素的一部分(方便外部访问 this.visual)
|
|
|
|
|
|
this.Add(visual);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void Callback(MouseDownEvent e)
|
|
|
|
|
|
{
|
|
|
|
|
|
if (e.button == 1)
|
|
|
|
|
|
{
|
|
|
|
|
|
ContextMenuUtils.Menu.BuildPrefabTabMenuItem(m_guid);
|
|
|
|
|
|
ContextMenuUtils.ShowContextMenu();
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void OnHoverChange(EventBase e)
|
|
|
|
|
|
{
|
|
|
|
|
|
if (m_guid == PrefabTabs.SelectedGuid) return;
|
|
|
|
|
|
if (e.eventTypeId == MouseEnterEvent.TypeId())
|
|
|
|
|
|
{
|
|
|
|
|
|
visual.style.backgroundColor = new StyleColor(new Color(78f / 255f, 78f / 255f, 78f / 255f, 1f));
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (e.eventTypeId == MouseLeaveEvent.TypeId())
|
|
|
|
|
|
{
|
|
|
|
|
|
visual.style.backgroundColor = new StyleColor(new Color(60f / 255f, 60f / 255f, 60f / 255f, 1f));
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void OnHoverClose(EventBase e, VisualElement close)
|
|
|
|
|
|
{
|
|
|
|
|
|
// if (e.eventTypeId == MouseEnterEvent.TypeId())
|
|
|
|
|
|
// {
|
|
|
|
|
|
// close.style.backgroundColor = new StyleColor(new Color(60f / 255f, 60f / 255f, 60f / 255f, 1f));
|
|
|
|
|
|
// }
|
|
|
|
|
|
// else if (e.eventTypeId == MouseLeaveEvent.TypeId())
|
|
|
|
|
|
// {
|
|
|
|
|
|
// close.style.backgroundColor = new StyleColor(new Color(60f / 255f, 60f / 255f, 60f / 255f, 0f));
|
|
|
|
|
|
// }
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void OnClick()
|
|
|
|
|
|
{
|
|
|
|
|
|
PrefabTabs.OpenTab(m_guid, true);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void OnClose()
|
|
|
|
|
|
{
|
|
|
|
|
|
PrefabTabs.CloseTab(m_guid);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private string SetTextWithEllipsis(int count, string name)
|
|
|
|
|
|
{
|
|
|
|
|
|
if (name.Length <= count)
|
|
|
|
|
|
{
|
|
|
|
|
|
return name;
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
string ans = name.Substring(0, Math.Max(0, count - 3));
|
|
|
|
|
|
ans += "...";
|
|
|
|
|
|
return ans;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
#endif
|