Files
PacManUdon/Assets/Scripts/PelletManager.cs
2026-01-18 19:28:12 +01:00

133 lines
4.1 KiB
C#

using System;
using UnityEngine;
namespace Marro.PacManUdon
{
public class PelletManager : SyncedObject
{
public int PelletCount => pellets.Length;
public int PelletCollectedCount { get; private set; }
Pellet[] pellets;
Animator[] powerPellets;
bool powerPelletBlinkEnabled;
float powerPelletBlinkToggleInterval;
float powerPelletBlinkProgress;
bool powerPelletBlinkCurrentlyVisible;
byte[] syncedPelletsCollected;
public void Initialize()
{
gameObject.SetActive(true);
pellets = GetComponentsInChildren<Pellet>(includeInactive: true);
powerPellets = GetComponentsInChildren<Animator>(true);
powerPelletBlinkToggleInterval = PacManConstants.GetPowerPelletBlinkToggleInterval();
SetPowerPelletsBlink(false);
RestoreAllPellets();
}
public override void SyncedUpdate()
{
if (!powerPelletBlinkEnabled)
{
return;
}
powerPelletBlinkProgress += networkManager.SyncedDeltaTime;
if (powerPelletBlinkProgress >= powerPelletBlinkToggleInterval)
{
// Debug.Log($"{gameObject} PowerPelletBlink toggle");
powerPelletBlinkProgress -= powerPelletBlinkToggleInterval;
powerPelletBlinkCurrentlyVisible = !powerPelletBlinkCurrentlyVisible;
SetPowerPelletsVisible(powerPelletBlinkCurrentlyVisible);
}
}
void SetPowerPelletsVisible(bool visible)
{
// Debug.Log($"{gameObject} SetPowerPelletVisible {visible}, powerPellets.Length: {powerPellets.Length}");
foreach (Animator powerPellet in powerPellets)
{
powerPellet.SetBool("Visible", visible);
}
}
public void SetPowerPelletsBlink(bool enabled)
{
// Debug.Log($"{gameObject} SetPowerPelletBlink {enabled}");
powerPelletBlinkEnabled = enabled;
powerPelletBlinkCurrentlyVisible = true;
powerPelletBlinkProgress = 0;
SetPowerPelletsVisible(true);
}
public void FreezePowerPelletsBlink(bool frozen)
{
powerPelletBlinkEnabled = !frozen;
}
public int PelletCollected(Pellet pellet)
{
pellet.gameObject.SetActive(false);
var index = pellet.transform.GetSiblingIndex();
syncedPelletsCollected[index/8] |= (byte)(1 << index%8);
PelletCollectedCount++;
return PelletCollectedCount;
}
public int RestoreAllPellets()
{
foreach (var pellet in pellets)
{
pellet.gameObject.SetActive(true);
}
syncedPelletsCollected = new byte[pellets.Length/8 + 1];
PelletCollectedCount = 0;
return PelletCount;
}
private void SetPelletsCollectedFromSync()
{
for (int i = 0; i < pellets.Length; i++)
{
var active = (syncedPelletsCollected[i/8] & (byte)(1 << i%8)) == 0;
pellets[i].gameObject.SetActive(active);
}
}
public override void CollectSyncedData(byte[] data, ref int index, NetworkEventType eventType)
{
if (eventType != NetworkEventType.SyncPellets)
{
return;
}
data.Append((byte)PelletCollectedCount, ref index);
data.Append(syncedPelletsCollected, ref index);
}
public override bool WriteSyncedData(byte[] data, ref int index, NetworkEventType eventType)
{
if (eventType != NetworkEventType.SyncPellets)
{
return true;
}
PelletCollectedCount = data.ReadByte(ref index);
Array.Copy(data, index, syncedPelletsCollected, 0, syncedPelletsCollected.Length);
index += syncedPelletsCollected.Length;
SetPelletsCollectedFromSync();
return true;
}
}
}