首次提交

This commit is contained in:
Bob.Song
2026-03-05 18:07:55 +08:00
commit e125bb869e
4534 changed files with 563920 additions and 0 deletions

View File

@@ -0,0 +1,192 @@
using System;
using System.Collections.Generic;
using UnityEditor;
using UnityEditor.IMGUI.Controls;
using UnityEngine;
using UnityEngine.Serialization;
using Object = UnityEngine.Object;
namespace NBC.Asset.Editor
{
public class CollectorWindow : EditorWindow
{
[MenuItem(Language.CollectorWindowMenuPath, false, 1)]
public static void ShowWindow()
{
CollectorWindow wnd =
GetWindow<CollectorWindow>(Language.CollectorWindowName, true, Defs.DockedWindowTypes);
wnd.minSize = new Vector2(Defs.DefWindowWidth, Defs.DefWindowHeight);
}
public PackageConfig SelectPackageConfig;
public GroupConfig SelectGroupConfig;
readonly VerticalSplitter _verticalSplitter = new VerticalSplitter();
readonly HorizontalSplitter _horizontalSplitter1 = new HorizontalSplitter(0.2f, 0.1f, 0.3f);
readonly HorizontalSplitter _horizontalSplitter2 = new HorizontalSplitter(0.2f, 0.1f, 0.3f);
const int _splitterThickness = 2;
PackageTreeEditor _packagesList;
GroupTreeEditor _groupsList;
private AssetsTreeEditor _assetsList;
private GroupInfoGUI _groupInfoGUI;
public void UpdateSelectedPackage(string packageName)
{
if (!string.IsNullOrEmpty(packageName))
{
var packages = CollectorSetting.Instance.Packages;
if (packages == null) return;
foreach (var package in packages)
{
if (package.Name != packageName) continue;
SelectPackageConfig = package;
SelectGroupConfig = null;
}
}
else
{
SelectPackageConfig = null;
SelectGroupConfig = null;
}
_groupsList?.Reload();
_groupsList?.SetSelection(new List<int>());
_assetsList?.Reload();
}
public void UpdateSelectedGroup(string groupName)
{
if (!string.IsNullOrEmpty(groupName))
{
if (SelectPackageConfig == null) return;
foreach (var group in SelectPackageConfig.Groups)
{
if (group.Name != groupName) continue;
SelectGroupConfig = group;
}
}
else
{
SelectGroupConfig = null;
}
_assetsList?.Reload();
}
public void UpdateAssets()
{
Builder.Gather();
_assetsList?.Reload();
}
protected void OnEnable()
{
Builder.Gather();
Styles.Initialize();
}
protected void OnGUI()
{
GUI.skin.label.richText = true;
GUI.skin.label.alignment = TextAnchor.UpperLeft;
EditorStyles.label.richText = true;
EditorStyles.textField.wordWrap = true;
EditorStyles.foldout.richText = true;
DrawToolBar();
var barHeight = EditorStyles.toolbar.fixedHeight + _splitterThickness;
Rect contentRect = new Rect(_splitterThickness, barHeight, position.width - _splitterThickness * 4,
position.height - barHeight - _splitterThickness);
var resizingPackage = _horizontalSplitter1.OnGUI(contentRect, out var packageRect, out var groupRect);
DrawPackagesList(packageRect);
var resizingGroup = _horizontalSplitter2.OnGUI(groupRect, out var groupListRect, out var groupInfoRect);
DrawGroupList(groupListRect);
bool resizingVer = _verticalSplitter.OnGUI(groupInfoRect, out var groupBaseInfo, out var groupAssetList);
DrawGroupInfo(groupBaseInfo);
DrawAssetList(groupAssetList);
if (resizingPackage || resizingGroup || resizingVer)
Repaint();
}
void DrawToolBar()
{
EditorGUILayout.BeginHorizontal(EditorStyles.toolbar);
var guiMode = new GUIContent(Language.Tools);
Rect rMode = GUILayoutUtility.GetRect(guiMode, EditorStyles.toolbarDropDown);
if (EditorGUI.DropdownButton(rMode, guiMode, FocusType.Passive, EditorStyles.toolbarDropDown))
{
var menu = new GenericMenu();
menu.AddItem(new GUIContent(Language.Profiler), false, () => { });
menu.AddItem(new GUIContent(Language.Analyse), false, () => { });
menu.DropDown(rMode);
}
GUILayout.FlexibleSpace();
if (GUILayout.Button(Language.Build, EditorStyles.toolbarButton))
{
Builder.Build();
}
if (GUILayout.Button(Language.Save, EditorStyles.toolbarButton, GUILayout.ExpandWidth(false)))
{
CollectorSetting.Instance.Save();
}
GUILayout.EndHorizontal();
}
void DrawPackagesList(Rect rect)
{
if (_packagesList == null)
{
_packagesList = new PackageTreeEditor(new TreeViewState(), this,
PackageTreeEditor.CreateDefaultMultiColumnHeaderState());
}
_packagesList.OnGUI(rect);
}
void DrawGroupList(Rect rect)
{
if (_groupsList == null)
{
_groupsList = new GroupTreeEditor(new TreeViewState(), this,
GroupTreeEditor.CreateDefaultMultiColumnHeaderState());
}
_groupsList.OnGUI(rect);
}
void DrawGroupInfo(Rect rect)
{
if (_groupInfoGUI == null)
{
_groupInfoGUI = new GroupInfoGUI(this);
}
_groupInfoGUI.OnGUI(rect);
}
void DrawAssetList(Rect rect)
{
if (_assetsList == null)
{
_assetsList = new AssetsTreeEditor(new TreeViewState(), this,
AssetsTreeEditor.CreateDefaultMultiColumnHeaderState());
}
_assetsList.OnGUI(rect);
}
}
}

View File

@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 64eabfbca2143c940a620e3fe03f8e2c
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

View File

@@ -0,0 +1,49 @@
// using System.Collections.Generic;
// using UnityEditor.IMGUI.Controls;
//
// namespace NBC.Asset.Editor
// {
// public class PackagesListTreeView : TreeView
// {
// private TreeViewItem mRoot = null;
//
// public PackagesListTreeView(TreeViewState state, AssetGroupMgr ctrl, MultiColumnHeaderState mchs) : base(state,
// new MultiColumnHeader(mchs))
// {
// showBorder = true;
//
// showAlternatingRowBackgrounds = false;
// mController = ctrl;
// Refresh();
// Reload();
// }
//
// protected override TreeViewItem BuildRoot()
// {
// mRoot = new TreeViewItem
// {
// id = -1,
// depth = -1,
// children = new List<TreeViewItem>()
// };
// int id = 0;
// var packages = CollectorSetting.Instance.Packages;
// foreach (var package in packages)
// {
// id++;
// var t = new PackageTreeViewItem(id, package);
// mRoot.AddChild(t);
// }
//
// return mRoot;
// }
//
// public PackagesListTreeView(TreeViewState state) : base(state)
// {
// }
//
// public PackagesListTreeView(TreeViewState state, MultiColumnHeader multiColumnHeader) : base(state, multiColumnHeader)
// {
// }
// }
// }

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 5a53cbb0029c40c6a39fa066cbae38d5
timeCreated: 1679405350

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 4ef2c25ab0b24e8c90faeec8bbad5cf8
timeCreated: 1679386737

View File

@@ -0,0 +1,239 @@
using System;
using System.Collections.Generic;
using System.IO;
using UnityEditor;
using UnityEditor.IMGUI.Controls;
using UnityEngine;
namespace NBC.Asset.Editor
{
public sealed class AssetTreeViewItem : TreeViewItem
{
private BuildAsset _asset;
public BuildAsset Asset => _asset;
public AssetTreeViewItem(int id, BuildAsset asset) : base(id, id, asset.Path)
{
_asset = asset;
icon = AssetDatabase.GetCachedIcon(asset.Path) as Texture2D;
}
}
public class AssetsTreeEditor : TreeView
{
public static MultiColumnHeaderState CreateDefaultMultiColumnHeaderState()
{
return new MultiColumnHeaderState(GetColumns());
}
private static MultiColumnHeaderState.Column[] GetColumns()
{
List<MultiColumnHeaderState.Column> retVal = new List<MultiColumnHeaderState.Column>();
retVal.Add(EditUtil.GetMultiColumnHeaderColumn(Language.Path,200));
retVal.Add(EditUtil.GetMultiColumnHeaderColumn(Language.FileSize));
retVal.Add(EditUtil.GetMultiColumnHeaderColumn(Language.AddressPath));
return retVal.ToArray();
}
/// <summary>
/// 当前选中了
/// </summary>
private bool mContextOnItem;
CollectorWindow _window;
public MultiColumnHeaderState HeaderState;
public AssetsTreeEditor(TreeViewState state, CollectorWindow window, MultiColumnHeaderState header) : base(state,
new MultiColumnHeader(header))
{
_window = window;
HeaderState = header;
showBorder = true;
showAlternatingRowBackgrounds = true;
Reload();
}
private TreeViewItem _root = null;
protected override TreeViewItem BuildRoot()
{
_root = new TreeViewItem
{
id = -1,
depth = -1,
children = new List<TreeViewItem>()
};
int id = 0;
var cache = Caches.Get();
if (cache.Assets.Count > 0)
{
if (_window.SelectPackageConfig != null && _window.SelectGroupConfig != null)
{
foreach (var asset in cache.Assets)
{
if (asset.Group == null) continue;
if (asset.Group != _window.SelectGroupConfig)
continue;
id++;
var t = new AssetTreeViewItem(id, asset);
_root.AddChild(t);
}
}
}
return _root;
}
enum MyColumns
{
Asset,
Size,
Path
}
public override void OnGUI(Rect rect)
{
base.OnGUI(rect);
HeaderState.AutoWidth(rect.width,2);
if (UnityEngine.Event.current.type == EventType.MouseDown && UnityEngine.Event.current.button == 0 &&
rect.Contains(UnityEngine.Event.current.mousePosition))
{
SetSelection(Array.Empty<int>(), TreeViewSelectionOptions.FireSelectionChanged);
}
}
protected override void RowGUI(RowGUIArgs args)
{
for (int i = 0; i < args.GetNumVisibleColumns(); ++i)
{
CellGUI(args.GetCellRect(i), args.item, args.GetColumn(i), ref args);
}
}
private void CellGUI(Rect cellRect, TreeViewItem item, int column, ref RowGUIArgs args)
{
AssetTreeViewItem assetTreeViewItem = item as AssetTreeViewItem;
if (assetTreeViewItem == null) return;
var assetData = assetTreeViewItem.Asset;
Color oldColor = GUI.color;
CenterRectUsingSingleLineHeight(ref cellRect);
if (!File.Exists(assetData.Path))
{
GUI.color = Color.red;
}
switch ((MyColumns)column)
{
case MyColumns.Asset:
{
var iconRect = new Rect(cellRect.x + 1, cellRect.y + 1, cellRect.height - 2, cellRect.height - 2);
if (item.icon != null)
{
GUI.DrawTexture(iconRect, item.icon, ScaleMode.ScaleToFit);
}
var nameRect = new Rect(cellRect.x + iconRect.xMax + 1
, cellRect.y, cellRect.width - iconRect.width, cellRect.height);
DefaultGUI.Label(nameRect,
item.displayName,
args.selected,
args.focused);
}
break;
case MyColumns.Size:
EditorGUI.LabelField(cellRect, GetSizeString(assetData), GUITools.DefLabelStyle);
break;
case MyColumns.Path:
DefaultGUI.Label(cellRect, assetData.Address, args.selected, args.focused);
break;
}
GUI.color = oldColor;
}
/// <summary>
/// 点击的时候
/// </summary>
protected override void ContextClicked()
{
if (HasSelection())
{
mContextOnItem = false;
}
}
protected override void DoubleClickedItem(int id)
{
if (FindItem(id, rootItem) is AssetTreeViewItem assetItem)
{
UnityEngine.Object o = AssetDatabase.LoadAssetAtPath<UnityEngine.Object>(assetItem.Asset.Path);
EditorGUIUtility.PingObject(o);
Selection.activeObject = o;
}
}
protected override void ContextClickedItem(int id)
{
if (mContextOnItem)
{
mContextOnItem = false;
return;
}
mContextOnItem = true;
List<int> selectedNodes = new List<int>();
foreach (var nodeID in GetSelection())
{
selectedNodes.Add(nodeID);
}
GenericMenu menu = new GenericMenu();
if (selectedNodes.Count == 1)
{
menu.AddItem(new GUIContent(Language.CopyPath), false, CopyPath, selectedNodes);
menu.AddItem(new GUIContent(Language.CopyAddressPath), false, CopyAddressPath, selectedNodes);
}
menu.ShowAsContext();
}
public string GetSizeString(BuildAsset asset)
{
if (asset.Size == 0)
return "--";
return EditorUtility.FormatBytes(asset.Size);
}
private void CopyAddressPath(object context)
{
if (context is List<int> selectedNodes && selectedNodes.Count > 0)
{
TreeViewItem item = FindItem(selectedNodes[0], rootItem);
if (item is AssetTreeViewItem assetTreeViewItem)
{
EditUtil.CopyToClipBoard(assetTreeViewItem.Asset.Address);
Debug.Log($"copy success{assetTreeViewItem.Asset.Address}");
}
}
}
private void CopyPath(object context)
{
if (context is List<int> selectedNodes && selectedNodes.Count > 0)
{
TreeViewItem item = FindItem(selectedNodes[0], rootItem);
if (item is AssetTreeViewItem assetTreeViewItem)
{
EditUtil.CopyToClipBoard(assetTreeViewItem.Asset.Path);
Debug.Log($"copy success{assetTreeViewItem.Asset.Path}");
}
}
}
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 3b65c85668d04d64aca7657c2305fd32
timeCreated: 1679386505

View File

@@ -0,0 +1,168 @@
using System.Collections.Generic;
using UnityEditor;
using UnityEngine;
namespace NBC.Asset.Editor
{
public class GroupInfoGUI
{
private bool _groupBaseInfoFold = true;
private bool _groupCollectorsInfoFold = true;
Vector2 _collectorsScrollPos;
private CollectorWindow _window;
private LabelGUI _labelGUI;
public GroupInfoGUI(CollectorWindow window)
{
_window = window;
}
public void OnGUI(Rect rect)
{
if (_window == null) return;
GUILayout.BeginArea(rect);
if (_window.SelectGroupConfig == null)
{
EditorGUILayout.Space();
EditorGUILayout.LabelField(Language.NoSelectGroup);
GUILayout.EndArea();
return;
}
DrawInfo();
EditorGUILayout.Space();
EditorGUILayout.Space();
DrawCollectors();
GUILayout.EndArea();
}
void DrawInfo()
{
GUI.color = new Color(0, 0, 0, 0.2f);
GUILayout.BeginHorizontal(Styles.headerBoxStyle);
GUI.color = Color.white;
GUILayout.Label(
$"<b><size=18>{(_groupBaseInfoFold ? "" : "")} 【{_window.SelectGroupConfig.Name}】 基础信息</size></b>");
GUILayout.EndHorizontal();
var lastRect = GUILayoutUtility.GetLastRect();
if (Event.current.type == EventType.MouseDown && lastRect.Contains(Event.current.mousePosition))
{
_groupBaseInfoFold = !_groupBaseInfoFold;
Event.current.Use();
}
if (!_groupBaseInfoFold) return;
EditorGUILayout.Space();
if (GUITools.EnumGUILayout(Language.GroupBundleMode, _window.SelectGroupConfig, "BundleMode"))
{
_window.UpdateAssets();
}
if (GUITools.EnumGUILayout(Language.GroupAddressMode, _window.SelectGroupConfig, "AddressMode"))
{
_window.UpdateAssets();
}
var newFilter =
(FilterEnum)EditorGUILayout.EnumPopup(Language.Filter, _window.SelectGroupConfig.FilterEnum);
if (newFilter != _window.SelectGroupConfig.FilterEnum)
{
_window.SelectGroupConfig.FilterEnum = newFilter;
_window.UpdateAssets();
}
if (_window.SelectGroupConfig.FilterEnum == FilterEnum.Custom)
{
var newField =
EditorGUILayout.TextField(Language.FilterCustom, _window.SelectGroupConfig.Filter);
if (newField != _window.SelectGroupConfig.Filter)
{
_window.SelectGroupConfig.Filter = newField;
_window.UpdateAssets();
}
}
DrawLabels();
}
void DrawLabels()
{
if (_labelGUI == null)
{
_labelGUI = new LabelGUI();
}
_labelGUI?.OnGUI(_window.SelectGroupConfig);
// if (_labelGUI != null && _labelGUI.Lable != _window.SelectGroupConfig.Tags)
// {
// _window.SelectGroupConfig.Tags = _labelGUI.Lable;
// }
}
void DrawCollectors()
{
GUI.color = new Color(0, 0, 0, 0.2f);
GUILayout.BeginHorizontal(Styles.headerBoxStyle);
GUI.color = Color.white;
GUILayout.Label(
$"<b><size=18>{(_groupCollectorsInfoFold ? "" : "")} 【{_window.SelectGroupConfig.Name}】 收集源 ({_window.SelectGroupConfig.Collectors.Count})</size></b>");
GUI.backgroundColor = default(Color);
if (GUILayout.Button(Styles.Add, GUILayout.Width(40)))
{
_window.SelectGroupConfig.Collectors.Add(null);
}
GUI.backgroundColor = Color.white;
GUILayout.EndHorizontal();
var lastRect = GUILayoutUtility.GetLastRect();
if (Event.current.type == EventType.MouseDown && lastRect.Contains(Event.current.mousePosition))
{
_groupCollectorsInfoFold = !_groupCollectorsInfoFold;
Event.current.Use();
}
if (!_groupCollectorsInfoFold) return;
EditorGUILayout.Space();
_collectorsScrollPos = EditorGUILayout.BeginScrollView(_collectorsScrollPos);
if (_window.SelectGroupConfig.Collectors == null)
{
_window.SelectGroupConfig.Collectors = new List<Object>();
}
for (int i = 0; i < _window.SelectGroupConfig.Collectors.Count; i++)
{
GUILayout.BeginHorizontal();
GUILayout.Label(string.Format(Language.CollectorTitle, i), GUILayout.Width(60));
var collector = _window.SelectGroupConfig.Collectors[i];
var newObj = EditorGUILayout.ObjectField("", collector, typeof(Object), false);
if (newObj != collector)
{
_window.SelectGroupConfig.Collectors[i] = newObj;
_window.UpdateAssets();
}
if (GUILayout.Button("-", GUILayout.Width(20)))
{
_window.SelectGroupConfig.Collectors.RemoveAt(i);
_window.UpdateAssets();
}
GUILayout.EndHorizontal();
EditorGUILayout.Space();
}
GUILayout.EndScrollView();
}
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: bafa30ca55c64371b097be0fc2dbfaf8
timeCreated: 1679468108

View File

@@ -0,0 +1,375 @@
using System;
using System.Collections.Generic;
using System.Linq;
using UnityEditor;
using UnityEditor.IMGUI.Controls;
using UnityEngine;
namespace NBC.Asset.Editor
{
public class GroupTreeViewItem : TreeViewItem
{
private GroupConfig _group;
public GroupConfig GroupConfig => _group;
public GroupTreeViewItem(int id, GroupConfig group) : base(id, id, group.Name)
{
_group = group;
}
}
public class GroupTreeEditor : TreeView
{
public static MultiColumnHeaderState CreateDefaultMultiColumnHeaderState()
{
return new MultiColumnHeaderState(GetColumns());
}
private static MultiColumnHeaderState.Column[] GetColumns()
{
List<MultiColumnHeaderState.Column> retVal = new List<MultiColumnHeaderState.Column>();
var fist = EditUtil.GetMultiColumnHeaderColumn(Language.AssetGroupName);
retVal.Add(fist);
return retVal.ToArray();
}
/// <summary>
/// 当前选中了
/// </summary>
private bool mContextOnItem = false;
CollectorWindow m_Window;
public MultiColumnHeaderState HeaderState;
public GroupTreeEditor(TreeViewState state, CollectorWindow window, MultiColumnHeaderState header)
: base(state, new MultiColumnHeader(header))
{
showBorder = true;
HeaderState = header;
showAlternatingRowBackgrounds = false;
m_Window = window;
Refresh();
Reload();
}
private TreeViewItem mRoot = null;
protected override TreeViewItem BuildRoot()
{
mRoot = new TreeViewItem
{
id = -1,
depth = -1,
children = new List<TreeViewItem>()
};
int id = 0;
var package = m_Window.SelectPackageConfig;
if (package != null && package.Groups.Count > 0)
{
foreach (var group in package.Groups)
{
id++;
var t = new GroupTreeViewItem(id, group);
mRoot.AddChild(t);
}
}
return mRoot;
}
internal void Refresh()
{
var selection = GetSelection();
SelectionChanged(selection);
}
private void ReloadAndSelect(IList<int> hashCodes)
{
Reload();
SetSelection(hashCodes, TreeViewSelectionOptions.RevealAndFrame);
SelectionChanged(hashCodes);
}
#region
public override void OnGUI(Rect rect)
{
base.OnGUI(rect);
HeaderState.AutoWidth(rect.width);
if (Event.current.type == EventType.MouseDown && Event.current.button == 0 &&
rect.Contains(Event.current.mousePosition))
{
SetSelection(Array.Empty<int>(), TreeViewSelectionOptions.FireSelectionChanged);
}
}
/// <summary>
/// 绘制行
/// </summary>
/// <param name="args"></param>
protected override void RowGUI(RowGUIArgs args)
{
for (int i = 0; i < args.GetNumVisibleColumns(); ++i)
{
CellGUI(args.GetCellRect(i), args.item, args.GetColumn(i), ref args);
}
}
private void CellGUI(Rect cellRect, TreeViewItem item, int column, ref RowGUIArgs args)
{
if (item is GroupTreeViewItem groupTreeViewItem)
{
Color oldColor = GUI.color;
if (!groupTreeViewItem.GroupConfig.Enable)
{
GUI.color = Color.gray;
}
CenterRectUsingSingleLineHeight(ref cellRect);
if (column == 0)
{
var iconRect = new Rect(cellRect.x + 4, cellRect.y + 1, cellRect.height - 2, cellRect.height - 2);
GUI.DrawTexture(iconRect, Styles.Group, ScaleMode.ScaleToFit);
var nameRect = new Rect(cellRect.x + iconRect.xMax + 1, cellRect.y, cellRect.width - iconRect.width,
cellRect.height);
DefaultGUI.Label(nameRect, item.displayName, args.selected, args.focused);
}
}
}
#endregion
#region
/// <summary>
/// 是否能多选
/// </summary>
/// <param name="item">选中的文件</param>
/// <returns></returns>
protected override bool CanMultiSelect(TreeViewItem item)
{
return false;
}
/// <summary>
/// 能否重新命名
/// </summary>
/// <param name="item"></param>
/// <returns></returns>
protected override bool CanRename(TreeViewItem item)
{
return item.displayName.Length > 0;
}
protected override Rect GetRenameRect(Rect rowRect, int row, TreeViewItem item)
{
return rowRect;
}
protected override float GetCustomRowHeight(int row, TreeViewItem item)
{
return 30;
}
#endregion
#region
/// <summary>
/// 更改名称完成
/// </summary>
/// <param name="args"></param>
protected override void RenameEnded(RenameEndedArgs args)
{
if (!string.IsNullOrEmpty(args.newName) && args.newName != args.originalName)
{
if (NameIsOnly(args.newName))
{
var group = m_Window.SelectPackageConfig.Groups[args.itemID - 1];
if (group.Name == args.originalName)
{
group.Name = args.newName;
}
Reload();
}
else
{
Debug.LogError(Language.RepetitiveName);
}
}
else
{
args.acceptedRename = false;
}
}
protected override void SelectionChanged(IList<int> selectedIds)
{
var selectedBundles = new List<string>();
foreach (var id in selectedIds)
{
var item = FindItem(id, rootItem);
if (item != null)
selectedBundles.Add(item.displayName);
}
m_Window.UpdateSelectedGroup(selectedBundles.Count > 0 ? selectedBundles[0] : string.Empty);
}
#endregion
#region
/// <summary>
/// 点击的时候
/// </summary>
protected override void ContextClicked()
{
if (HasSelection())
{
mContextOnItem = false;
return;
}
GenericMenu menu = new GenericMenu();
menu.AddItem(new GUIContent(Language.AddGroup), false, CreateResGroup, null);
menu.ShowAsContext();
}
protected override void ContextClickedItem(int id)
{
if (mContextOnItem)
{
mContextOnItem = false;
return;
}
mContextOnItem = true;
List<int> selectedNodes = new List<int>();
foreach (var nodeID in GetSelection())
{
selectedNodes.Add(nodeID);
}
GenericMenu menu = new GenericMenu();
if (selectedNodes.Count == 1)
{
try
{
var index = selectedNodes[0] - 1;
var package = m_Window.SelectPackageConfig.Groups[index];
menu.AddItem(new GUIContent(package.Enable ? Language.Disable : Language.Enable), false,
ChangeEnable,
selectedNodes);
}
catch (Exception e)
{
Debug.LogError(e);
}
menu.AddItem(new GUIContent(Language.ReName), false, RenameGroupName, selectedNodes);
menu.AddItem(new GUIContent(Language.Del), false, DeleteGroups, selectedNodes);
}
menu.ShowAsContext();
}
protected override void KeyEvent()
{
if (Event.current.keyCode == KeyCode.Delete && GetSelection().Count > 0)
{
var list = GetSelection();
DeleteGroups(list.ToList());
}
}
void ChangeEnable(object b)
{
if (b is List<int> selectedNodes)
{
var groups = m_Window.SelectPackageConfig.Groups;
foreach (var id in selectedNodes)
{
var pack = groups[id - 1];
pack.Enable = !pack.Enable;
}
}
}
void CreateResGroup(object context)
{
var group = new GroupConfig
{
Name = GetOnlyName()
};
m_Window.SelectPackageConfig.Groups.Add(group);
var id = m_Window.SelectPackageConfig.Groups.Count;
ReloadAndSelect(new List<int>() { id });
}
void DeleteGroups(object b)
{
if (b is List<int> selectedNodes)
{
foreach (var i in selectedNodes)
{
var index = i - 1;
m_Window.SelectPackageConfig.Groups.RemoveAt(index);
}
Reload();
m_Window.UpdateSelectedGroup(string.Empty);
}
}
void RenameGroupName(object context)
{
if (context is List<int> selectedNodes && selectedNodes.Count > 0)
{
TreeViewItem item = FindItem(selectedNodes[0], rootItem);
BeginRename(item, 0.25f);
}
}
#endregion
#region
bool NameIsOnly(string name)
{
foreach (var group in m_Window.SelectPackageConfig.Groups)
{
if (group.Name == name)
{
return false;
}
}
return true;
}
string GetOnlyName()
{
var index = m_Window.SelectPackageConfig.Groups.Count;
for (int i = 0; i < 10; i++)
{
var name = $"group{index + i}";
if (NameIsOnly(name))
{
return name;
}
}
return $"group{DateTimeOffset.Now.ToUnixTimeSeconds()}";
}
#endregion
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 2ac8a0e5654140f2a53b3c6ad600f51e
timeCreated: 1679368950

View File

@@ -0,0 +1,399 @@
using System;
using System.Collections.Generic;
using System.Linq;
using UnityEditor;
using UnityEditor.IMGUI.Controls;
using UnityEngine;
namespace NBC.Asset.Editor
{
public class PackageTreeViewItem : TreeViewItem
{
private PackageConfig _package;
public PackageConfig Package => _package;
public PackageTreeViewItem(int id, PackageConfig package) : base(id, id, package.Name)
{
_package = package;
}
}
public class PackageTreeEditor : TreeView
{
public static MultiColumnHeaderState CreateDefaultMultiColumnHeaderState()
{
return new MultiColumnHeaderState(GetColumns());
}
private static MultiColumnHeaderState.Column[] GetColumns()
{
List<MultiColumnHeaderState.Column> retVal = new List<MultiColumnHeaderState.Column>();
var fist = EditUtil.GetMultiColumnHeaderColumn(Language.AssetPackageName);
retVal.Add(fist);
return retVal.ToArray();
}
/// <summary>
/// 当前选中了
/// </summary>
private bool mContextOnItem = false;
CollectorWindow m_Window;
public MultiColumnHeaderState HeaderState;
public PackageTreeEditor(TreeViewState state, CollectorWindow window, MultiColumnHeaderState header)
: base(state, new MultiColumnHeader(header))
{
showBorder = true;
HeaderState = header;
showAlternatingRowBackgrounds = false;
m_Window = window;
Refresh();
Reload();
}
private TreeViewItem mRoot = null;
protected override TreeViewItem BuildRoot()
{
mRoot = new TreeViewItem
{
id = -1,
depth = -1,
children = new List<TreeViewItem>()
};
int id = 0;
var packages = CollectorSetting.Instance.Packages;
foreach (var package in packages)
{
id++;
var t = new PackageTreeViewItem(id, package);
mRoot.AddChild(t);
}
return mRoot;
}
internal void Refresh()
{
var selection = GetSelection();
SelectionChanged(selection);
}
private void ReloadAndSelect(IList<int> hashCodes)
{
Reload();
SetSelection(hashCodes, TreeViewSelectionOptions.RevealAndFrame);
SelectionChanged(hashCodes);
}
#region
public override void OnGUI(Rect rect)
{
base.OnGUI(rect);
HeaderState.AutoWidth(rect.width);
if (Event.current.type == EventType.MouseDown && Event.current.button == 0 &&
rect.Contains(Event.current.mousePosition))
{
SetSelection(Array.Empty<int>(), TreeViewSelectionOptions.FireSelectionChanged);
}
}
/// <summary>
/// 绘制行
/// </summary>
/// <param name="args"></param>
protected override void RowGUI(RowGUIArgs args)
{
for (int i = 0; i < args.GetNumVisibleColumns(); ++i)
{
CellGUI(args.GetCellRect(i), args.item, args.GetColumn(i), ref args);
}
}
private void CellGUI(Rect cellRect, TreeViewItem item, int column, ref RowGUIArgs args)
{
if (item is PackageTreeViewItem packageTreeViewItem)
{
Color oldColor = GUI.color;
if (!packageTreeViewItem.Package.Enable)
{
GUI.color = Color.gray;
}
CenterRectUsingSingleLineHeight(ref cellRect);
if (column == 0)
{
var iconRect = new Rect(cellRect.x + 4, cellRect.y + 1, cellRect.height - 2, cellRect.height - 2);
var icon = packageTreeViewItem.Package.Default ? Styles.Package : Styles.PackageLow;
GUI.DrawTexture(iconRect, icon, ScaleMode.ScaleToFit);
var nameRect = new Rect(cellRect.x + iconRect.xMax + 1, cellRect.y, cellRect.width - iconRect.width,
cellRect.height);
if (packageTreeViewItem.Package.Default)
{
DefaultGUI.BoldLabel(nameRect, item.displayName, args.selected, args.focused);
}
else
{
DefaultGUI.Label(nameRect, item.displayName, args.selected, args.focused);
}
}
GUI.color = oldColor;
}
}
#endregion
#region
/// <summary>
/// 是否能多选
/// </summary>
/// <param name="item">选中的文件</param>
/// <returns></returns>
protected override bool CanMultiSelect(TreeViewItem item)
{
return false;
}
/// <summary>
/// 能否重新命名
/// </summary>
/// <param name="item"></param>
/// <returns></returns>
protected override bool CanRename(TreeViewItem item)
{
return item.displayName.Length > 0;
}
protected override Rect GetRenameRect(Rect rowRect, int row, TreeViewItem item)
{
return rowRect;
}
protected override float GetCustomRowHeight(int row, TreeViewItem item)
{
return 30;
}
#endregion
#region
/// <summary>
/// 更改名称完成
/// </summary>
/// <param name="args"></param>
protected override void RenameEnded(RenameEndedArgs args)
{
if (!string.IsNullOrEmpty(args.newName) && args.newName != args.originalName)
{
if (NameIsOnly(args.newName))
{
var packages = CollectorSetting.Instance.Packages;
var package = packages[args.itemID - 1];
if (package.Name == args.originalName)
{
package.Name = args.newName;
}
Reload();
}
else
{
Debug.LogError(Language.RepetitiveName);
}
}
else
{
args.acceptedRename = false;
}
}
protected override void SelectionChanged(IList<int> selectedIds)
{
var selectedBundles = new List<string>();
foreach (var id in selectedIds)
{
var item = FindItem(id, rootItem);
if (item != null)
selectedBundles.Add(item.displayName);
}
m_Window.UpdateSelectedPackage(selectedBundles.Count > 0 ? selectedBundles[0] : string.Empty);
}
#endregion
#region
/// <summary>
/// 点击的时候
/// </summary>
protected override void ContextClicked()
{
if (HasSelection())
{
mContextOnItem = false;
return;
}
GenericMenu menu = new GenericMenu();
menu.AddItem(new GUIContent(Language.AddPackage), false, CreateResGroup, null);
menu.ShowAsContext();
}
protected override void ContextClickedItem(int id)
{
if (mContextOnItem)
{
mContextOnItem = false;
return;
}
mContextOnItem = true;
List<int> selectedNodes = new List<int>();
foreach (var nodeID in GetSelection())
{
selectedNodes.Add(nodeID);
}
GenericMenu menu = new GenericMenu();
if (selectedNodes.Count == 1)
{
menu.AddItem(new GUIContent(Language.AddGroup), false, CreateResGroup, null);
try
{
var index = selectedNodes[0] - 1;
var package = CollectorSetting.Instance.Packages[index];
menu.AddItem(new GUIContent(package.Enable ? Language.Disable : Language.Enable), false,
ChangeEnable,
selectedNodes);
var str = package.Default ? Language.DisableDefPackage : Language.EnableDefPackage;
menu.AddItem(new GUIContent(str), false, ChangeDefPackage, selectedNodes);
}
catch (Exception e)
{
Debug.LogError(e);
}
menu.AddItem(new GUIContent(Language.ReName), false, RenameGroupName, selectedNodes);
menu.AddItem(new GUIContent(Language.Del), false, DeleteGroups, selectedNodes);
}
menu.ShowAsContext();
}
protected override void KeyEvent()
{
if (Event.current.keyCode == KeyCode.Delete && GetSelection().Count > 0)
{
var list = GetSelection();
DeleteGroups(list.ToList());
}
}
void ChangeDefPackage(object b)
{
if (b is List<int> selectedNodes)
{
var packages = CollectorSetting.Instance.Packages;
foreach (var id in selectedNodes)
{
var pack = packages[id - 1];
pack.Default = !pack.Default;
}
}
}
void ChangeEnable(object b)
{
if (b is List<int> selectedNodes)
{
var packages = CollectorSetting.Instance.Packages;
foreach (var id in selectedNodes)
{
var pack = packages[id - 1];
pack.Enable = !pack.Enable;
}
}
}
void CreateResGroup(object context)
{
var package = new PackageConfig()
{
Name = GetOnlyName()
};
CollectorSetting.Instance.Packages.Add(package);
var id = CollectorSetting.Instance.Packages.Count;
ReloadAndSelect(new List<int>() { id });
}
void DeleteGroups(object b)
{
if (b is List<int> selectedNodes)
{
foreach (var i in selectedNodes)
{
var index = i - 1;
CollectorSetting.Instance.Packages.RemoveAt(index);
}
ReloadAndSelect(new List<int>());
m_Window.UpdateSelectedPackage(string.Empty);
}
}
void RenameGroupName(object context)
{
if (context is List<int> selectedNodes && selectedNodes.Count > 0)
{
TreeViewItem item = FindItem(selectedNodes[0], rootItem);
BeginRename(item, 0.25f);
}
}
#endregion
#region
bool NameIsOnly(string name)
{
var packages = CollectorSetting.Instance.Packages;
foreach (var package in packages)
{
if (package.Name == name)
{
return false;
}
}
return true;
}
string GetOnlyName()
{
var index = CollectorSetting.Instance.Packages.Count;
for (int i = 0; i < 10; i++)
{
var name = $"package{index + i}";
if (NameIsOnly(name))
{
return name;
}
}
return $"package{DateTimeOffset.Now.ToUnixTimeSeconds()}";
}
#endregion
}
}

View File

@@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: d89d8be5d8fb487aa4f5c21469255890
timeCreated: 1679369408