修复BUG

This commit is contained in:
MuHua-123
2025-06-17 16:18:54 +08:00
parent 5e7fa2ef57
commit e14ba6d45f
71 changed files with 6471 additions and 214 deletions
@@ -8,7 +8,7 @@ namespace MuHua {
/// <summary>
/// UI项
/// </summary>
public abstract class ModuleUIItem<Data> : ModuleUIPanel {
public abstract class ModuleUIItem<Data> : ModuleUIPanel, IDisposable {
/// <summary> 选择事件 </summary>
public static event Action<Data> OnSelect;
/// <summary> 触发事件 </summary>
@@ -34,6 +34,6 @@ namespace MuHua {
/// <summary> 选中状态 </summary>
public virtual void SelectState() { }
/// <summary> 释放 </summary>
public virtual void Release() => OnSelect -= UIItem_OnSelect;
public virtual void Dispose() => OnSelect -= UIItem_OnSelect;
}
}
@@ -8,7 +8,7 @@ namespace MuHua {
/// <summary>
/// UI项容器
/// </summary>
public class ModuleUIItems<TItem, TData> : ModuleUIPanel where TItem : ModuleUIItem<TData> {
public class ModuleUIItems<TItem, TData> : ModuleUIPanel, IDisposable where TItem : ModuleUIItem<TData> {
public readonly VisualTreeAsset templateAsset;// 模板资源
public readonly Func<TData, VisualElement, TItem> generate;// 生成UI项的函数
@@ -22,14 +22,14 @@ namespace MuHua {
this.generate = generate;
}
/// <summary> 释放资源 </summary>
public void Release() {
public void Dispose() {
element.Clear();
uiItems.ForEach(obj => obj.Release());
uiItems.ForEach(obj => obj.Dispose());
uiItems = new List<TItem>();
}
/// <summary> 创建UI项 </summary>
public void Create(List<TData> datas) {
Release();
Dispose();
datas.ForEach(Create);
}
/// <summary> 创建UI项 </summary>
@@ -1,3 +1,4 @@
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
@@ -6,6 +7,7 @@ namespace MuHua {
/// <summary>
/// 方向
/// </summary>
[Obsolete("使用类内置的 UIDirection")]
public enum UIDirection {
FromLeftToRight = 0,
FromRightToLeft = 1,
@@ -8,7 +8,7 @@ namespace MuHua {
/// <summary>
/// 下拉框
/// </summary>
public class UIDropdown<T> : ModuleUIPanel {
public class UIDropdown<T> : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
internal readonly VisualElement canvas;
/// <summary> 下拉框容器 </summary>
@@ -50,16 +50,18 @@ namespace MuHua {
DropdownScrollView.EnableInClassList("dropdown-hide", false);
DropdownContainer.Add(DropdownScrollView);
scrollView = new UIScrollView(DropdownScrollView, DropdownContainer, UIDirection.FromTopToBottom);
scrollView = new UIScrollView(DropdownScrollView, DropdownContainer);
DropdownItems = new ModuleUIItems<UIDropdownItem, T>(scrollView.Container, TemplateAsset,
(data, element) => new UIDropdownItem(data, element, this));
Input.RegisterCallback<ClickEvent>(evt => OpenDropdown());
DropdownContainer.RegisterCallback<PointerDownEvent>(evt => CloseDropdown());
}
public virtual void Release() {
public virtual void Dispose() {
canvas.Remove(DropdownContainer);
DropdownItems.Release();
DropdownItems.Dispose();
Input.UnregisterCallback<ClickEvent>(evt => OpenDropdown());
DropdownContainer.UnregisterCallback<PointerDownEvent>(evt => CloseDropdown());
}
public virtual void Update() {
scrollView.Update();
@@ -1,6 +1,7 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;
using UnityEngine.UIElements;
@@ -8,15 +9,13 @@ namespace MuHua {
/// <summary>
/// 滚动视图
/// </summary>
public class UIScrollView : ModuleUIPanel {
public class UIScrollView : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
/// <summary> 元素方向 </summary>
public readonly UIDirection direction;
/// <summary> 水平滑动方向 </summary>
public readonly UIDirection sh;
/// <summary> 垂直滑动方向 </summary>
public readonly UIDirection sv;
/// <summary> 水平滑块 </summary>
public readonly UIScrollerH horizontal;
/// <summary> 垂直滑块 </summary>
public readonly UIScrollerV vertical;
/// <summary> 值改变时 </summary>
public event Action<Vector2> ValueChanged;
@@ -25,42 +24,23 @@ namespace MuHua {
public Vector3 originalPosition;
public Vector3 pointerPosition;
public readonly UIScroller horizontal;
public readonly UIScroller vertical;
public readonly VisualElement Viewport;
public readonly VisualElement Container;
public readonly VisualElement ScrollerHorizontal;
public readonly VisualElement ScrollerVertical;
public VisualElement Viewport => Q<VisualElement>("Viewport");
public VisualElement Container => Q<VisualElement>("Container");
public VisualElement ScrollerHorizontal => Q<VisualElement>("ScrollerHorizontal");
public VisualElement ScrollerVertical => Q<VisualElement>("ScrollerVertical");
public UIScrollView(VisualElement element, VisualElement canvas,
UIDirection direction = UIDirection.HorizontalAndVertical,
UIDirection sh = UIDirection.FromLeftToRight,
UIDirection sv = UIDirection.FromTopToBottom) : base(element) {
public UIScrollView(VisualElement element, VisualElement canvas) : base(element) {
this.canvas = canvas;
this.direction = direction;
this.sh = sh;
this.sv = sv;
Viewport = element.Children().FirstOrDefault(e => e.name == "Viewport");
Container = Viewport.Children().FirstOrDefault(e => e.name == "Container");
ScrollerHorizontal = element.Children().FirstOrDefault(e => e.name == "ScrollerHorizontal");
ScrollerVertical = element.Children().FirstOrDefault(e => e.name == "ScrollerVertical");
element.generateVisualContent += ElementGenerateVisualContent;
if (sh == UIDirection.FromLeftToRight) {
horizontal = new UIScroller(ScrollerHorizontal, canvas, sh);
Viewport.style.flexDirection = FlexDirection.Row;
}
if (sh == UIDirection.FromRightToLeft) {
horizontal = new UIScroller(ScrollerHorizontal, canvas, sh);
Viewport.style.flexDirection = FlexDirection.RowReverse;
}
if (sv == UIDirection.FromTopToBottom) {
vertical = new UIScroller(ScrollerVertical, canvas, sv);
Viewport.style.flexDirection = FlexDirection.Column;
}
if (sv == UIDirection.FromBottomToTop) {
vertical = new UIScroller(ScrollerVertical, canvas, sv);
Viewport.style.flexDirection = FlexDirection.ColumnReverse;
}
horizontal = new UIScrollerH(ScrollerHorizontal, canvas, UIScrollerH.UIDirection.FromLeftToRight);
vertical = new UIScrollerV(ScrollerVertical, canvas, UIScrollerV.UIDirection.FromTopToBottom);
// 设置事件
horizontal.ValueChanged += (x) => { UpdateValue(new Vector2(x, value.y)); };
@@ -68,74 +48,86 @@ namespace MuHua {
Viewport.RegisterCallback<WheelEvent>(ViewportWheel);
Viewport.RegisterCallback<PointerDownEvent>(DraggerDown);
Viewport.RegisterCallback<MouseCaptureEvent>((evt) => isDrag = false);
Viewport.RegisterCallback<MouseCaptureEvent>(DraggerUpOrLeave);
// 释放
canvas.RegisterCallback<PointerUpEvent>((evt) => isDrag = false);
canvas.RegisterCallback<PointerLeaveEvent>((evt) => isDrag = false);
canvas.RegisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.RegisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 解绑事件,防止内存泄漏 </summary>
public virtual void Dispose() {
Viewport.UnregisterCallback<WheelEvent>(ViewportWheel);
Viewport.UnregisterCallback<PointerDownEvent>(DraggerDown);
Viewport.UnregisterCallback<MouseCaptureEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
element.generateVisualContent -= ElementGenerateVisualContent;
}
/// <summary> 视图原始更新 </summary>
private void ElementGenerateVisualContent(MeshGenerationContext context) {
float width = Mathf.Clamp01(Viewport.resolvedStyle.width / Container.resolvedStyle.width);
float height = Mathf.Clamp01(Viewport.resolvedStyle.height / Container.resolvedStyle.height);
horizontal.Dragger.style.width = Length.Percent(width * 100);
float height = Mathf.Clamp01(Viewport.resolvedStyle.height / Container.resolvedStyle.height);
vertical.Dragger.style.height = Length.Percent(height * 100);
}
/// <summary> 视图滚轮滑动 </summary>
private void ViewportWheel(WheelEvent evt) {
float wheel = Mathf.Clamp(evt.delta.y, -1, 1);
Vector2 offset = new Vector2(0, wheel);
if (direction == UIDirection.Horizontal) { offset = new Vector2(wheel, 0); }
UpdateValue(new Vector2(value.x, value.y) - offset);
float x = Mathf.Clamp(evt.delta.x, -1, 1);
float y = Mathf.Clamp(evt.delta.y, -1, 1);
UpdateValue(new Vector2(value.x - x, value.y - y));
}
/// <summary> 拖拽按下 </summary>
private void DraggerDown(PointerDownEvent evt) {
isDrag = true;
originalPosition = Container.transform.position;
Vector3 mousePosition = UITool.GetMousePosition();
pointerPosition = new Vector3(mousePosition.x, Screen.height - mousePosition.y);
}
/// <summary> 拖拽滑动 </summary>
private void Dragger() {
Vector3 mousePosition = UITool.GetMousePosition();
Vector3 differ = new Vector3(mousePosition.x, Screen.height - mousePosition.y) - pointerPosition;
Vector3 offset = differ + originalPosition;
float maxWidth = Viewport.resolvedStyle.width - Container.resolvedStyle.width;
float x = offset.x / maxWidth;
float maxHeight = Viewport.resolvedStyle.height - Container.resolvedStyle.height;
float y = offset.y / maxHeight;
UpdateValue(new Vector2(x, y));
}
/// <summary> 滑动弹性 </summary>
private void SlidingElasticity() {
Vector2 original = value;
float maxX = Viewport.resolvedStyle.width < Container.resolvedStyle.width ? 1 : 0;
if (value.x < 0) { value.x = Mathf.Lerp(value.x, 0, Time.deltaTime * 10); }
if (value.x > maxX) { value.x = Mathf.Lerp(value.x, maxX, Time.deltaTime * 10); }
float maxY = Viewport.resolvedStyle.height < Container.resolvedStyle.height ? 1 : 0;
if (value.y < 0) { value.y = Mathf.Lerp(value.y, 0, Time.deltaTime * 10); }
if (value.y > maxY) { value.y = Mathf.Lerp(value.y, maxY, Time.deltaTime * 10); }
if (original != value) { UpdateValue(value); }
}
/// <summary> 鼠标松开或离开 </summary>
private void DraggerUpOrLeave(EventBase evt) {
isDrag = false;
}
/// <summary> 更新状态 </summary>
public virtual void Update() {
horizontal.Update();
vertical.Update();
Vector2 original = value;
float maxX = Viewport.resolvedStyle.width < Container.resolvedStyle.width ? 1 : 0;
float maxY = Viewport.resolvedStyle.height < Container.resolvedStyle.height ? 1 : 0;
if (value.x < 0) { value.x = Mathf.Lerp(value.x, 0, Time.deltaTime * 10); }
if (value.x > maxX) { value.x = Mathf.Lerp(value.x, maxX, Time.deltaTime * 10); }
if (value.y < 0) { value.y = Mathf.Lerp(value.y, 0, Time.deltaTime * 10); }
if (value.y > maxY) { value.y = Mathf.Lerp(value.y, maxY, Time.deltaTime * 10); }
if (original != value) { UpdateValue(value); }
if (!isDrag) { return; }
Vector3 mousePosition = UITool.GetMousePosition();
Vector3 differ = new Vector3(mousePosition.x, Screen.height - mousePosition.y) - pointerPosition;
Vector3 offset = differ + originalPosition;
float maxWidth = Viewport.resolvedStyle.width - Container.resolvedStyle.width;
float maxHeight = Viewport.resolvedStyle.height - Container.resolvedStyle.height;
float x = offset.x / maxWidth;
float y = offset.y / maxHeight;
x *= sh == UIDirection.FromLeftToRight ? 1 : -1;
y *= sv == UIDirection.FromTopToBottom ? 1 : -1;
UpdateValue(new Vector2(x, y));
SlidingElasticity();
if (isDrag) { Dragger(); }
}
/// <summary> 更新值(0-1) </summary>
public void UpdateValue(Vector2 value, bool send = true) {
if (direction == UIDirection.Horizontal) { value.y = 0; }
if (direction == UIDirection.Vertical) { value.x = 0; }
this.value = value;
if (send) { ValueChanged?.Invoke(value); }
float maxWidth = Viewport.resolvedStyle.width - Container.resolvedStyle.width;
float x = maxWidth * value.x;
float maxHeight = Viewport.resolvedStyle.height - Container.resolvedStyle.height;
float xPos = maxWidth * value.x;
float yPos = maxHeight * value.y;
xPos *= sh == UIDirection.FromLeftToRight ? 1 : -1;
yPos *= sv == UIDirection.FromTopToBottom ? 1 : -1;
Container.transform.position = new Vector3(xPos, yPos);
float y = maxHeight * value.y;
Container.transform.position = new Vector3(x, y);
if (horizontal.value != value.x) { horizontal.UpdateValue(value.x, false); }
if (vertical.value != value.y) { vertical.UpdateValue(value.y, false); }
@@ -0,0 +1,130 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;
using UnityEngine.UIElements;
namespace MuHua {
/// <summary>
/// 滚动视图 - 水平
/// </summary>
public class UIScrollViewH : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
/// <summary> 元素方向 </summary>
public readonly UIDirection direction;
/// <summary> 水平滑块 </summary>
public readonly UIScrollerH horizontal;
/// <summary> 值改变时 </summary>
public event Action<float> ValueChanged;
/// <summary>
/// 方向
/// </summary>
public enum UIDirection {
FromLeftToRight = 0,
FromRightToLeft = 1,
}
public float value;
public bool isDrag;
public Vector3 originalPosition;
public Vector3 pointerPosition;
public readonly VisualElement Viewport;
public readonly VisualElement Container;
public readonly VisualElement ScrollerHorizontal;
public UIScrollViewH(VisualElement element, VisualElement canvas, UIDirection direction = UIDirection.FromLeftToRight) : base(element) {
this.canvas = canvas;
this.direction = direction;
Viewport = element.Children().FirstOrDefault(e => e.name == "Viewport");
Container = Viewport.Children().FirstOrDefault(e => e.name == "Container");
ScrollerHorizontal = element.Children().FirstOrDefault(e => e.name == "ScrollerHorizontal");
if (direction == UIDirection.FromLeftToRight) { horizontal = new UIScrollerH(ScrollerHorizontal, canvas, UIScrollerH.UIDirection.FromLeftToRight); }
if (direction == UIDirection.FromRightToLeft) { horizontal = new UIScrollerH(ScrollerHorizontal, canvas, UIScrollerH.UIDirection.FromRightToLeft); }
// 设置事件
horizontal.ValueChanged += (y) => { UpdateValue(y); };
Viewport.RegisterCallback<WheelEvent>(ViewportWheel);
Viewport.RegisterCallback<PointerDownEvent>(DraggerDown);
Viewport.RegisterCallback<MouseCaptureEvent>(DraggerUpOrLeave);
Viewport.style.flexDirection = direction == UIDirection.FromLeftToRight ? FlexDirection.Row : FlexDirection.RowReverse;
// 释放
canvas.RegisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.RegisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
// 视图原始更新
element.generateVisualContent += ElementGenerateVisualContent;
}
/// <summary> 解绑事件,防止内存泄漏 </summary>
public virtual void Dispose() {
Viewport.UnregisterCallback<WheelEvent>(ViewportWheel);
Viewport.UnregisterCallback<PointerDownEvent>(DraggerDown);
Viewport.UnregisterCallback<MouseCaptureEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
element.generateVisualContent -= ElementGenerateVisualContent;
}
/// <summary> 原始更新 </summary>
private void ElementGenerateVisualContent(MeshGenerationContext context) {
float width = Mathf.Clamp01(Viewport.resolvedStyle.width / Container.resolvedStyle.width);
horizontal.Dragger.style.width = Length.Percent(width * 100);
}
/// <summary> 滚轮滑动 </summary>
private void ViewportWheel(WheelEvent evt) {
float wheel = Mathf.Clamp(evt.delta.y, -1, 1);
UpdateValue(value - wheel);
}
/// <summary> 拖拽按下 </summary>
private void DraggerDown(PointerDownEvent evt) {
isDrag = true;
originalPosition = Container.transform.position;
Vector3 mousePosition = UITool.GetMousePosition();
pointerPosition = new Vector3(mousePosition.x, Screen.height - mousePosition.y);
}
/// <summary> 拖拽滑动 </summary>
private void Dragger() {
Vector3 mousePosition = UITool.GetMousePosition();
Vector3 differ = new Vector3(mousePosition.x, Screen.height - mousePosition.y) - pointerPosition;
Vector3 offset = differ + originalPosition;
float maxWidth = Viewport.resolvedStyle.width - Container.resolvedStyle.width;
float x = offset.x / maxWidth;
x *= direction == UIDirection.FromLeftToRight ? 1 : -1;
UpdateValue(x);
}
/// <summary> 滑动弹性 </summary>
private void SlidingElasticity() {
float original = value;
float max = Viewport.resolvedStyle.width < Container.resolvedStyle.width ? 1 : 0;
if (value < 0) { value = Mathf.Lerp(value, 0, Time.deltaTime * 10); }
if (value > max) { value = Mathf.Lerp(value, max, Time.deltaTime * 10); }
if (original != value) { UpdateValue(value); }
}
/// <summary> 鼠标松开或离开 </summary>
private void DraggerUpOrLeave(EventBase evt) {
isDrag = false;
}
/// <summary> 更新状态 </summary>
public void Update() {
horizontal.Update();
SlidingElasticity();
if (isDrag) { Dragger(); }
}
/// <summary> 更新值(0-1) </summary>
public void UpdateValue(float value, bool send = true) {
this.value = value;
if (send) { ValueChanged?.Invoke(value); }
float maxWidth = Viewport.resolvedStyle.width - Container.resolvedStyle.width;
float position = maxWidth * value;
position *= direction == UIDirection.FromLeftToRight ? 1 : -1;
Container.transform.position = new Vector3(position, 0);
if (horizontal.value != value) { horizontal.UpdateValue(value, false); }
}
}
}
@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 8b2173ac895d7f74aa8bf9332f7abbbc
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:
@@ -1,6 +1,7 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;
using UnityEngine.UIElements;
@@ -8,13 +9,13 @@ namespace MuHua {
/// <summary>
/// 滚动视图 - 垂直
/// </summary>
public class UIScrollViewV : ModuleUIPanel {
public class UIScrollViewV : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
/// <summary> 元素方向 </summary>
public readonly UIDirection direction;
/// <summary> 垂直滑块 </summary>
public readonly UIScroller vertical;
public readonly UIScrollerV vertical;
/// <summary> 值改变时 </summary>
public event Action<float> ValueChanged;
@@ -31,35 +32,43 @@ namespace MuHua {
public Vector3 originalPosition;
public Vector3 pointerPosition;
public VisualElement Viewport => Q<VisualElement>("Viewport");
public VisualElement Container => Q<VisualElement>("Container");
public VisualElement ScrollerVertical => Q<VisualElement>("ScrollerVertical");
public readonly VisualElement Viewport;
public readonly VisualElement Container;
public readonly VisualElement ScrollerVertical;
public UIScrollViewV(VisualElement element, VisualElement canvas, UIDirection direction) : base(element) {
public UIScrollViewV(VisualElement element, VisualElement canvas, UIDirection direction = UIDirection.FromTopToBottom) : base(element) {
this.canvas = canvas;
this.direction = direction;
if (direction == UIDirection.FromTopToBottom) {
// vertical = new UIScroller(ScrollerVertical, canvas, direction);
Viewport.style.flexDirection = FlexDirection.Column;
}
if (direction == UIDirection.FromBottomToTop) {
// vertical = new UIScroller(ScrollerVertical, canvas, direction);
Viewport.style.flexDirection = FlexDirection.ColumnReverse;
}
Viewport = element.Children().FirstOrDefault(e => e.name == "Viewport");
Container = Viewport.Children().FirstOrDefault(e => e.name == "Container");
ScrollerVertical = element.Children().FirstOrDefault(e => e.name == "ScrollerVertical");
if (direction == UIDirection.FromTopToBottom) { vertical = new UIScrollerV(ScrollerVertical, canvas, UIScrollerV.UIDirection.FromTopToBottom); }
if (direction == UIDirection.FromBottomToTop) { vertical = new UIScrollerV(ScrollerVertical, canvas, UIScrollerV.UIDirection.FromBottomToTop); }
// 设置事件
vertical.ValueChanged += (y) => { UpdateValue(y); };
Viewport.RegisterCallback<WheelEvent>(ViewportWheel);
Viewport.RegisterCallback<PointerDownEvent>(DraggerDown);
Viewport.RegisterCallback<MouseCaptureEvent>((evt) => isDrag = false);
Viewport.RegisterCallback<MouseCaptureEvent>(DraggerUpOrLeave);
Viewport.style.flexDirection = direction == UIDirection.FromTopToBottom ? FlexDirection.Column : FlexDirection.ColumnReverse;
// 释放
canvas.RegisterCallback<PointerUpEvent>((evt) => isDrag = false);
canvas.RegisterCallback<PointerLeaveEvent>((evt) => isDrag = false);
canvas.RegisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.RegisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
// 视图原始更新
element.generateVisualContent += ElementGenerateVisualContent;
}
/// <summary> 解绑事件,防止内存泄漏 </summary>
public virtual void Dispose() {
Viewport.UnregisterCallback<WheelEvent>(ViewportWheel);
Viewport.UnregisterCallback<PointerDownEvent>(DraggerDown);
Viewport.UnregisterCallback<MouseCaptureEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
element.generateVisualContent -= ElementGenerateVisualContent;
}
/// <summary> 原始更新 </summary>
private void ElementGenerateVisualContent(MeshGenerationContext context) {
float height = Mathf.Clamp01(Viewport.resolvedStyle.height / Container.resolvedStyle.height);
@@ -96,6 +105,10 @@ namespace MuHua {
if (value > max) { value = Mathf.Lerp(value, max, Time.deltaTime * 10); }
if (original != value) { UpdateValue(value); }
}
/// <summary> 鼠标松开或离开 </summary>
private void DraggerUpOrLeave(EventBase evt) {
isDrag = false;
}
/// <summary> 更新状态 </summary>
public virtual void Update() {
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: f32cb99a110601f4985e70f5d5e2c9d5
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -8,18 +8,18 @@ namespace MuHua {
/// <summary>
/// 滚动列表
/// </summary>
public class UIScrollList<T, Data> : UIScrollView where T : ModuleUIItem<Data> {
public class UIScrollViewList<T, Data> : UIScrollView where T : ModuleUIItem<Data> {
private ModuleUIItems<T, Data> Items;// UI项容器
public UIScrollList(VisualElement element, VisualElement canvas, VisualTreeAsset templateAsset, Func<Data, VisualElement, T> generate,
UIDirection direction = UIDirection.HorizontalAndVertical,
UIDirection sh = UIDirection.FromLeftToRight,
UIDirection sv = UIDirection.FromTopToBottom) : base(element, canvas, direction, sh, sv) {
public UIScrollViewList(VisualElement element, VisualElement canvas, VisualTreeAsset templateAsset, Func<Data, VisualElement, T> generate) : base(element, canvas) {
Items = new ModuleUIItems<T, Data>(Container, templateAsset, generate);
}
/// <summary> 释放资源 </summary>
public void Release() => Items.Release();
public override void Dispose() {
base.Dispose();
Items.Dispose();
}
/// <summary> 创建UI项 </summary>
public void Create(List<Data> datas) => Items.Create(datas);
/// <summary> 创建UI项 </summary>
@@ -0,0 +1,28 @@
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UIElements;
namespace MuHua {
/// <summary>
/// 滚动列表 - 水平
/// </summary>
public class UIScrollViewListH<T, Data> : UIScrollViewH where T : ModuleUIItem<Data> {
private ModuleUIItems<T, Data> Items;// UI项容器
public UIScrollViewListH(VisualElement element, VisualElement canvas, VisualTreeAsset templateAsset, Func<Data, VisualElement, T> generate) : base(element, canvas) {
Items = new ModuleUIItems<T, Data>(Container, templateAsset, generate);
}
/// <summary> 释放资源 </summary>
public override void Dispose() {
base.Dispose();
Items.Dispose();
}
/// <summary> 创建UI项 </summary>
public void Create(List<Data> datas) => Items.Create(datas);
/// <summary> 创建UI项 </summary>
public void Create(Data data) => Items.Create(data);
}
}
@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f01945ff69872ec4badbee195ca34658
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,27 @@
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UIElements;
namespace MuHua {
/// <summary>
/// 滚动列表 - 垂直
/// </summary>
public class UIScrollViewListV<T, Data> : UIScrollViewV where T : ModuleUIItem<Data> {
private ModuleUIItems<T, Data> Items;// UI项容器
public UIScrollViewListV(VisualElement element, VisualElement canvas, VisualTreeAsset templateAsset, Func<Data, VisualElement, T> generate) : base(element, canvas) {
Items = new ModuleUIItems<T, Data>(Container, templateAsset, generate);
}
/// <summary> 释放资源 </summary>
public override void Dispose() {
base.Dispose();
Items.Dispose();
}
/// <summary> 创建UI项 </summary>
public void Create(List<Data> datas) => Items.Create(datas);
/// <summary> 创建UI项 </summary>
public void Create(Data data) => Items.Create(data);
}
}
@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 0cb080753ee549f4eadcd17ccd688ccb
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:
@@ -8,6 +8,7 @@ namespace MuHua {
/// <summary>
/// 滚动条
/// </summary>
[Obsolete("使用 UIScrollerV 或者 UIScrollerH 替换")]
public class UIScroller : ModuleUIPanel {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
@@ -0,0 +1,96 @@
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UIElements;
namespace MuHua {
/// <summary>
/// 滚动条 - 水平
/// </summary>
public class UIScrollerH : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
/// <summary> 元素方向 </summary>
public readonly UIDirection direction;
/// <summary> 值改变时 </summary>
public event Action<float> ValueChanged;
/// <summary>
/// 方向
/// </summary>
public enum UIDirection {
FromLeftToRight = 0,
FromRightToLeft = 1,
}
public float value;
public bool isDragger;
public float originalPosition;
public float pointerPosition;
public readonly VisualElement Dragger;
public UIScrollerH(VisualElement element, VisualElement canvas, UIDirection direction = UIDirection.FromLeftToRight) : base(element) {
this.canvas = canvas;
this.direction = direction;
Dragger = Q<VisualElement>("Dragger");
element.style.flexDirection = direction == UIDirection.FromLeftToRight ? FlexDirection.Row : FlexDirection.RowReverse;
//设置事件
Dragger.RegisterCallback<PointerDownEvent>(DraggerDown);
element.RegisterCallback<PointerDownEvent>(ElementDown);
canvas.RegisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.RegisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 解绑事件,防止内存泄漏 </summary>
public void Dispose() {
Dragger.UnregisterCallback<PointerDownEvent>(DraggerDown);
element.UnregisterCallback<PointerDownEvent>(ElementDown);
canvas.UnregisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 拖拽按下 </summary>
private void DraggerDown(PointerDownEvent evt) {
isDragger = true;
originalPosition = Dragger.transform.position.x;
pointerPosition = UITool.GetMousePosition().x;
}
/// <summary> 元素按下 </summary>
private void ElementDown(PointerDownEvent evt) {
float offset = evt.localPosition.x - Dragger.resolvedStyle.width * 0.5f;
float max = element.resolvedStyle.width - Dragger.resolvedStyle.width;
float value1 = Mathf.InverseLerp(0, max, offset);
float value2 = Mathf.InverseLerp(max, 0, offset);
float value = direction == UIDirection.FromLeftToRight ? value1 : value2;
UpdateValue(value);
}
/// <summary> 鼠标松开或离开 </summary>
private void DraggerUpOrLeave(EventBase evt) {
isDragger = false;
}
/// <summary> 更新状态 </summary>
public void Update() {
if (!isDragger) { return; }
float differ = UITool.GetMousePosition().x - pointerPosition;
float offset = differ + originalPosition;
offset *= direction == UIDirection.FromLeftToRight ? 1 : -1;
float max = element.resolvedStyle.width - Dragger.resolvedStyle.width;
float value = Mathf.InverseLerp(0, max, offset);
UpdateValue(value);
}
/// <summary> 更新值(0-1) </summary>
public void UpdateValue(float value, bool send = true) {
this.value = value;
if (send) { ValueChanged?.Invoke(value); }
float max = element.resolvedStyle.width - Dragger.resolvedStyle.width;
float position = Mathf.Lerp(0, max, value);
position *= direction == UIDirection.FromLeftToRight ? 1 : -1;
Dragger.transform.position = new Vector2(position, 0);
}
}
}
@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 78dab512282488544bf9d6f4ab6af6a7
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:
@@ -8,15 +8,89 @@ namespace MuHua {
/// <summary>
/// 滚动条 - 垂直
/// </summary>
public class UIScrollerV : MonoBehaviour {
// Start is called before the first frame update
void Start() {
public class UIScrollerV : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
/// <summary> 元素方向 </summary>
public readonly UIDirection direction;
/// <summary> 值改变时 </summary>
public event Action<float> ValueChanged;
/// <summary>
/// 方向
/// </summary>
public enum UIDirection {
FromTopToBottom = 0,
FromBottomToTop = 1,
}
// Update is called once per frame
void Update() {
public float value;
public bool isDragger;
public float originalPosition;
public float pointerPosition;
public readonly VisualElement Dragger;
public UIScrollerV(VisualElement element, VisualElement canvas, UIDirection direction = UIDirection.FromTopToBottom) : base(element) {
this.canvas = canvas;
this.direction = direction;
Dragger = Q<VisualElement>("Dragger");
element.style.flexDirection = direction == UIDirection.FromTopToBottom ? FlexDirection.Column : FlexDirection.ColumnReverse;
//设置事件
Dragger.RegisterCallback<PointerDownEvent>(DraggerDown);
element.RegisterCallback<PointerDownEvent>(ElementDown);
canvas.RegisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.RegisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 解绑事件,防止内存泄漏 </summary>
public void Dispose() {
Dragger.UnregisterCallback<PointerDownEvent>(DraggerDown);
element.UnregisterCallback<PointerDownEvent>(ElementDown);
canvas.UnregisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 拖拽按下 </summary>
private void DraggerDown(PointerDownEvent evt) {
isDragger = true;
originalPosition = Dragger.transform.position.y;
pointerPosition = Screen.height - UITool.GetMousePosition().y;
}
/// <summary> 元素按下 </summary>
private void ElementDown(PointerDownEvent evt) {
float offset = evt.localPosition.y - Dragger.resolvedStyle.height * 0.5f;
float max = element.resolvedStyle.height - Dragger.resolvedStyle.height;
float value1 = Mathf.InverseLerp(0, max, offset);
float value2 = Mathf.InverseLerp(max, 0, offset);
float value = direction == UIDirection.FromTopToBottom ? value1 : value2;
UpdateValue(value);
}
/// <summary> 鼠标松开或离开 </summary>
private void DraggerUpOrLeave(EventBase evt) {
isDragger = false;
}
/// <summary> 更新状态 </summary>
public void Update() {
if (!isDragger) { return; }
float differ = Screen.height - UITool.GetMousePosition().y - pointerPosition;
float offset = differ + originalPosition;
offset *= direction == UIDirection.FromTopToBottom ? 1 : -1;
float max = element.resolvedStyle.height - Dragger.resolvedStyle.height;
float value = Mathf.InverseLerp(0, max, offset);
UpdateValue(value);
}
/// <summary> 更新值(0-1) </summary>
public void UpdateValue(float value, bool send = true) {
this.value = value;
if (send) { ValueChanged?.Invoke(value); }
float max = element.resolvedStyle.height - Dragger.resolvedStyle.height;
float position = Mathf.Lerp(0, max, value);
position *= direction == UIDirection.FromTopToBottom ? 1 : -1;
Dragger.transform.position = new Vector2(0, position);
}
}
}
@@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 985a0cbfe2511cf4da59008d35538c18
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
@@ -8,6 +8,7 @@ namespace MuHua {
/// <summary>
/// 滑块
/// </summary>
[Obsolete("使用 UISliderV 或者 UISliderH 替换")]
public class UISlider : ModuleUIPanel {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
@@ -23,8 +24,8 @@ namespace MuHua {
public readonly UISliderFunc sliderFunc;
public VisualElement Container => Q<VisualElement>("Container");
public VisualElement Title => Q<VisualElement>("Title");
public VisualElement Container => Q<VisualElement>("Container");
public VisualElement Tracker => Q<VisualElement>("Tracker");
public VisualElement Dragger => Q<VisualElement>("Dragger");
@@ -0,0 +1,100 @@
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UIElements;
namespace MuHua {
/// <summary>
/// 滑块 - 水平
/// </summary>
public class UISliderH : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
/// <summary> 元素方向 </summary>
public readonly UIDirection direction;
/// <summary> 值改变时 </summary>
public event Action<float> ValueChanged;
/// <summary>
/// 方向
/// </summary>
public enum UIDirection {
FromLeftToRight = 0,
FromRightToLeft = 1,
}
public float value;
public bool isDragger;
public float originalPosition;
public float pointerPosition;
public readonly VisualElement Title;
public readonly VisualElement Container;
public readonly VisualElement Tracker;
public readonly VisualElement Dragger;
public UISliderH(VisualElement element, VisualElement canvas, UIDirection direction = UIDirection.FromLeftToRight) : base(element) {
this.canvas = canvas;
this.direction = direction;
Title = Q<VisualElement>("Title");
Container = Q<VisualElement>("Container");
Tracker = Q<VisualElement>("Tracker");
Dragger = Q<VisualElement>("Dragger");
//设置事件
Dragger.RegisterCallback<PointerDownEvent>(DraggerDown);
Container.RegisterCallback<PointerDownEvent>(ElementDown);
canvas.RegisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.RegisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 解绑事件,防止内存泄漏 </summary>
public void Dispose() {
Dragger.UnregisterCallback<PointerDownEvent>(DraggerDown);
element.UnregisterCallback<PointerDownEvent>(ElementDown);
canvas.UnregisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 拖拽按下 </summary>
private void DraggerDown(PointerDownEvent evt) {
isDragger = true;
float value1 = Tracker.resolvedStyle.width;
float value2 = Container.resolvedStyle.width - Tracker.resolvedStyle.width;
originalPosition = direction == UIDirection.FromLeftToRight ? value1 : value2;
pointerPosition = UITool.GetMousePosition().x;
}
/// <summary> 元素按下 </summary>
private void ElementDown(PointerDownEvent evt) {
float offset = evt.localPosition.x;
float max = Container.resolvedStyle.width;
float value1 = Mathf.InverseLerp(0, max, offset);
float value2 = Mathf.InverseLerp(max, 0, offset);
float value = direction == UIDirection.FromLeftToRight ? value1 : value2;
UpdateValue(value);
}
/// <summary> 鼠标松开或离开 </summary>
private void DraggerUpOrLeave(EventBase evt) {
isDragger = false;
}
/// <summary> 更新状态 </summary>
public void Update() {
if (!isDragger) { return; }
float differ = UITool.GetMousePosition().x - pointerPosition;
float offset = differ + originalPosition;
float max = Container.resolvedStyle.width;
float value1 = Mathf.InverseLerp(0, max, offset);
float value2 = Mathf.InverseLerp(max, 0, offset);
float value = direction == UIDirection.FromLeftToRight ? value1 : value2;
UpdateValue(value);
}
/// <summary> 更新值(0-1) </summary>
public void UpdateValue(float obj, bool send = true) {
value = (float)Math.Round(obj, 3);
if (send) { ValueChanged?.Invoke(value); }
Tracker.style.width = Length.Percent(value * 100);
}
}
}
@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 444651e6c05c5bc4cbf72b8740f2c429
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:
@@ -0,0 +1,100 @@
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UIElements;
namespace MuHua {
/// <summary>
/// 滑块 - 垂直
/// </summary>
public class UISliderV : ModuleUIPanel, IDisposable {
/// <summary> 绑定的画布 </summary>
public readonly VisualElement canvas;
/// <summary> 元素方向 </summary>
public readonly UIDirection direction;
/// <summary> 值改变时 </summary>
public event Action<float> ValueChanged;
/// <summary>
/// 方向
/// </summary>
public enum UIDirection {
FromTopToBottom = 0,
FromBottomToTop = 1,
}
public float value;
public bool isDragger;
public float originalPosition;
public float pointerPosition;
public readonly VisualElement Title;
public readonly VisualElement Container;
public readonly VisualElement Tracker;
public readonly VisualElement Dragger;
public UISliderV(VisualElement element, VisualElement canvas, UIDirection direction = UIDirection.FromTopToBottom) : base(element) {
this.canvas = canvas;
this.direction = direction;
Title = Q<VisualElement>("Title");
Container = Q<VisualElement>("Container");
Tracker = Q<VisualElement>("Tracker");
Dragger = Q<VisualElement>("Dragger");
//设置事件
Dragger.RegisterCallback<PointerDownEvent>(DraggerDown);
Container.RegisterCallback<PointerDownEvent>(ElementDown);
canvas.RegisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.RegisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 解绑事件,防止内存泄漏 </summary>
public void Dispose() {
Dragger.UnregisterCallback<PointerDownEvent>(DraggerDown);
element.UnregisterCallback<PointerDownEvent>(ElementDown);
canvas.UnregisterCallback<PointerUpEvent>(DraggerUpOrLeave);
canvas.UnregisterCallback<PointerLeaveEvent>(DraggerUpOrLeave);
}
/// <summary> 拖拽按下 </summary>
private void DraggerDown(PointerDownEvent evt) {
isDragger = true;
float value1 = Tracker.resolvedStyle.height;
float value2 = Container.resolvedStyle.height - Tracker.resolvedStyle.height;
originalPosition = direction == UIDirection.FromTopToBottom ? value1 : value2;
pointerPosition = Screen.height - UITool.GetMousePosition().y;
}
/// <summary> 元素按下 </summary>
private void ElementDown(PointerDownEvent evt) {
float offset = evt.localPosition.y;
float max = Container.resolvedStyle.height;
float value1 = Mathf.InverseLerp(0, max, offset);
float value2 = Mathf.InverseLerp(max, 0, offset);
float value = direction == UIDirection.FromTopToBottom ? value1 : value2;
UpdateValue(value);
}
/// <summary> 鼠标松开或离开 </summary>
private void DraggerUpOrLeave(EventBase evt) {
isDragger = false;
}
/// <summary> 更新状态 </summary>
public void Update() {
if (!isDragger) { return; }
float differ = Screen.height - UITool.GetMousePosition().y - pointerPosition;
float offset = differ + originalPosition;
float max = Container.resolvedStyle.height;
float value1 = Mathf.InverseLerp(0, max, offset);
float value2 = Mathf.InverseLerp(max, 0, offset);
float value = direction == UIDirection.FromTopToBottom ? value1 : value2;
UpdateValue(value);
}
/// <summary> 更新值(0-1) </summary>
public void UpdateValue(float obj, bool send = true) {
value = (float)Math.Round(obj, 3);
if (send) { ValueChanged?.Invoke(value); }
Tracker.style.height = Length.Percent(value * 100);
}
}
}
@@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f80b8dbc68fee4444bbce14f02dafe44
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant: