summaryrefslogtreecommitdiff
path: root/Client/Assembly-CSharp/GameData.cs
diff options
context:
space:
mode:
Diffstat (limited to 'Client/Assembly-CSharp/GameData.cs')
-rw-r--r--Client/Assembly-CSharp/GameData.cs556
1 files changed, 556 insertions, 0 deletions
diff --git a/Client/Assembly-CSharp/GameData.cs b/Client/Assembly-CSharp/GameData.cs
new file mode 100644
index 0000000..4941bd6
--- /dev/null
+++ b/Client/Assembly-CSharp/GameData.cs
@@ -0,0 +1,556 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using Assets.CoreScripts;
+using Hazel;
+using InnerNet;
+using UnityEngine;
+
+public class GameData : InnerNetObject, IDisconnectHandler
+{
+ public int PlayerCount
+ {
+ get
+ {
+ return this.AllPlayers.Count;
+ }
+ }
+
+ public static GameData Instance;
+
+ // 所有角色数据
+ public List<GameData.PlayerInfo> AllPlayers = new List<GameData.PlayerInfo>();
+
+ public int TotalTasks;
+
+ public int CompletedTasks;
+
+ public const byte InvalidPlayerId = 255;
+
+ public const byte DisconnectedPlayerId = 254;
+
+ public class TaskInfo
+ {
+ public uint Id;
+
+ public bool Complete;
+
+ public void Serialize(MessageWriter writer)
+ {
+ writer.WritePacked(this.Id);
+ writer.Write(this.Complete);
+ }
+
+ public void Deserialize(MessageReader reader)
+ {
+ this.Id = reader.ReadPackedUInt32();
+ this.Complete = reader.ReadBoolean();
+ }
+ }
+
+ //c 角色数据,包括外观、装饰、是否是imposter、是否死亡
+ public class PlayerInfo
+ {
+ public PlayerControl Object
+ {
+ get
+ {
+ if (!this._object)
+ {
+ this._object = PlayerControl.AllPlayerControls.FirstOrDefault((PlayerControl p) => p.PlayerId == this.PlayerId);
+ }
+ return this._object;
+ }
+ }
+
+ public readonly byte PlayerId;
+
+ public string PlayerName = string.Empty;
+
+ public byte ColorId;
+
+ public uint HatId;
+
+ public uint PetId;
+
+ public uint SkinId;
+
+ public bool Disconnected;
+
+ public List<GameData.TaskInfo> Tasks;
+
+ public bool IsImpostor;
+
+ public bool IsDead;
+
+ private PlayerControl _object;
+
+ public PlayerInfo(byte playerId)
+ {
+ this.PlayerId = playerId;
+ }
+
+ public PlayerInfo(PlayerControl pc) : this(pc.PlayerId)
+ {
+ this._object = pc;
+ }
+
+ public void Serialize(MessageWriter writer)
+ {
+ writer.Write(this.PlayerName);
+ writer.Write(this.ColorId);
+ writer.WritePacked(this.HatId);
+ writer.WritePacked(this.PetId);
+ writer.WritePacked(this.SkinId);
+ byte b = 0;
+ if (this.Disconnected)
+ {
+ b |= 1;
+ }
+ if (this.IsImpostor)
+ {
+ b |= 2;
+ }
+ if (this.IsDead)
+ {
+ b |= 4;
+ }
+ writer.Write(b);
+ if (this.Tasks != null)
+ {
+ writer.Write((byte)this.Tasks.Count);
+ for (int i = 0; i < this.Tasks.Count; i++)
+ {
+ this.Tasks[i].Serialize(writer);
+ }
+ return;
+ }
+ writer.Write(0);
+ }
+
+ public void Deserialize(MessageReader reader)
+ {
+ this.PlayerName = reader.ReadString();
+ this.ColorId = reader.ReadByte();
+ this.HatId = reader.ReadPackedUInt32();
+ this.PetId = reader.ReadPackedUInt32();
+ this.SkinId = reader.ReadPackedUInt32();
+ byte b = reader.ReadByte();
+ this.Disconnected = ((b & 1) > 0);
+ this.IsImpostor = ((b & 2) > 0);
+ this.IsDead = ((b & 4) > 0);
+ byte b2 = reader.ReadByte();
+ this.Tasks = new List<GameData.TaskInfo>((int)b2);
+ for (int i = 0; i < (int)b2; i++)
+ {
+ this.Tasks.Add(new GameData.TaskInfo());
+ this.Tasks[i].Deserialize(reader);
+ }
+ }
+
+ public GameData.TaskInfo FindTaskById(uint taskId)
+ {
+ for (int i = 0; i < this.Tasks.Count; i++)
+ {
+ if (this.Tasks[i].Id == taskId)
+ {
+ return this.Tasks[i];
+ }
+ }
+ return null;
+ }
+ }
+
+ private enum RpcCalls
+ {
+ SetTasks
+ }
+
+ public void Awake()
+ {
+ if (GameData.Instance && GameData.Instance != this)
+ {
+ UnityEngine.Object.Destroy(base.gameObject);
+ return;
+ }
+ GameData.Instance = this;
+ if (AmongUsClient.Instance)
+ {
+ AmongUsClient.Instance.DisconnectHandlers.AddUnique(this);
+ }
+ }
+
+ internal void SetDirty()
+ {
+ base.SetDirtyBit(uint.MaxValue);
+ }
+
+ public GameData.PlayerInfo GetHost()
+ {
+ ClientData host = AmongUsClient.Instance.GetHost();
+ if (host != null && host.Character)
+ {
+ return host.Character.Data;
+ }
+ return null;
+ }
+
+ public sbyte GetAvailableId()
+ {
+ sbyte i;
+ sbyte j;
+ for (i = 0; i < 10; i = j + 1)
+ {
+ if (!this.AllPlayers.Any((GameData.PlayerInfo p) => p.PlayerId == (byte)i))
+ {
+ return i;
+ }
+ j = i;
+ }
+ return -1;
+ }
+
+ public GameData.PlayerInfo GetPlayerById(byte id)
+ {
+ if (id == 255)
+ {
+ return null;
+ }
+ for (int i = 0; i < this.AllPlayers.Count; i++)
+ {
+ if (this.AllPlayers[i].PlayerId == id)
+ {
+ return this.AllPlayers[i];
+ }
+ }
+ return null;
+ }
+
+ public void UpdateName(byte playerId, string name)
+ {
+ GameData.PlayerInfo playerById = this.GetPlayerById(playerId);
+ if (playerById != null)
+ {
+ playerById.PlayerName = name;
+ }
+ base.SetDirtyBit(1U << (int)playerId);
+ }
+
+ public void UpdateColor(byte playerId, byte color)
+ {
+ GameData.PlayerInfo playerById = this.GetPlayerById(playerId);
+ if (playerById != null)
+ {
+ playerById.ColorId = color;
+ }
+ base.SetDirtyBit(1U << (int)playerId);
+ }
+
+ public void UpdateHat(byte playerId, uint hat)
+ {
+ GameData.PlayerInfo playerById = this.GetPlayerById(playerId);
+ if (playerById != null)
+ {
+ playerById.HatId = hat;
+ }
+ base.SetDirtyBit(1U << (int)playerId);
+ }
+
+ public void UpdatePet(byte playerId, uint petId)
+ {
+ GameData.PlayerInfo playerById = this.GetPlayerById(playerId);
+ if (playerById != null)
+ {
+ playerById.PetId = petId;
+ }
+ base.SetDirtyBit(1U << (int)playerId);
+ }
+
+ public void UpdateSkin(byte playerId, uint skin)
+ {
+ GameData.PlayerInfo playerById = this.GetPlayerById(playerId);
+ if (playerById != null)
+ {
+ playerById.SkinId = skin;
+ }
+ base.SetDirtyBit(1U << (int)playerId);
+ }
+
+ public void AddPlayer(PlayerControl pc)
+ {
+ GameData.PlayerInfo item = new GameData.PlayerInfo(pc);
+ this.AllPlayers.Add(item);
+ base.SetDirtyBit(1U << (int)pc.PlayerId);
+ }
+
+ public bool RemovePlayer(byte playerId)
+ {
+ for (int i = 0; i < this.AllPlayers.Count; i++)
+ {
+ if (this.AllPlayers[i].PlayerId == playerId)
+ {
+ this.SetDirty();
+ this.AllPlayers.RemoveAt(i);
+ return true;
+ }
+ }
+ return false;
+ }
+
+ public void RecomputeTaskCounts()
+ {
+ this.TotalTasks = 0;
+ this.CompletedTasks = 0;
+ for (int i = 0; i < this.AllPlayers.Count; i++)
+ {
+ GameData.PlayerInfo playerInfo = this.AllPlayers[i];
+ if (!playerInfo.Disconnected && playerInfo.Tasks != null && playerInfo.Object && (PlayerControl.GameOptions.GhostsDoTasks || !playerInfo.IsDead) && !playerInfo.IsImpostor)
+ {
+ for (int j = 0; j < playerInfo.Tasks.Count; j++)
+ {
+ this.TotalTasks++;
+ if (playerInfo.Tasks[j].Complete)
+ {
+ this.CompletedTasks++;
+ }
+ }
+ }
+ }
+ }
+
+ public void TutOnlyRemoveTask(byte playerId, uint taskId)
+ {
+ GameData.PlayerInfo playerById = this.GetPlayerById(playerId);
+ GameData.TaskInfo item = playerById.FindTaskById(taskId);
+ playerById.Tasks.Remove(item);
+ this.RecomputeTaskCounts();
+ }
+
+ public void TutOnlyAddTask(byte playerId, uint taskId)
+ {
+ this.GetPlayerById(playerId).Tasks.Add(new GameData.TaskInfo
+ {
+ Id = taskId
+ });
+ this.TotalTasks++;
+ }
+
+ private void SetTasks(byte playerId, byte[] taskTypeIds)
+ {
+ GameData.PlayerInfo playerById = this.GetPlayerById(playerId);
+ if (playerById == null)
+ {
+ Debug.Log("Could not set tasks for player id: " + playerId);
+ return;
+ }
+ if (playerById.Disconnected)
+ {
+ return;
+ }
+ if (!playerById.Object)
+ {
+ Debug.Log(string.Concat(new object[]
+ {
+ "Could not set tasks for player (",
+ playerById.PlayerName,
+ "): ",
+ playerId
+ }));
+ return;
+ }
+ playerById.Tasks = new List<GameData.TaskInfo>(taskTypeIds.Length);
+ for (int i = 0; i < taskTypeIds.Length; i++)
+ {
+ playerById.Tasks.Add(new GameData.TaskInfo());
+ playerById.Tasks[i].Id = (uint)i;
+ }
+ playerById.Object.SetTasks(taskTypeIds);
+ base.SetDirtyBit(1U << (int)playerById.PlayerId);
+ }
+
+ public void CompleteTask(PlayerControl pc, uint taskId)
+ {
+ GameData.TaskInfo taskInfo = pc.Data.FindTaskById(taskId);
+ if (taskInfo == null)
+ {
+ Debug.LogWarning("Couldn't find task: " + taskId);
+ return;
+ }
+ if (!taskInfo.Complete)
+ {
+ taskInfo.Complete = true;
+ this.CompletedTasks++;
+ return;
+ }
+ Debug.LogWarning("Double complete task: " + taskId);
+ }
+
+ public void HandleDisconnect(PlayerControl player, DisconnectReasons reason)
+ {
+ if (!player)
+ {
+ return;
+ }
+ GameData.PlayerInfo playerById = this.GetPlayerById(player.PlayerId);
+ if (playerById == null)
+ {
+ return;
+ }
+ if (AmongUsClient.Instance.IsGameStarted)
+ {
+ if (!playerById.Disconnected)
+ {
+ playerById.Disconnected = true;
+ TempData.LastDeathReason = DeathReason.Disconnect;
+ this.ShowNotification(playerById.PlayerName, reason);
+ }
+ }
+ else if (this.RemovePlayer(player.PlayerId))
+ {
+ this.ShowNotification(playerById.PlayerName, reason);
+ }
+ this.RecomputeTaskCounts();
+ }
+
+ private void ShowNotification(string playerName, DisconnectReasons reason)
+ {
+ if (string.IsNullOrEmpty(playerName))
+ {
+ return;
+ }
+ if (reason <= DisconnectReasons.Banned)
+ {
+ if (reason == DisconnectReasons.ExitGame)
+ {
+ DestroyableSingleton<HudManager>.Instance.Notifier.AddItem(playerName + " left the game.");
+ return;
+ }
+ if (reason == DisconnectReasons.Banned)
+ {
+ GameData.PlayerInfo data = AmongUsClient.Instance.GetHost().Character.Data;
+ DestroyableSingleton<HudManager>.Instance.Notifier.AddItem(playerName + " was banned by " + data.PlayerName + ".");
+ return;
+ }
+ }
+ else if (reason == DisconnectReasons.Kicked)
+ {
+ GameData.PlayerInfo data2 = AmongUsClient.Instance.GetHost().Character.Data;
+ DestroyableSingleton<HudManager>.Instance.Notifier.AddItem(playerName + " was kicked by " + data2.PlayerName + ".");
+ return;
+ }
+ DestroyableSingleton<HudManager>.Instance.Notifier.AddItem(playerName + " left the game due to error.");
+ }
+
+ public void HandleDisconnect()
+ {
+ if (!AmongUsClient.Instance.IsGameStarted)
+ {
+ for (int i = this.AllPlayers.Count - 1; i >= 0; i--)
+ {
+ if (!this.AllPlayers[i].Object)
+ {
+ this.AllPlayers.RemoveAt(i);
+ }
+ }
+ }
+ }
+
+ public override bool Serialize(MessageWriter writer, bool initialState)
+ {
+ if (initialState)
+ {
+ if (!DestroyableSingleton<Telemetry>.Instance.IsInitialized)
+ {
+ DestroyableSingleton<Telemetry>.Instance.Initialize();
+ }
+ writer.WriteBytesAndSize(DestroyableSingleton<Telemetry>.Instance.CurrentGuid.ToByteArray());
+ writer.WritePacked(this.AllPlayers.Count);
+ for (int i = 0; i < this.AllPlayers.Count; i++)
+ {
+ GameData.PlayerInfo playerInfo = this.AllPlayers[i];
+ writer.Write(playerInfo.PlayerId);
+ playerInfo.Serialize(writer);
+ }
+ }
+ else
+ {
+ int position = writer.Position;
+ byte b = 0;
+ writer.Write(b);
+ for (int j = 0; j < this.AllPlayers.Count; j++)
+ {
+ GameData.PlayerInfo playerInfo2 = this.AllPlayers[j];
+ if ((this.DirtyBits & 1U << (int)playerInfo2.PlayerId) != 0U)
+ {
+ writer.Write(playerInfo2.PlayerId);
+ playerInfo2.Serialize(writer);
+ b += 1;
+ }
+ }
+ writer.Position = position;
+ writer.Write(b);
+ writer.Position = writer.Length;
+ this.DirtyBits = 0U;
+ }
+ return true;
+ }
+
+ public override void Deserialize(MessageReader reader, bool initialState)
+ {
+ if (initialState)
+ {
+ Guid gameGuid = new Guid(reader.ReadBytesAndSize());
+ if (!DestroyableSingleton<Telemetry>.Instance.IsInitialized)
+ {
+ DestroyableSingleton<Telemetry>.Instance.Initialize(gameGuid);
+ }
+ int num = reader.ReadPackedInt32();
+ for (int i = 0; i < num; i++)
+ {
+ GameData.PlayerInfo playerInfo = new GameData.PlayerInfo(reader.ReadByte());
+ playerInfo.Deserialize(reader);
+ this.AllPlayers.Add(playerInfo);
+ }
+ }
+ else
+ {
+ byte b = reader.ReadByte();
+ for (int j = 0; j < (int)b; j++)
+ {
+ byte b2 = reader.ReadByte();
+ GameData.PlayerInfo playerInfo2 = this.GetPlayerById(b2);
+ if (playerInfo2 != null)
+ {
+ playerInfo2.Deserialize(reader);
+ }
+ else
+ {
+ playerInfo2 = new GameData.PlayerInfo(b2);
+ playerInfo2.Deserialize(reader);
+ this.AllPlayers.Add(playerInfo2);
+ }
+ }
+ }
+ this.RecomputeTaskCounts();
+ }
+
+ public void RpcSetTasks(byte playerId, byte[] taskTypeIds)
+ {
+ if (AmongUsClient.Instance.AmClient)
+ {
+ this.SetTasks(playerId, taskTypeIds);
+ }
+ MessageWriter messageWriter = AmongUsClient.Instance.StartRpc(this.NetId, 0, SendOption.Reliable);
+ messageWriter.Write(playerId);
+ messageWriter.WriteBytesAndSize(taskTypeIds);
+ messageWriter.EndMessage();
+ }
+
+ public override void HandleRpc(byte callId, MessageReader reader)
+ {
+ if (callId == 0)
+ {
+ this.SetTasks(reader.ReadByte(), reader.ReadBytesAndSize());
+ }
+ }
+}