SecretPluginLaboratories/GamblingCoin/GamblingCoinEventHandler.cs
2025-06-08 00:54:06 +02:00

243 lines
11 KiB
C#

using LabApi.Events.Arguments.PlayerEvents;
using LabApi.Features.Wrappers;
using MapGeneration;
using Mirror;
using PlayerRoles;
using Respawning;
using UnityEngine;
using MicroHIDItem = InventorySystem.Items.MicroHID.MicroHIDItem;
using Random = UnityEngine.Random;
namespace GamblingCoin;
public class GamblingCoinEventHandler
{
private readonly WeightedRandomExecutor<PlayerFlippedCoinEventArgs> _executor;
public GamblingCoinEventHandler()
{
var configMessages = Plugin.Singleton.ConfigMessages;
var configGameplay = Plugin.Singleton.ConfigGameplay;
var configChances = Plugin.Singleton.ConfigChances;
_executor = new WeightedRandomExecutor<PlayerFlippedCoinEventArgs>();
_executor
.AddAction(_ =>
{
Warhead.DetonationTime += configGameplay.WarheadTimeIncrease;
Warhead.Start(suppressSubtitles: true);
}, configChances.NukeChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.SpawnWaveMessage, configGameplay.BroadcastDuration);
if (GetPlayers().Any(player => player.Role == RoleTypeId.Spectator))
WaveManager.InitiateRespawn(WaveManager.Waves[Random.Range(0, WaveManager.Waves.Count)]);
}, configChances.SpawnWaveChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.ItemSpawnMessage, configGameplay.BroadcastDuration);
SpawnRandomItemAtPlayer(x.Player, configGameplay.Items.CommonItems);
}, configChances.CommonItemChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.UncommonItemSpawnMessage, configGameplay.BroadcastDuration);
SpawnRandomItemAtPlayer(x.Player, configGameplay.Items.UncommonItems);
}, configChances.UncommonItemChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.RareItemSpawnMessage, configGameplay.BroadcastDuration);
SpawnRandomItemAtPlayer(x.Player, configGameplay.Items.RareItems);
}, configChances.RareItemChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.EpicItemSpawnMessage, configGameplay.BroadcastDuration);
SpawnRandomItemAtPlayer(x.Player, configGameplay.Items.EpicItems);
}, configChances.EpicItemChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.LegendaryItemSpawnMessage, configGameplay.BroadcastDuration);
var player = x.Player;
var items = configGameplay.Items.LegendaryItems;
var itemIndex = Random.Range(0, items.Length);
var item = items[itemIndex];
var pickup = Pickup.Create(item, player.Position + new Vector3(0, 1, 0));
if (pickup == null) return;
if (item is ItemType.MicroHID)
{
var host = Player.List.First(player1 => player1.IsHost);
var micro = host.AddItem(pickup)!.Base;
var microItem = (MicroHIDItem)micro;
microItem.EnergyManager.ServerSetEnergy(microItem.ItemId.SerialNumber, 100);
var newPickup = host.DropItem(micro);
newPickup.Position = player.Position + new Vector3(0, 1, 0);
return;
}
pickup.Spawn();
}, configChances.LegendaryItemChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.RandomTeleportMessage, configGameplay.BroadcastDuration);
var randomRoom = Map.GetRandomRoom();
if (randomRoom == null) return;
var isInOtherZone = randomRoom is { Zone: FacilityZone.Other };
var isDetonated = Warhead.IsDetonated;
var isDecontaminating = Decontamination.IsDecontaminating;
var isInDetonatedZone = isDetonated && randomRoom.Zone is FacilityZone.HeavyContainment
or FacilityZone.LightContainment or FacilityZone.Entrance;
var isInDecontaminatedZone = isDecontaminating && randomRoom.Zone is FacilityZone.LightContainment;
while (isInOtherZone || isInDetonatedZone || isInDecontaminatedZone)
{
randomRoom = Map.GetRandomRoom();
if (randomRoom == null) return;
isInOtherZone = randomRoom is { Zone: FacilityZone.Other };
isInDetonatedZone = isDetonated && randomRoom.Zone is FacilityZone.HeavyContainment
or FacilityZone.LightContainment or FacilityZone.Entrance;
isInDecontaminatedZone = isDecontaminating && randomRoom.Zone is FacilityZone.LightContainment;
}
var newPos = randomRoom.Position;
x.Player.Position = newPos + new Vector3(0, configGameplay.TeleportHeightOffset, 0);
;
}, configChances.RandomTeleportChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.StealItemMessage, configGameplay.BroadcastDuration);
if (x.Player.CurrentItem != null) x.Player.DropItem(x.Player.CurrentItem);
}, configChances.StealItemChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.ExplosionMessage, configGameplay.BroadcastDuration);
x.Player.ClearInventory();
TimedGrenadeProjectile.SpawnActive(x.Player.Position, ItemType.GrenadeHE, x.Player);
}, configChances.ExplosionChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.AntiMicroMessage, configGameplay.BroadcastDuration);
GetPlayers().ForEach(p => { p.RemoveItem(ItemType.MicroHID, configGameplay.MaxMicrosToRemove); });
//TODO: remove *all* micros
}, configChances.AntiMicroChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.GrenadeMessage, configGameplay.BroadcastDuration);
TimedGrenadeProjectile.SpawnActive(x.Player.Position, ItemType.GrenadeHE, x.Player, 2);
}, configChances.GrenadeChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.PocketDimensionMessage, configGameplay.BroadcastDuration);
PocketDimension.ForceInside(x.Player);
},
configChances.PocketDimensionChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.AdvancedPositiveEffectMessage, configGameplay.BroadcastDuration);
ApplyRandomEffect(x.Player, configGameplay.Effects.AdvancedPositive);
}, configChances.AdvancedPositiveEffectChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.PositiveEffectMessage, configGameplay.BroadcastDuration);
ApplyRandomEffect(x.Player, configGameplay.Effects.Positive);
}, configChances.PositiveEffectChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.NegativeEffectMessage, configGameplay.BroadcastDuration);
ApplyRandomEffect(x.Player, configGameplay.Effects.Negative);
}, configChances.NegativeEffectChance)
.AddAction(x =>
{
x.Player.SendBroadcast(configMessages.AdvancedNegativeEffectMessage, configGameplay.BroadcastDuration);
ApplyRandomEffect(x.Player, configGameplay.Effects.AdvancedNegative);
}, configChances.AdvancedNegativeEffectChance)
.AddAction(x =>
{
var players = GetPlayers();
var randomPlayer = players[Random.Range(0, GetPlayers().Length)];
while (randomPlayer.RoleBase.Team is Team.Dead or Team.SCPs)
randomPlayer = players[Random.Range(0, GetPlayers().Length)];
x.Player.SendBroadcast(configMessages.SwitchInventoryMessage, configGameplay.BroadcastDuration);
randomPlayer.SendBroadcast(configMessages.SwitchInventoryMessage, configGameplay.BroadcastDuration);
var randomPlayerItems = new List<Item>();
randomPlayer.Items.CopyTo(randomPlayerItems);
var items = x.Player.Items;
randomPlayer.ClearInventory();
foreach (var itemBase in items) randomPlayer.AddItem(itemBase.Type);
x.Player.ClearInventory();
foreach (var randomPlayerItem in randomPlayerItems) x.Player.AddItem(randomPlayerItem.Type);
}, configChances.SwitchInventoryChance)
.AddAction(x => { x.Player.CurrentItem?.DropItem().Destroy(); }, configChances.RemoveCoinChance)
.AddAction(x =>
{
var spectators = Player.List.Where(player => player.Role == RoleTypeId.Spectator).ToArray();
var spectator = spectators[Random.Range(0, spectators.Length)];
spectator.SendBroadcast(configMessages.SpawnZombieMessage, configGameplay.BroadcastDuration);
spectator.SetRole(RoleTypeId.Scp0492);
var spawnRoom = Map.Rooms.First(room => room.Name == RoomName.HczWarhead);
if (Warhead.IsDetonated)
{
spawnRoom = Map.Rooms.First(room => room.Name == RoomName.Outside);
}
spectator.Position = spawnRoom.Position + new Vector3(0, 1, 0);
}, configChances.SpawnZombieChance);
return;
void ApplyRandomEffect(Player player, AdvancedEffectSettings settings)
{
var effectChosen = settings.Effects[Random.Range(0, settings.Effects.Length)];
var effectSettings = settings.Settings[effectChosen];
player.ReferenceHub.playerEffectsController.ChangeState(effectChosen, effectSettings.Intensity,
effectSettings.Duration, effectSettings.AddDuration);
}
void SpawnItemAtPlayer(Player player, ItemType item)
{
var pickup = Pickup.Create(item, player.Position + new Vector3(0, 1, 0));
if (pickup == null) return;
pickup.Spawn();
}
void SpawnRandomItemAtPlayer(Player player, ItemType[] items)
{
var itemIndex = Random.Range(0, items.Length);
SpawnItemAtPlayer(player, items[itemIndex]);
}
Player[] GetPlayers()
{
return Player.ReadyList.ToArray();
}
}
public void OnFlippedCoin(PlayerFlippedCoinEventArgs ev)
{
_executor.Execute(ev);
}
}