73 lines
1.9 KiB
C#

using UnityEngine;
using Cysharp.Threading.Tasks;
using System.Threading;
using System;
using System.Collections.Concurrent;
public class ReplicasPlayer : MonoBehaviour
{
[SerializeField] float delay = 0.5f;
private bool initialized = false;
private ConcurrentQueue<Replica> replicas;
public void Init()
{
if (initialized)
{
Debug.LogWarning("Попытка повторной инициализации системы", this);
return;
}
replicas = new ConcurrentQueue<Replica>();
var token = this.GetCancellationTokenOnDestroy();
Process(token).Forget();
initialized = true;
}
public void EnqueueReplica(Replica replica)
{
if (!initialized) return;
var handledReplica = replica;
if (handledReplica.clip == null) return;
if (UnityEngine.Random.Range(0f, 1f) >= handledReplica.probability)
return;
if (handledReplica.playParallel)
{
Debug.Log("исполняю");
SoundManager.PlayReplica(handledReplica.clip);
return;
}
handledReplica.creationTime = Time.time;
replicas.Enqueue(handledReplica);
}
public void EnqueueReplica(ReplicasSequence replicas) => EnqueueReplica(replicas.GetRandomReplica());
private async UniTask Process(CancellationToken token)
{
while (!token.IsCancellationRequested)
{
if (replicas.TryDequeue(out Replica replica))
{
bool replicaIsFresh = Time.time - replica.creationTime <= replica.lifetime;
if (replicaIsFresh)
{
SoundManager.PlayReplica(replica.clip);
await UniTask.Delay(TimeSpan.FromSeconds(replica.clip.length + delay), cancellationToken: token);
continue;
}
}
await UniTask.Yield();
}
}
}