Files
riversong-code-showcase/Source/Riversong/Game/World/Buildings/Visualizations/BuildingStorageVisualizationSystem.cs
2026-05-21 16:04:49 +02:00

96 lines
3.2 KiB
C#

using System;
using Cysharp.Threading.Tasks;
using UnityEngine;
namespace DanieleMarotta.RiversongCodeShowcase
{
public class BuildingStorageVisualizationSystem : GameSystem, IInitializable, IDisposable, IUpdatable
{
private const int StackProductCount = 10;
[InjectService]
private IEntityCache _entityCache;
[InjectService]
private IPoolingService _poolingService;
[InjectService]
private IProductCatalog _productCatalog;
[InjectService]
private IBuildingVisualizationCollection _buildingVisualizations;
[InjectService]
private ISignalBus _signalBus;
public BuildingStorageVisualizationSystem(IServiceLocator serviceLocator) : base(serviceLocator)
{
}
public UniTask InitializeAsync()
{
_signalBus.Subscribe<BuildingDeletedSignal>(OnBuildingDeleted);
return UniTask.CompletedTask;
}
public void Dispose()
{
_signalBus.Unsubscribe<BuildingDeletedSignal>(OnBuildingDeleted);
}
public void Update()
{
foreach (var storehouse in _entityCache.GetStorageBuildings()) UpdateStorehouse(storehouse);
}
private void UpdateStorehouse(Building storehouse)
{
if (!_buildingVisualizations.TryGetVisualization(storehouse.Id, out var buildingVisualization)) return;
var storageVisualization = buildingVisualization.GetComponent<BuildingStorageVisualization>();
if (storageVisualization.SlotCount <= 0) return;
ReleaseProductVisualizations(storageVisualization);
ref var storage = ref storehouse.GetStorageRW();
var slotIndex = 0;
foreach (var (productHandle, amount) in storage)
{
var product = _productCatalog.GetProduct(productHandle);
var poolKey = ((GameObject)product.ProductStackVisualization.Asset).GetInstanceID();
var amountLeft = amount;
while (amountLeft > 0)
{
var productVisualization = _poolingService.Get<GameObject>(poolKey);
storageVisualization.SetProductVisualization(slotIndex, productVisualization);
if (++slotIndex >= storageVisualization.SlotCount) return;
amountLeft -= StackProductCount;
}
}
}
private void OnBuildingDeleted(BuildingDeletedSignal signal)
{
if (!signal.Building.Definition.IsStorage) return;
_buildingVisualizations.TryGetVisualization(signal.Building.Id, out var buildingVisualization);
var storageVisualization = buildingVisualization.GetComponent<BuildingStorageVisualization>();
ReleaseProductVisualizations(storageVisualization);
}
private void ReleaseProductVisualizations(BuildingStorageVisualization storageVisualization)
{
for (var i = 0; i < storageVisualization.SlotCount; i++)
{
if (!storageVisualization.TryGetProductVisualization(i, out var productVisualization)) return;
_poolingService.Release(productVisualization);
}
}
}
}