1
This commit is contained in:
@@ -16,20 +16,27 @@ namespace BITFALL.UX
|
||||
public class UXDialogue : MonoBehaviour
|
||||
{
|
||||
[SerializeField] private UXBuilder dialogueBuilder;
|
||||
private CancellationToken _cancellationToken;
|
||||
private void Awake()
|
||||
{
|
||||
DialogueTree.OnSubtitlesRequest += OnSubtitlesRequest;
|
||||
_cancellationToken = this.GetCancellationTokenOnDestroy();
|
||||
}
|
||||
|
||||
private readonly ValidHandle allowBackground = new();
|
||||
private readonly List<int> _dialogueIds = new();
|
||||
|
||||
private void Start()
|
||||
{
|
||||
dialogueBuilder.VisualElement.SetActive(false);
|
||||
allowBackground.AddListener(dialogueBuilder.VisualElement.SetActive);
|
||||
allowBackground.Invoke();
|
||||
destroyCancellationToken.Register(() =>
|
||||
{
|
||||
DialogueTree.OnSubtitlesRequest -= OnSubtitlesRequest;
|
||||
});
|
||||
}
|
||||
|
||||
private async void OnSubtitlesRequest(SubtitlesRequestInfo obj)
|
||||
{
|
||||
|
||||
var id = obj.GetHashCode();
|
||||
|
||||
_dialogueIds.Add(id);
|
||||
|
||||
dialogueBuilder.VisualElement.SetActive(true);
|
||||
var container = dialogueBuilder.BuildAsContainer();
|
||||
container.contextLabel.text = $"{obj.actor.name}:{obj.statement}";
|
||||
@@ -37,32 +44,29 @@ namespace BITFALL.UX
|
||||
{
|
||||
if (double.TryParse( obj.statement.meta,out var duration))
|
||||
{
|
||||
await Task.Delay(TimeSpan.FromSeconds(duration), _cancellationToken);
|
||||
await Task.Delay(TimeSpan.FromSeconds(duration), destroyCancellationToken);
|
||||
}
|
||||
else
|
||||
{
|
||||
await Task.Delay(5000, _cancellationToken);
|
||||
await Task.Delay(5000, destroyCancellationToken);
|
||||
}
|
||||
obj.Continue.Invoke();
|
||||
await Task.Delay(5000, _cancellationToken);
|
||||
await Task.Delay(5000, destroyCancellationToken);
|
||||
container.visualElement.AddToClassList("dispose");
|
||||
await Task.Delay(1000, _cancellationToken);
|
||||
await Task.Delay(1000, destroyCancellationToken);
|
||||
container.visualElement.RemoveFromHierarchy();
|
||||
}
|
||||
catch (OperationCanceledException)
|
||||
{
|
||||
obj.Continue.Invoke();
|
||||
}
|
||||
|
||||
_dialogueIds.Remove(id);
|
||||
}
|
||||
|
||||
private void Update()
|
||||
{
|
||||
dialogueBuilder.VisualElement.SetActive(dialogueBuilder.VisualElement.childCount > 0);
|
||||
}
|
||||
|
||||
private void OnDestroy()
|
||||
{
|
||||
DialogueTree.OnSubtitlesRequest -= OnSubtitlesRequest;
|
||||
allowBackground.SetElements(this, _dialogueIds.Count is not 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
141
Assets/Artists/Scripts/UX/UXGunModify.cs
Normal file
141
Assets/Artists/Scripts/UX/UXGunModify.cs
Normal file
@@ -0,0 +1,141 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using BITFALL.Entities.Equipment;
|
||||
using BITFALL.Entities.Inventory;
|
||||
using BITFALL.Guns.Modify;
|
||||
using BITFALL.Items;
|
||||
using BITFALL.Player.Equip;
|
||||
using BITKit;
|
||||
using BITKit.Entities;
|
||||
using BITKit.Entities.Player;
|
||||
using BITKit.UX;
|
||||
using UnityEngine;
|
||||
using UnityEngine.UIElements;
|
||||
|
||||
namespace BITFALL.UX
|
||||
{
|
||||
public class UXGunModify : MonoBehaviour
|
||||
{
|
||||
[SerializeReference, SubclassSelector] private IPlayerService playerService;
|
||||
private VisualElement _container => UXInventoryInspector.Container;
|
||||
|
||||
[Inject] private IEntityInventory _inventory;
|
||||
[Inject] private IEntityEquipment _equipment;
|
||||
[Inject] private IEquipService _equipService;
|
||||
[Inject] private IUXPopup _popup;
|
||||
private void Start()
|
||||
{
|
||||
UXInventoryInspector.OnInspect += OnInspect;
|
||||
|
||||
playerService.OnPlayerInitialized += OnPlayerInitialized;
|
||||
destroyCancellationToken.Register(() =>
|
||||
{
|
||||
UXInventoryInspector.OnInspect -= OnInspect;
|
||||
playerService.OnPlayerInitialized -= OnPlayerInitialized;
|
||||
});
|
||||
}
|
||||
|
||||
private void OnPlayerInitialized(Entity obj)
|
||||
{
|
||||
obj.Inject(this);
|
||||
}
|
||||
|
||||
private void OnInspect(IBasicItem obj)
|
||||
{
|
||||
if (_inventory is null)
|
||||
{
|
||||
Debug.LogWarning("Inventory is null");
|
||||
return;
|
||||
}
|
||||
if (obj is null) return;
|
||||
var assetable = obj.GetAssetable();
|
||||
if (obj.TryGetProperty<GunModify>(out var modify) is false) return;
|
||||
|
||||
var playerItems = _inventory.GetItems();
|
||||
|
||||
foreach (var pair in modify.Modifies)
|
||||
{
|
||||
var container = _container.Create<VisualElement>();
|
||||
var dropdown = container.Create<DropdownField>();
|
||||
|
||||
container.style.flexDirection = FlexDirection.Row;
|
||||
dropdown.style.flexGrow = 1;
|
||||
|
||||
dropdown.label = pair.Key.GetType().Name;
|
||||
|
||||
if (pair.Value is AssetableItem modifyItem)
|
||||
{
|
||||
dropdown.SetValueWithoutNotify(modifyItem.Name);
|
||||
}
|
||||
|
||||
if (pair.Value is not null)
|
||||
{
|
||||
dropdown.SetEnabled(false);
|
||||
var button = container.Create<Button>();
|
||||
button.text = "卸下";
|
||||
button.clicked += () =>
|
||||
{
|
||||
modify.Remove(pair.Key, out var value);
|
||||
var copy = value.As<ICloneable>().Clone().As<IBasicItem>();
|
||||
if (_inventory.Add(copy))
|
||||
{
|
||||
_popup.Popup("配件已返回背包");
|
||||
}
|
||||
else if (_inventory.DropOrSpawn(copy))
|
||||
{
|
||||
_popup.Popup("背包可能已满,配件已掉落");
|
||||
}
|
||||
|
||||
UXInventoryInspector.Entry(obj);
|
||||
RebuildPlayerLayout();
|
||||
};
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
|
||||
var attachments = (
|
||||
from item in playerItems
|
||||
where item.GetAssetable() is AssetableAttachment attachment &&
|
||||
attachment.Type.GetType().IsInstanceOfType(pair.Key)
|
||||
select item
|
||||
).ToArray();
|
||||
|
||||
if (attachments.Length is 0 && pair.Value is null)
|
||||
{
|
||||
dropdown.SetValueWithoutNotify("无可用配件");
|
||||
dropdown.SetEnabled(false);
|
||||
}
|
||||
|
||||
dropdown.choices = attachments.Select(item => item.Name).ToList();
|
||||
|
||||
var nextAttachmentList = attachments.ToList();
|
||||
|
||||
dropdown.RegisterValueChangedCallback(x =>
|
||||
{
|
||||
var next = nextAttachmentList[dropdown.index];
|
||||
if (_inventory.Remove(next))
|
||||
{
|
||||
var nextAsset = next.GetAssetable();
|
||||
modify.Add(pair.Key, nextAsset);
|
||||
_popup.Popup($"配件{nextAsset.name}已装备在{obj.Name}");
|
||||
}
|
||||
|
||||
UXInventoryInspector.Entry(obj);
|
||||
RebuildPlayerLayout();
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
private async void RebuildPlayerLayout()
|
||||
{
|
||||
_equipService.AllowEquip.AddDisableElements(this);
|
||||
await Task.Delay(100, destroyCancellationToken);
|
||||
_equipService.AllowEquip.RemoveDisableElements(this);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
@@ -2,6 +2,8 @@ using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using BITFALL.Entities.Armor;
|
||||
using BITFALL.Entities.Equipment;
|
||||
using BITFALL.Guns;
|
||||
using BITFALL.Player.Equip;
|
||||
using BITFALL.Player.Movement;
|
||||
using UnityEngine;
|
||||
@@ -43,6 +45,7 @@ namespace BITFALL.UX
|
||||
[Header(Constant.Header.Input)]
|
||||
[SerializeField] private InputActionReference inventoryAction;
|
||||
[SerializeField] private InputActionReference returnAction;
|
||||
[SerializeField] private InputActionReference inspectAction;
|
||||
|
||||
[Inject]
|
||||
private IHealth _health;
|
||||
@@ -53,9 +56,14 @@ namespace BITFALL.UX
|
||||
[Inject]
|
||||
private IEquipService _equipService;
|
||||
[Inject]
|
||||
private IEntityEquipment _equipment;
|
||||
[Inject]
|
||||
private ISelector _selector;
|
||||
[Inject]
|
||||
private IArmor _armor;
|
||||
|
||||
[UXBindPath("count-label")] private Label countLabel;
|
||||
|
||||
private float _currentHealthLerp;
|
||||
protected override void Awake()
|
||||
{
|
||||
@@ -63,10 +71,23 @@ namespace BITFALL.UX
|
||||
seleableLabel.SetActive(false);
|
||||
inputActionGroup.RegisterCallback(returnAction, OnReturn);
|
||||
inputActionGroup.RegisterCallback(inventoryAction, OnInventory);
|
||||
inputActionGroup.RegisterCallback(inspectAction, OnInspect);
|
||||
|
||||
sceneService.OnSceneLoaded += x=>Entry();
|
||||
|
||||
playerService.OnPlayerInitialized += OnPlayerInitializedLocalPlayer;
|
||||
|
||||
BITKit.UX.UXUtils.Inject(this);
|
||||
}
|
||||
|
||||
private void OnInspect(InputAction.CallbackContext obj)
|
||||
{
|
||||
switch (obj,_equipment)
|
||||
{
|
||||
case ({interaction:HoldInteraction,performed:true}, {CurrentItem: not null}):
|
||||
UXInventoryInspector.Entry(_equipment.CurrentItem);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private void OnDestroy()
|
||||
@@ -156,6 +177,28 @@ namespace BITFALL.UX
|
||||
: "互动");
|
||||
}
|
||||
}
|
||||
|
||||
countLabel.SetVisible(false);
|
||||
if (_equipment is not null)
|
||||
{
|
||||
if (_equipment.CurrentItem is not null)
|
||||
{
|
||||
switch (_equipment.CurrentItem)
|
||||
{
|
||||
case var x when x.TryGetProperty<IClip>(out var clip):
|
||||
countLabel.text = clip.ToString();
|
||||
|
||||
countLabel.SetVisible(true);
|
||||
break;
|
||||
case var x when x.TryGetProperty<ICount>(out var count):
|
||||
countLabel.text = count.Count.ToString();
|
||||
|
||||
countLabel.SetVisible(true);
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void LateUpdate()
|
||||
|
@@ -140,6 +140,7 @@ namespace BITFALL.UX
|
||||
.Create()
|
||||
.BuildAction("使用", () => UseItem(item))
|
||||
.BuildAction("丢下", () => DropItem(item))
|
||||
.BuildAction("检视", () => UXInventoryInspector.Entry(item))
|
||||
.Build();
|
||||
}
|
||||
});
|
||||
@@ -154,10 +155,7 @@ namespace BITFALL.UX
|
||||
private void OnSet(IBasicItem item)
|
||||
{
|
||||
if (!itemContainers.TryGetValue(item.Id, out var uxContainer)) return;
|
||||
if(item.TryGetProperty<int>(out var count))
|
||||
{
|
||||
uxContainer.numberLabel.text = count.ToString();
|
||||
}
|
||||
UXUtils.CreateItemContainer(uxContainer, item);
|
||||
}
|
||||
|
||||
private void UseItem(IBasicItem item)
|
||||
|
69
Assets/Artists/Scripts/UX/UXInventoryInspector.cs
Normal file
69
Assets/Artists/Scripts/UX/UXInventoryInspector.cs
Normal file
@@ -0,0 +1,69 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using BITKit;
|
||||
using BITKit.UX;
|
||||
using UnityEngine;
|
||||
using UnityEngine.InputSystem;
|
||||
using UnityEngine.InputSystem.Interactions;
|
||||
using UnityEngine.UIElements;
|
||||
|
||||
namespace BITFALL.UX
|
||||
{
|
||||
public class UXInventoryInspector : UIToolKitPanel
|
||||
{
|
||||
public static void Entry(IBasicItem item)
|
||||
{
|
||||
OnInspect?.Invoke(item);
|
||||
}
|
||||
|
||||
public static event Action<IBasicItem> OnInspect;
|
||||
public static VisualElement Container { get; private set; }
|
||||
|
||||
[SerializeField] private InputActionReference cancelAction;
|
||||
[SerializeField] private InputActionReference inventoryAction;
|
||||
|
||||
private UXContainer _container;
|
||||
[UXBindPath("modify-container")]
|
||||
private VisualElement _modifyContainer;
|
||||
protected override void Start()
|
||||
{
|
||||
base.Start();
|
||||
OnInspect += OnInspectItem;
|
||||
destroyCancellationToken.Register(() =>
|
||||
{
|
||||
OnInspect -= OnInspectItem;
|
||||
});
|
||||
_container = new UXContainer(document.rootVisualElement);
|
||||
inputActionGroup.RegisterCallback(cancelAction, OnCancel);
|
||||
inputActionGroup.RegisterCallback(inventoryAction, OnInventory);
|
||||
BITKit.UX.UXUtils.Inject(this);
|
||||
Container = _modifyContainer;
|
||||
}
|
||||
|
||||
private void OnInventory(InputAction.CallbackContext context)
|
||||
{
|
||||
//UXService.Entry<UXInventory>();
|
||||
if(context is {interaction:PressInteraction,performed:true})
|
||||
UXService.Return();
|
||||
}
|
||||
|
||||
private void OnCancel(InputAction.CallbackContext obj)
|
||||
{
|
||||
UXService.Entry<UXHud>();
|
||||
}
|
||||
|
||||
private void OnInspectItem(IBasicItem obj)
|
||||
{
|
||||
Container.Clear();
|
||||
Entry();
|
||||
var source = obj.GetAssetable();
|
||||
_container.titleLabel.text = source.Name;
|
||||
_container.icon.style.backgroundImage = source.RectangleIcon ? source.RectangleIcon : source.SquareIcon;
|
||||
_container.contextLabel.text = source.Description;
|
||||
_container.descriptionLabel.text =string.Join("\n",obj.GetProperties());
|
||||
}
|
||||
}
|
||||
|
||||
}
|
@@ -11,6 +11,7 @@ using BITKit.UX;
|
||||
using Cysharp.Threading.Tasks;
|
||||
using UnityEngine;
|
||||
using UnityEngine.InputSystem;
|
||||
using UnityEngine.InputSystem.Composites;
|
||||
using UnityEngine.InputSystem.Interactions;
|
||||
using UnityEngine.UIElements;
|
||||
using UXUtils = BITFALL.UX.UXUtils;
|
||||
@@ -34,16 +35,19 @@ namespace BITFALL.Items
|
||||
[Inject]
|
||||
private IEntityInventory inventory;
|
||||
|
||||
[UXBindPath("self-container")]
|
||||
private VisualElement selfContainer;
|
||||
[UXBindPath("other-container")]
|
||||
private VisualElement otherContainer;
|
||||
[UXBindPath("other-label")]
|
||||
private Label otherLabel;
|
||||
protected override void Start()
|
||||
{
|
||||
base.Start();
|
||||
inputActionGroup.RegisterCallback(escapeAction, OnEscape);
|
||||
inputActionGroup.RegisterCallback(inventoryAction, OnInventory);
|
||||
|
||||
selfContainer = document.rootVisualElement.Q<VisualElement>("self-container");
|
||||
otherContainer = document.rootVisualElement.Q<VisualElement>("other-container");
|
||||
BITKit.UX.UXUtils.Inject(this);
|
||||
}
|
||||
|
||||
protected override void OnEnable()
|
||||
@@ -79,6 +83,10 @@ namespace BITFALL.Items
|
||||
{
|
||||
UXService.Entry<UXInventorySwap>();
|
||||
|
||||
if (obj is WorldItemContainer container)
|
||||
{
|
||||
otherLabel.text = $"{container.Name}\t{(container.AllowStorage ? "存储" : "<color=yellow>不可存储</color>")}\t{(container.AllowLoot ? "可拾取" : "<color=yellow>不可拾取</color>")}";
|
||||
}
|
||||
ReBuild(obj);
|
||||
}
|
||||
|
||||
@@ -110,14 +118,19 @@ namespace BITFALL.Items
|
||||
{
|
||||
var container = otherContainer.Create(itemPrefab);
|
||||
UXUtils.CreateItemContainer(container, item);
|
||||
container.Q<Button>().clicked += () => swapItem.Add(item);
|
||||
|
||||
container.RegisterCallback<MouseDownEvent>(x =>
|
||||
{
|
||||
swapItem.Add(item);
|
||||
});
|
||||
}
|
||||
foreach (var item in inventory.GetItems())
|
||||
{
|
||||
var container = selfContainer.Create(itemPrefab);
|
||||
UXUtils.CreateItemContainer(container, item);
|
||||
container.Q<Button>().clicked += () => swapItem.Remove(item);
|
||||
container.RegisterCallback<MouseDownEvent>(x =>
|
||||
{
|
||||
swapItem.Remove(item);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -32,6 +32,8 @@ namespace bitfall.UX
|
||||
[UXBindPath("equipSelector-container")]
|
||||
private VisualElement _equipSelectorContainerElement;
|
||||
|
||||
private VisualElement _currentEquipElement;
|
||||
|
||||
private readonly ConcurrentDictionary<string, VisualElement> _equipmentContainerDictionary = new();
|
||||
private readonly ConcurrentDictionary<int,VisualElement> _equipSelectorContainerDictionary=new();
|
||||
|
||||
@@ -42,6 +44,8 @@ namespace bitfall.UX
|
||||
|
||||
_playerService.OnPlayerInitialized += OnStartLocalPlayer;
|
||||
destroyCancellationToken.Register(() => _playerService.OnPlayerInitialized -= OnStartLocalPlayer);
|
||||
|
||||
|
||||
}
|
||||
|
||||
private void OnStartLocalPlayer(Entity obj)
|
||||
@@ -50,6 +54,8 @@ namespace bitfall.UX
|
||||
|
||||
_equipmentContainerElement.Clear();
|
||||
_equipSelectorContainerElement.Clear();
|
||||
|
||||
|
||||
|
||||
_playerEquipSelector.OnUpdateEquip += OnUpdateEquip;
|
||||
_equipmentContainer.OnEquip += OnEquip;
|
||||
@@ -83,6 +89,8 @@ namespace bitfall.UX
|
||||
_equipSelectorContainerElement.Clear();
|
||||
_equipSelectorContainerDictionary.Clear();
|
||||
|
||||
|
||||
|
||||
foreach (var (index,x) in obj)
|
||||
{
|
||||
var element =_equipSelectorContainerDictionary.GetOrAdd(index,CreateEquipSelectorContainer(x.AddressablePath));
|
||||
@@ -109,11 +117,12 @@ namespace bitfall.UX
|
||||
var container =
|
||||
_equipSelectorContainerElement.Create<VisualElement>(() => equipSelectorVisualTreeAsset.CloneTree());
|
||||
var element = BITFALL.UX.UXUtils.CreateItemContainer(container, item);
|
||||
|
||||
element.icon.style.backgroundImage = item.RectangleIcon;
|
||||
|
||||
|
||||
if (item.RectangleIcon)
|
||||
element.icon.style.backgroundImage = item.RectangleIcon;
|
||||
|
||||
element.visualElement.userData = addressablePath;
|
||||
|
||||
|
||||
return element;
|
||||
}
|
||||
|
||||
@@ -122,16 +131,32 @@ namespace bitfall.UX
|
||||
var current = _equipment.CurrentItem?.AddressablePath ?? string.Empty;
|
||||
const string active = "active";
|
||||
|
||||
_currentEquipElement?.RemoveFromHierarchy();
|
||||
_currentEquipElement =
|
||||
_equipSelectorContainerElement.Create<VisualElement>(equipSelectorVisualTreeAsset.CloneTree);
|
||||
_currentEquipElement.SetActive(false);
|
||||
|
||||
var list = new List<VisualElement>();
|
||||
list.AddRange(_equipmentContainerElement.Children());
|
||||
list.AddRange(_equipSelectorContainerElement.Children());
|
||||
foreach (var visualElement in list)
|
||||
list.Add(_currentEquipElement);
|
||||
foreach (var visualElement in list.Where(visualElement => visualElement.userData is not null))
|
||||
{
|
||||
visualElement.EnableInClassList(active,current == (string)visualElement.userData);
|
||||
var item = ItemExtensions.GetAssetable((string)visualElement.userData);
|
||||
visualElement.SetEnabled(
|
||||
!_knockdown.IsKnockdown || item.AllowUseWhileKnocked
|
||||
);
|
||||
);
|
||||
}
|
||||
|
||||
if (_equipment.CurrentItem is not null && _playerEquipSelector.Equipped.Values.All(x => x.AddressablePath != _equipment.CurrentItem.AddressablePath))
|
||||
{
|
||||
BITFALL.UX.UXUtils.CreateItemContainer(_currentEquipElement, _equipment.CurrentItem);
|
||||
_currentEquipElement.SetActive(true);
|
||||
}
|
||||
else
|
||||
{
|
||||
_currentEquipElement.SetActive(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -2,6 +2,7 @@ using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using BITKit;
|
||||
using BITKit.UX;
|
||||
using Steamworks.Data;
|
||||
using UnityEngine;
|
||||
using UnityEngine.UIElements;
|
||||
|
||||
@@ -13,8 +14,27 @@ namespace BITFALL.UX
|
||||
{
|
||||
var asset = item.GetAssetable();
|
||||
var uxContainer = new UXContainer(visualElement);
|
||||
uxContainer.icon.style.backgroundImage = asset.SquareIcon;
|
||||
uxContainer.icon.style.backgroundImage =asset.SquareIcon;
|
||||
uxContainer.contextLabel.text = asset.Name;
|
||||
visualElement.userData = item.AddressablePath;
|
||||
|
||||
if (uxContainer.numberLabel is not null)
|
||||
{
|
||||
if (item.TryGetProperty<ICount>(out var count))
|
||||
{
|
||||
uxContainer.numberLabel.text = count.Count.ToString();
|
||||
uxContainer.numberLabel.SetActive(true);
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
uxContainer.numberLabel.SetActive(false);
|
||||
}
|
||||
}
|
||||
if (uxContainer.descriptionLabel is not null)
|
||||
{
|
||||
uxContainer.descriptionLabel.text = asset.Description;
|
||||
}
|
||||
return uxContainer;
|
||||
}
|
||||
}
|
||||
|
Reference in New Issue
Block a user