-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge branch 'dev' into dependabot/nuget/dev/Microsoft.Extensions.Dep…
…endencyInjection.Abstractions-8.0.2
- Loading branch information
Showing
18 changed files
with
325 additions
and
8 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
namespace Raffle; | ||
|
||
public interface IRaffleManager { | ||
Raffle? Raffle { get; } | ||
|
||
bool StartRaffle(int buyIn); | ||
bool AreEntriesOpen(); | ||
void SetEntriesOpen(float seconds); | ||
void DrawWinner(); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
namespace Raffle; | ||
|
||
public class Raffle(int buyIn) { | ||
private readonly HashSet<ulong> players = []; | ||
|
||
public int BuyIn => buyIn; | ||
|
||
public int Value => players.Count * buyIn; | ||
|
||
public int TotalPlayers => players.Count; | ||
|
||
public void AddPlayer(ulong player) { players.Add(player); } | ||
|
||
/// <summary> | ||
/// Get the winner of the raffle | ||
/// </summary> | ||
/// <returns>The winner, or null if there are no players</returns> | ||
public ulong? GetWinner() { | ||
if (players.Count == 0) return null; | ||
var random = new Random(); | ||
var winnerIndex = random.Next(players.Count); | ||
// remove the winner from the list of players | ||
var winner = players.ElementAt(winnerIndex); | ||
players.Remove(winner); | ||
return winner; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
<Project Sdk="Microsoft.NET.Sdk"> | ||
|
||
<PropertyGroup> | ||
<TargetFramework>net8.0</TargetFramework> | ||
<ImplicitUsings>enable</ImplicitUsings> | ||
<Nullable>enable</Nullable> | ||
</PropertyGroup> | ||
|
||
<ItemGroup> | ||
<ProjectReference Include="..\src\GangsAPI\GangsAPI.csproj"/> | ||
</ItemGroup> | ||
|
||
</Project> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
using GangsAPI.Extensions; | ||
using Microsoft.Extensions.DependencyInjection; | ||
|
||
namespace Raffle; | ||
|
||
public static class RaffleCollection { | ||
public static void RegisterRaffle(this IServiceCollection provider) { | ||
provider.AddPluginBehavior<IRaffleManager, RaffleManager>(); | ||
provider.AddPluginBehavior<RaffleCommand>(); | ||
provider.AddPluginBehavior<StartRaffleCommand>(); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
using GangsAPI.Data; | ||
using GangsAPI.Data.Command; | ||
using GangsAPI.Services; | ||
using GangsAPI.Services.Commands; | ||
using Microsoft.Extensions.DependencyInjection; | ||
|
||
namespace Raffle; | ||
|
||
public class RaffleCommand(IServiceProvider provider) : ICommand { | ||
private readonly IEcoManager eco = provider.GetRequiredService<IEcoManager>(); | ||
|
||
private readonly IRaffleManager raffle = | ||
provider.GetRequiredService<IRaffleManager>(); | ||
|
||
public string Name => "css_raffle"; | ||
|
||
public async Task<CommandResult> Execute(PlayerWrapper? executor, | ||
CommandInfoWrapper info) { | ||
if (executor == null) return CommandResult.PLAYER_ONLY; | ||
if (info.ArgCount != 1) return CommandResult.PRINT_USAGE; | ||
|
||
if (raffle.Raffle == null) | ||
// no raffle is currently running | ||
return CommandResult.SUCCESS; | ||
|
||
if (!raffle.AreEntriesOpen()) | ||
// entries are closed | ||
return CommandResult.SUCCESS; | ||
|
||
if (await eco.TryPurchase(executor, raffle.Raffle.BuyIn, true, "Raffle Ticket", | ||
true) < 0) | ||
return CommandResult.SUCCESS; | ||
|
||
raffle.Raffle.AddPlayer(executor.Steam); | ||
return CommandResult.SUCCESS; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,105 @@ | ||
using CounterStrikeSharp.API; | ||
using CounterStrikeSharp.API.Core; | ||
using CounterStrikeSharp.API.Core.Attributes.Registration; | ||
using CounterStrikeSharp.API.Modules.Cvars; | ||
using GangsAPI; | ||
using Microsoft.Extensions.Localization; | ||
using Timer = CounterStrikeSharp.API.Modules.Timers.Timer; | ||
|
||
namespace Raffle; | ||
|
||
public class RaffleManager(IStringLocalizer locale) | ||
: IPluginBehavior, IRaffleManager { | ||
public static FakeConVar<float> CV_RAFFLE_CHANCE = | ||
new("cs2_gangs_raffle_chance", "The chance of a raffle starting per round", | ||
0.1f); | ||
|
||
public static FakeConVar<int> CV_RAFFLE_COOLDOWN = | ||
new("cs2_gangs_raffle_cooldown", "Minimum number of rounds between raffles", | ||
2); | ||
|
||
public static FakeConVar<int> CV_RAFFLE_MINIMUM = | ||
new("cs2_gangs_raffle_min", "Minimum amount per player", 2); | ||
|
||
public static FakeConVar<int> CV_RAFFLE_MAXIMUM = | ||
new("cs2_gangs_raffle_max", "Maximum amount per player", 2); | ||
|
||
public static FakeConVar<float> CV_RAFFLE_DURATION = | ||
new("cs2_gangs_raffle_duration", "Time to give playeres to enter raffle", | ||
20); | ||
|
||
private static readonly Random rng = new(); | ||
private int cooldownRounds; | ||
|
||
private Timer? entryTimer; | ||
private BasePlugin? plugin; | ||
|
||
public void Start(BasePlugin? plugin, bool hotReload) { | ||
if (plugin == null) return; | ||
this.plugin = plugin; | ||
} | ||
|
||
public Raffle? Raffle { get; private set; } | ||
|
||
public bool StartRaffle(int buyIn) { | ||
if (Raffle != null || plugin == null) return false; | ||
Raffle = new Raffle(buyIn); | ||
|
||
SetEntriesOpen(CV_RAFFLE_DURATION.Value); | ||
return true; | ||
} | ||
|
||
public bool AreEntriesOpen() { return entryTimer != null; } | ||
|
||
public void SetEntriesOpen(float seconds) { | ||
entryTimer?.Kill(); | ||
if (plugin == null || Raffle == null) return; | ||
Server.PrintToChatAll(locale.Get(MSG.RAFFLE_BEGIN, Raffle?.BuyIn ?? 0)); | ||
|
||
entryTimer = plugin.AddTimer(seconds, () => { | ||
entryTimer = null; | ||
if (Raffle == null) return; | ||
|
||
Server.PrintToChatAll(locale.Get(MSG.RAFFLE_PRE_ANNOUNCE, Raffle.Value, | ||
Raffle.TotalPlayers)); | ||
|
||
plugin.AddTimer(5, DrawWinner); | ||
}); | ||
} | ||
|
||
public void DrawWinner() { | ||
if (Raffle == null || plugin == null) return; | ||
ulong? winner; | ||
do { winner = Raffle.GetWinner(); } while (winner != null | ||
&& Raffle.TotalPlayers > 0); | ||
|
||
if (winner == null) { | ||
Server.PrintToChatAll(locale.Get(MSG.GENERIC_ERROR_INFO, | ||
"Could not find a winner")); | ||
Raffle = null; | ||
return; | ||
} | ||
|
||
var name = Utilities.GetPlayerFromSteamId(winner.Value)?.PlayerName | ||
?? winner.ToString() ?? ""; | ||
|
||
Server.PrintToChatAll(locale.Get(MSG.RAFFLE_WINNER, name, | ||
(1.0f / (Raffle.TotalPlayers + 1)).ToString("P1"))); | ||
Raffle = null; | ||
} | ||
|
||
[GameEventHandler] | ||
public HookResult OnRoundStart(EventRoundStart ev, GameEventInfo info) { | ||
if (RoundUtil.IsWarmup()) return HookResult.Continue; | ||
if (cooldownRounds > 0) { | ||
cooldownRounds--; | ||
return HookResult.Continue; | ||
} | ||
|
||
if (rng.NextDouble() > CV_RAFFLE_CHANCE.Value) return HookResult.Continue; | ||
var amo = rng.Next(CV_RAFFLE_MINIMUM.Value, CV_RAFFLE_MAXIMUM.Value); | ||
StartRaffle(amo); | ||
cooldownRounds = CV_RAFFLE_COOLDOWN.Value; | ||
return HookResult.Continue; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
using CounterStrikeSharp.API; | ||
|
||
namespace Raffle; | ||
|
||
public static class RoundUtil { | ||
public static int GetTimeElapsed() { | ||
var gamerules = ServerExtensions.GetGameRules(); | ||
if (gamerules == null) return 0; | ||
var freezeTime = gamerules.FreezeTime; | ||
return (int)(Server.CurrentTime - gamerules.RoundStartTime - freezeTime); | ||
} | ||
|
||
public static int GetTimeRemaining() { | ||
var gamerules = ServerExtensions.GetGameRules(); | ||
if (gamerules == null) return 0; | ||
return gamerules.RoundTime - GetTimeElapsed(); | ||
} | ||
|
||
public static void SetTimeRemaining(int seconds) { | ||
var gamerules = ServerExtensions.GetGameRules(); | ||
if (gamerules == null) return; | ||
gamerules.RoundTime = GetTimeElapsed() + seconds; | ||
var proxy = ServerExtensions.GetGameRulesProxy(); | ||
if (proxy == null) return; | ||
Utilities.SetStateChanged(proxy, "CCSGameRulesProxy", "m_pGameRules"); | ||
} | ||
|
||
public static void AddTimeRemaining(int time) { | ||
var gamerules = ServerExtensions.GetGameRules(); | ||
if (gamerules == null) return; | ||
gamerules.RoundTime += time; | ||
|
||
var proxy = ServerExtensions.GetGameRulesProxy(); | ||
if (proxy == null) return; | ||
Utilities.SetStateChanged(proxy, "CCSGameRulesProxy", "m_pGameRules"); | ||
} | ||
|
||
public static bool IsWarmup() { | ||
var rules = ServerExtensions.GetGameRules(); | ||
return rules == null || rules.WarmupPeriod; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
using CounterStrikeSharp.API; | ||
using CounterStrikeSharp.API.Core; | ||
|
||
namespace Raffle; | ||
|
||
public static class ServerExtensions { | ||
/// <summary> | ||
/// Get the current CCSGameRules for the server | ||
/// </summary> | ||
/// <returns></returns> | ||
public static CCSGameRules? GetGameRules() { | ||
// From killstr3ak | ||
return Utilities | ||
.FindAllEntitiesByDesignerName<CCSGameRulesProxy>("cs_gamerules") | ||
.First() | ||
.GameRules; | ||
} | ||
|
||
public static CCSGameRulesProxy? GetGameRulesProxy() { | ||
// From killstr3ak | ||
return Utilities | ||
.FindAllEntitiesByDesignerName<CCSGameRulesProxy>("cs_gamerules") | ||
.FirstOrDefault(); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
using GangsAPI.Data; | ||
using GangsAPI.Data.Command; | ||
using GangsAPI.Services.Commands; | ||
using Microsoft.Extensions.DependencyInjection; | ||
|
||
namespace Raffle; | ||
|
||
public class StartRaffleCommand(IServiceProvider provider) : ICommand { | ||
private readonly IRaffleManager raffle = | ||
provider.GetRequiredService<IRaffleManager>(); | ||
|
||
public string Name => "css_startraffle"; | ||
public string[] RequiredFlags => ["@css/root"]; | ||
public string[] Usage => ["", "<amount>"]; | ||
|
||
public Task<CommandResult> Execute(PlayerWrapper? executor, | ||
CommandInfoWrapper info) { | ||
var amo = 100; | ||
if (info.ArgCount == 2) | ||
if (!int.TryParse(info.Args[1], out amo)) | ||
return Task.FromResult(CommandResult.PRINT_USAGE); | ||
|
||
raffle.StartRaffle(amo); | ||
return Task.FromResult(CommandResult.SUCCESS); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.