Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions .github/workflows/nightly.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
name: Build and Publish C# Project
name: Build and Publish C# Project

on:
push:
Expand Down Expand Up @@ -36,13 +36,13 @@ jobs:
${{ runner.os }}-dotnet-

- name: Restore dependencies
run: dotnet restore SharpTimer.csproj
run: dotnet restore SharpTimer-main.sln

- name: Build the project
run: dotnet build --configuration Release SharpTimer.csproj
run: dotnet build --configuration Release SharpTimer-main.sln

- name: Publish the project
run: dotnet publish --configuration Release --output ./publish SharpTimer.csproj
run: dotnet publish --configuration Release --output ./publish src/SharpTimer.csproj

- name: Move files
run: |
Expand Down
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,7 @@ CounterStrikeSharp.API.dll
.vscode/
.vs/
/.idea
/src/SharpTimer.csproj.user
/src/Properties/PublishProfiles/FolderProfile.pubxml
/src/Properties/PublishProfiles/FolderProfile.pubxml.user
/Build
66 changes: 19 additions & 47 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,18 +1,10 @@
<a name="readme-top"></a>
<div align="center">

![GitHub Repo stars](https://img.shields.io/github/stars/Letaryat/poor-sharptimer?style=for-the-badge)
![GitHub all releases](https://img.shields.io/github/downloads/Letaryat/poor-sharptimer/total?style=for-the-badge)
</div>
# SharpTimer
SharpTimer is a "simple" Surf/Bhop/MG/Deathrun/etc. CS2 Timer plugin using CounterStrikeSharp<br>

> [!NOTE]
> The original creator of SharpTimer is [Dea](https://github.com/girlglock), who discontinued support for the project after version 0.2.6. This fork is now maintaned by the community, mainly [rcnoob](https://github.com/rcnoob).


> The original creator of SharpTimer is dea_bb, who discontinued support for the project after version 0.2.6. This fork is now maintaned by the community, mainly [rcnoob](https://github.com/rcnoob).

## **Join Our Discord For Support**

<a href="https://discord.com/invite/SmQXeyMcny"><img src="https://discord.com/api/guilds/1196646791450472488/widget.png?style=banner2"></a>
[**Discord**](https://discord.com/invite/SmQXeyMcny)

<div align="center">
<img src="https://files.catbox.moe/qvawnf.png" alt="" style="margin: 0;">
Expand All @@ -22,11 +14,6 @@
<a href="https://ko-fi.com/rcnoob"><img width="185" src="https://files.catbox.moe/rig9aq.svg" alt="Badge"></a>
</p>


# SharpTimer
SharpTimer is a "simple" Surf/KZ/Bhop/MG/Deathrun/etc. CS2 Timer plugin using CounterStrikeSharp<br>


## Features
<details>
<summary>Timer, speedometer and key input with color customization</summary>
Expand All @@ -51,10 +38,6 @@ SharpTimer is a "simple" Surf/KZ/Bhop/MG/Deathrun/etc. CS2 Timer plugin using Co
<summary>Discord Webhook</summary>
</details>

<details>
<summary>JumpStats</summary>
</details>

<details>
<summary>Map CFGs</summary>
</details>
Expand Down Expand Up @@ -82,15 +65,13 @@ SharpTimer is a "simple" Surf/KZ/Bhop/MG/Deathrun/etc. CS2 Timer plugin using Co
</details>

<details>
<summary>KZ Checkpoint system (disabled by default, check config)</summary>
<summary>Checkpoint system (disabled by default, check config)</summary>
<img src="https://i.imgur.com/USX5i8C.png"><br>
<img src="https://i.imgur.com/kWiHOlz.png"><br>
<img src="https://i.imgur.com/lXwXNN7.png"><br>
<img src="https://i.imgur.com/nyn76Q4.png">
</details>

<p align="right">(<a href="#readme-top"> back to top </a>)</p>

## Dependencies

[**MetaMod**](https://cs2.poggu.me/metamod/installation/)
Expand All @@ -105,15 +86,17 @@ SharpTimer is a "simple" Surf/KZ/Bhop/MG/Deathrun/etc. CS2 Timer plugin using Co

[**Web panel** *(optional but recommended)*](https://github.com/Letaryat/sharptimer-web-panel)

[**SharpTimer-WallLists** *(optional but recommended)*](https://github.com/M-archand/SharpTimer-WallLists)

[**CS2-TeleportAnglesFix** *(optional but recommended)*](https://github.com/M-archand/CS2-TeleportAnglesFix)

[**STFixes** *(optional but recommended)*](https://github.com/rcnoob/STFixes)

[**Flashing HUD Fix** *(optional but recommended)*](https://github.com/M-archand/CS2FlashingHtmlHudFix)
[**CS#-Fixes** *(optional but recommended)*](https://github.com/CharlesBarone/CSSharp-Fixes)

[**SharpTimer-WallLists** *(optional)*](https://github.com/SharpTimer/WallLists)
[**Flashing HUD Fix** *(optional but recommended)*](https://github.com/deabb/CS2FlashingHtmlHudFix)

[**SharpTimer-Trails** *(optional)*](https://github.com/SharpTimer/Trails)
[**Flashing HUD Fix (alt)** *(optional but recommended)*](https://gitlab.com/dea_bb/FlashingXMLHintFix)


## Install
Expand Down Expand Up @@ -142,7 +125,7 @@ SharpTimer is a "simple" Surf/KZ/Bhop/MG/Deathrun/etc. CS2 Timer plugin using Co
- [x] Zones
- [x] Hook common triggers by default
- [x] Manual Zones
- [x] Hook Bonus Zones Triggers (KZ & Surf)
- [x] Hook Bonus Zones Triggers (Surf)
- [x] Player PBs
- [x] Save to Json
- [x] Save to MySQL
Expand All @@ -161,30 +144,19 @@ SharpTimer is a "simple" Surf/KZ/Bhop/MG/Deathrun/etc. CS2 Timer plugin using Co
- [x] Player Server Stats
- [x] Player Map Stats
- [x] Replays
- [x] Jumpstats
- [x] Distance
- [x] Pre
- [x] Max
- [x] Height
- [x] Width
- [ ] Sync
- [ ] Jump Types
- [x] Long Jump
- [x] BunnyHop
- [x] MultiBunnyHop
- [x] Jump Bug
- [ ] Edge Bug
- [ ] Ladder Jump
- [X] Silly Stuff
- [ ] Silly Stuff
- [x] Color customization
- [x] Special Tester Gifs
- [x] Custom Player Gifs
- [x] Dioscord Webhook
- [X] Strafe Sync Bar on HUD
- [ ] Strafe Sync Bar on HUD


## Authors:
[Deana](https://twitter.com/girlglock)
original creator: [DEA_BB](https://twitter.com/dea_bb)

sharptimer team:
[Letaryat](https://github.com/Letaryat)
[rcnoob](https://github.com/rcnoob)

<p align="right">(<a href="#readme-top"> back to top </a>)</p>
[exkludera](https://github.com/exkludera)
[Marchand](https://github.com/M-archand)
22 changes: 17 additions & 5 deletions SharpTimer-main.sln
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,30 @@ Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 17
VisualStudioVersion = 17.5.002.0
MinimumVisualStudioVersion = 10.0.40219.1
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "SharpTimer", "SharpTimer.csproj", "{8E786DDC-5BDE-462A-AC36-BB39D6D1560D}"
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SharpTimerAPI", "SharpTimerAPI\SharpTimerAPI.csproj", "{A950E141-B4D1-4338-9238-A1592AA42E1A}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SharpTimer", "src\SharpTimer.csproj", "{09BD8C5E-A95F-4C42-9090-FD35ECEAF518}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "SharpTimer-Example", "SharpTimerAPI-Example\SharpTimer-Example.csproj", "{FF468BD2-D94C-467F-A6FD-DE4CB4C71D69}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{8E786DDC-5BDE-462A-AC36-BB39D6D1560D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{8E786DDC-5BDE-462A-AC36-BB39D6D1560D}.Debug|Any CPU.Build.0 = Debug|Any CPU
{8E786DDC-5BDE-462A-AC36-BB39D6D1560D}.Release|Any CPU.ActiveCfg = Release|Any CPU
{8E786DDC-5BDE-462A-AC36-BB39D6D1560D}.Release|Any CPU.Build.0 = Release|Any CPU
{A950E141-B4D1-4338-9238-A1592AA42E1A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{A950E141-B4D1-4338-9238-A1592AA42E1A}.Debug|Any CPU.Build.0 = Debug|Any CPU
{A950E141-B4D1-4338-9238-A1592AA42E1A}.Release|Any CPU.ActiveCfg = Release|Any CPU
{A950E141-B4D1-4338-9238-A1592AA42E1A}.Release|Any CPU.Build.0 = Release|Any CPU
{09BD8C5E-A95F-4C42-9090-FD35ECEAF518}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{09BD8C5E-A95F-4C42-9090-FD35ECEAF518}.Debug|Any CPU.Build.0 = Debug|Any CPU
{09BD8C5E-A95F-4C42-9090-FD35ECEAF518}.Release|Any CPU.ActiveCfg = Release|Any CPU
{09BD8C5E-A95F-4C42-9090-FD35ECEAF518}.Release|Any CPU.Build.0 = Release|Any CPU
{FF468BD2-D94C-467F-A6FD-DE4CB4C71D69}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{FF468BD2-D94C-467F-A6FD-DE4CB4C71D69}.Debug|Any CPU.Build.0 = Debug|Any CPU
{FF468BD2-D94C-467F-A6FD-DE4CB4C71D69}.Release|Any CPU.ActiveCfg = Release|Any CPU
{FF468BD2-D94C-467F-A6FD-DE4CB4C71D69}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand Down
119 changes: 119 additions & 0 deletions SharpTimerAPI-Example/SharpTimer-Example.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,119 @@
using CounterStrikeSharp.API;
using CounterStrikeSharp.API.Core;
using CounterStrikeSharp.API.Modules.Commands;
using CounterStrikeSharp.API.Modules.Utils;
using Microsoft.Extensions.Logging;
using SharpTimerAPI;

public class SharpTimer_Example : BasePlugin
{
public override string ModuleName => "SharpTimer API Example";
public override string ModuleVersion => "";
public override string ModuleAuthor => "";

public ISharpTimerEventSender? eventSender { get; set; }
public ISharpTimerManager? timerManager { get; set; }
public ISharpTimerDatabase? databaseManager { get; set; }

public override void Load(bool hotReload)
{
AddCommand("css_SharpTimerAPI_TimerCheck", "", Command_API_TimerCheck);
AddCommand("css_SharpTimerAPI_ToggleTimer", "", Command_API_ToggleTimer);
AddCommand("css_SharpTimerAPI_GetSR", "", Command_API_GetSR);

RegisterEventHandler<EventPlayerDeath>(EventPlayerDeath);
}

public override void Unload(bool hotReload)
{
RemoveCommand("css_SharpTimerAPI_TimerCheck", Command_API_TimerCheck);
RemoveCommand("css_SharpTimerAPI_ToggleTimer", Command_API_ToggleTimer);
RemoveCommand("css_SharpTimerAPI_GetSR", Command_API_GetSR);

DeregisterEventHandler<EventPlayerDeath>(EventPlayerDeath);
}

public override void OnAllPluginsLoaded(bool hotReload)
{
eventSender = ISharpTimerEventSender.Capability.Get();
timerManager = ISharpTimerManager.Capability.Get();
databaseManager = ISharpTimerDatabase.Capability.Get();

if (eventSender == null || timerManager == null || databaseManager == null)
{
Logger.LogError("Error: Could not load SharpTimerAPI! Ensure everything is installed properly.");
return;
}
}

public void Command_API_TimerCheck(CCSPlayerController? player, CommandInfo command)
{
if (player == null)
return;

if (timerManager == null)
{
Logger.LogError("Error: ISharpTimerManager not loaded! Ensure everything is installed properly.");
return;
}

command.ReplyToCommand($" {ChatColors.LightPurple}[SharpTimer-Example] {ChatColors.Grey}Timer: " + (timerManager.IsTimerOn(player) ? $"{ChatColors.Green}ON" : $"{ChatColors.Red}OFF"));
}

public void Command_API_ToggleTimer(CCSPlayerController? player, CommandInfo command)
{
if (player == null)
return;

if (timerManager == null)
{
Logger.LogError("Error: ISharpTimerManager not loaded! Ensure everything is installed properly.");
return;
}

timerManager.ToggleTimer(player);

command.ReplyToCommand($" {ChatColors.LightPurple}[SharpTimer-Example] {ChatColors.Grey}Timer has been toggeled: " + (timerManager.IsTimerOn(player) ? $"{ChatColors.Green}ON" : $"{ChatColors.Red}OFF"));
}

public void Command_API_GetSR(CCSPlayerController? player, CommandInfo command)
{
if (player == null)
return;

if (databaseManager == null)
{
Logger.LogError("Error: ISharpTimerDatabase not loaded! Ensure everything is installed properly.");
return;
}

var record = databaseManager.GetSortedRecordsFromDatabase(1, 0, Server.MapName, 0).Result.FirstOrDefault().Value;

string formattedTime;

TimeSpan timeSpan = TimeSpan.FromSeconds(record.TimerTicks / 64.0);
string milliseconds = $"{record.TimerTicks % 64 * (1000.0 / 64.0):000}";
int totalMinutes = (int)timeSpan.TotalMinutes;

if (totalMinutes >= 60)
formattedTime = $"{totalMinutes / 60:D1}:{totalMinutes % 60:D2}:{timeSpan.Seconds:D2}.{milliseconds}";
else
formattedTime = $"{totalMinutes:D1}:{timeSpan.Seconds:D2}.{milliseconds}";

command.ReplyToCommand($" {ChatColors.LightPurple}[SharpTimer-Example] {ChatColors.Grey}player: {ChatColors.White}{record.PlayerName} {ChatColors.Grey}has the SR on {ChatColors.White}{Server.MapName} {ChatColors.Grey}with time: {ChatColors.White}{formattedTime}");
}


public HookResult EventPlayerDeath(EventPlayerDeath @event, GameEventInfo gameEventInfo)
{
var player = @event.Userid;
if (player == null || player.IsBot)
return HookResult.Continue;

timerManager?.RestartTimer(player);

player.PrintToChat($" {ChatColors.LightPurple}[SharpTimer-Example] {ChatColors.Red}Timer has been reset, because you died :(");

return HookResult.Continue;
}
}
20 changes: 20 additions & 0 deletions SharpTimerAPI-Example/SharpTimer-Example.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net8.0</TargetFramework>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<GenerateDependencyFile>false</GenerateDependencyFile>
<OutputPath>$(ProjectDir)..\Build\plugins\SharpTimer-Example\</OutputPath>
<AppendTargetFrameworkToOutputPath>false</AppendTargetFrameworkToOutputPath>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="CounterStrikeSharp.API" Version="1.0.318" />
<ProjectReference Include="..\SharpTimerAPI\SharpTimerAPI.csproj" />
</ItemGroup>

<Target Name="ExcludeStoreApiFiles" AfterTargets="Build">
<Delete Files="$(OutputPath)SharpTimer-Example.pdb" />
<Delete Files="$(OutputPath)SharpTimerAPI.dll" />
</Target>
</Project>
5 changes: 5 additions & 0 deletions SharpTimerAPI/Events/FinishMapEvent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
using CounterStrikeSharp.API.Core;

namespace SharpTimerAPI.Events;

public record FinishMapEvent(CCSPlayerController? Player, bool IsSr, bool IsPb, int Tier) : ISharpTimerPlayerEvent;
9 changes: 9 additions & 0 deletions SharpTimerAPI/Events/ISharpTimerPlayerEvent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
using CounterStrikeSharp.API.Core;

namespace SharpTimerAPI.Events;
using CounterStrikeSharp;

public interface ISharpTimerPlayerEvent
{
public CCSPlayerController? Player { get;}
}
5 changes: 5 additions & 0 deletions SharpTimerAPI/Events/StartTimerEvent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
using CounterStrikeSharp.API.Core;

namespace SharpTimerAPI.Events;

public record StartTimerEvent(CCSPlayerController? Player) : ISharpTimerPlayerEvent;
20 changes: 20 additions & 0 deletions SharpTimerAPI/ISharpTimerDatabase.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
using CounterStrikeSharp.API.Core.Capabilities;

namespace SharpTimerAPI;

public interface ISharpTimerDatabase
{
public static readonly PluginCapability<ISharpTimerDatabase> Capability = new("sharptimer:database");

public class PlayerRecord
{
public int RecordID { get; set; }
public string? PlayerName { get; set; }
public string? SteamID { get; set; }
public string? MapName { get; set; }
public int TimerTicks { get; set; }
public bool Replay { get; set; }
}
public Task<Dictionary<int, PlayerRecord>> GetSortedRecordsFromDatabase(int limit = 0, int bonusX = 0, string mapName = "", int style = 0);
public Task<List<PlayerRecord>> GetAllSortedRecordsFromDatabase(int limit = 0, int bonusX = 0, int style = 0);
}
Loading