RUMBLE does not support other mod managers. If you want to use a manager, you must use the RUMBLE Mod Manager, a manager specifically designed for this game.
Decompiled source of SteamTimelineIntegration v1.0.1
Mods/SteamTimelineIntegration.dll
Decompiled a day agousing System; using System.Diagnostics; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text.RegularExpressions; using HarmonyLib; using Il2CppInterop.Runtime.InteropTypes.Arrays; using Il2CppRUMBLE.Environment.MatchFlow; using Il2CppRUMBLE.Networking.MatchFlow; using Il2CppRUMBLE.Players; using Il2CppRUMBLE.Utilities; using Il2CppSteamworks; using MelonLoader; using Microsoft.CodeAnalysis; using RumbleModUI; using RumbleModdingAPI.RMAPI; using SteamTimelineIntegration; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: MelonInfo(typeof(Core), "SteamTimelineIntegration", "1.0.1", "Dazbii", null)] [assembly: VerifyLoaderVersion(0, 7, 2)] [assembly: MelonGame("Buckethead Entertainment", "RUMBLE")] [assembly: MelonColor(255, 253, 188, 180)] [assembly: MelonAuthorColor(255, 253, 188, 180)] [assembly: AssemblyTitle("SteamTimelineIntegration")] [assembly: AssemblyDescription("Rumble mod to enable integrations with the steam timeline ")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("")] [assembly: AssemblyProduct("SteamTimelineIntegration")] [assembly: AssemblyCopyright("Copyright © 2026")] [assembly: AssemblyTrademark("")] [assembly: ComVisible(false)] [assembly: Guid("621d30a5-8fa1-4d87-9826-92c0149b033e")] [assembly: AssemblyFileVersion("1.0.1")] [assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.1.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } [HarmonyPatch(typeof(PedestalManager), "TeleportPedestalsToOwners")] public static class Pedestal_Patch { public static void Prefix() { Il2CppStructArray<int> roundsWonList = Singleton<MatchHandler>.Instance.RoundsWonList; int currentRound = Singleton<MatchHandler>.Instance.CurrentRound; Melon<Core>.Instance.RoundEnded(Il2CppArrayBase<int>.op_Implicit((Il2CppArrayBase<int>)(object)roundsWonList), currentRound); } } namespace SteamTimelineIntegration { public static class BuildInfo { public const string ModName = "SteamTimelineIntegration"; public const string ModVersion = "1.0.1"; public const string Description = "Rumble mod to enable integrations with the steam timeline "; public const string Author = "Dazbii"; public const string Company = ""; } internal enum Gamemode { Playing = 1, Park, Gym, BetweenMatches } public class Core : MelonMod { private Mod Mod = new Mod(); private ModSetting<bool> incomingDamage; private ModSetting<bool> outgoingDamage; private string opponentName; private PlayerData player; private PlayerData opponent; private int clientRoundWins; private string previousOpponentName; private int cumulativeWins; private int cumulativeClientWins; private int cumulativeLosses; private int cumulativeHostLosses; private TimelineEventHandle_t roundEvent; public override void OnLateInitializeMelon() { ((MelonBase)this).OnLateInitializeMelon(); UI.instance.UI_Initialized += OnUIInit; Actions.onRoundStarted += RoundStarted; Actions.onMatchStarted += MatchStarted; Actions.onMatchEnded += MatchEnded; Actions.onPlayerHealthChanged += PlayerHealthChange; } public void OnUIInit() { //IL_0045: Unknown result type (might be due to invalid IL or missing references) //IL_004a: Unknown result type (might be due to invalid IL or missing references) //IL_0056: Expected O, but got Unknown //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Expected O, but got Unknown //IL_008c: Unknown result type (might be due to invalid IL or missing references) //IL_0096: Expected O, but got Unknown Mod.ModName = "SteamTimelineIntegration"; Mod.ModVersion = "1.0.1"; Mod.SetFolder("SteamTimelineIntegration"); Mod.AddDescription("Description", "", "Rumble mod to enable integrations with the steam timeline ", new Tags { IsSummary = true }); incomingDamage = Mod.AddToList("Incoming", false, 0, "!!WARNING: This will clutter your timeline!!\nIf true, this will set add a marker each time you take damage", new Tags()); outgoingDamage = Mod.AddToList("Outgoing", false, 0, "!!WARNING: This will clutter your timeline!!\nIf true, this will set add a marker each time your opponent takes damage", new Tags()); Mod.GetFromFile(); UI.instance.AddMod(Mod); ((MelonBase)this).LoggerInstance.Msg("Added Mod"); } public override void OnSceneWasLoaded(int buildIndex, string sceneName) { ((MelonMod)this).OnSceneWasLoaded(buildIndex, sceneName); switch (sceneName) { case "Gym": SteamTimeline.SetTimelineGameMode((ETimelineGameMode)3); break; case "Park": SteamTimeline.SetTimelineGameMode((ETimelineGameMode)2); break; case "Map0": case "Map1": SteamTimeline.SetTimelineGameMode((ETimelineGameMode)4); break; } } private void PlayerHealthChange(Player damagedPlayer, int damage) { //IL_006c: Unknown result type (might be due to invalid IL or missing references) bool flag = damagedPlayer == player.Player; if ((flag && (bool)((ModSetting)incomingDamage).Value) || (!flag && (bool)((ModSetting)outgoingDamage).Value)) { SteamTimeline.AddInstantaneousTimelineEvent($"{damage}", "", flag ? "steam_defend" : "steam_attack", 0u, 0f, (ETimelineEventClipPriority)1); } } private void RoundStarted() { //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0057: Unknown result type (might be due to invalid IL or missing references) int value = Singleton<MatchHandler>.Instance.CurrentRound + 1; roundEvent = SteamTimeline.StartRangeTimelineEvent($"Round {value}", "Versus " + opponentName, "steam_pair", 1000u, 0f, (ETimelineEventClipPriority)2); } public void RoundEnded(int[] roundsWonList, int currentRound) { //IL_0066: Unknown result type (might be due to invalid IL or missing references) //IL_00c5: Unknown result type (might be due to invalid IL or missing references) //IL_015a: Unknown result type (might be due to invalid IL or missing references) WinsLosses winsLosses = Util.CalcWinsLosses(roundsWonList, currentRound); if ((!Players.IsHost() && player.HealthPoints > 0) || (Players.IsHost() && player.HealthPoints <= 0)) { clientRoundWins++; if (!Players.IsHost()) { cumulativeClientWins++; } else { cumulativeHostLosses++; } } SteamTimeline.UpdateRangeTimelineEvent(roundEvent, $"Round {currentRound}", "Versus " + opponentName, (player.HealthPoints > 0) ? "steam_crown" : "steam_death", 1000u, (ETimelineEventClipPriority)2); SteamTimeline.EndRangeTimelineEvent(roundEvent, 0f); SteamTimeline.AddInstantaneousTimelineEvent($"Round {currentRound} {((player.HealthPoints > 0) ? "Win" : "Loss")}", "Versus " + opponentName, (player.HealthPoints > 0) ? "steam_crown" : "steam_death", 900u, 0f, (ETimelineEventClipPriority)1); SteamTimeline.SetGamePhaseAttribute("Round Score", $"{winsLosses.wins}/{winsLosses.losses}", 2u); } private void MatchStarted() { opponent = Players.GetEnemyPlayers().First().Data; player = Players.GetLocalPlayer().Data; opponentName = Util.GetPlayerName(opponent); if (opponentName != previousOpponentName) { cumulativeClientWins = 0; cumulativeHostLosses = 0; cumulativeLosses = 0; cumulativeWins = 0; } previousOpponentName = opponentName; clientRoundWins = 0; SteamTimeline.SetTimelineGameMode((ETimelineGameMode)1); SteamTimeline.StartGamePhase(); SteamTimeline.SetGamePhaseID("Match against " + opponentName); SteamTimeline.SetGamePhaseAttribute("Round Score", "0/0", 10u); SteamTimeline.SetGamePhaseAttribute("Opponent", opponentName, 9u); if (Players.IsHost()) { SteamTimeline.SetGamePhaseAttribute("Host/Client", "Host", 10u); } else { SteamTimeline.SetGamePhaseAttribute("Host/Client", "Client", 10u); } } private void MatchEnded() { SteamTimeline.SetTimelineGameMode((ETimelineGameMode)4); if (player.MatchData.MatchPoints >= 2) { SteamTimeline.AddGamePhaseTag("Win", "steam_crown", "Result", 10u); cumulativeWins++; if (clientRoundWins == 2) { cumulativeClientWins -= 2; } } else { SteamTimeline.AddGamePhaseTag("Loss", "steam_death", "Result", 10u); cumulativeLosses++; if (clientRoundWins == 2) { cumulativeHostLosses -= 2; } } SteamTimeline.SetGamePhaseAttribute("Set Score", $"Set: {cumulativeWins}({cumulativeClientWins}) - {cumulativeLosses}({cumulativeHostLosses})", 10u); SteamTimeline.SetGamePhaseAttribute("Client Round Wins", $"Client round wins: {clientRoundWins}", 5u); SteamTimeline.EndGamePhase(); } } internal class WinsLosses { public int wins; public int losses; } internal static class Util { public static WinsLosses CalcWinsLosses(int[] roundsWonList, int currentRound) { WinsLosses winsLosses = new WinsLosses(); for (int i = 0; i <= currentRound; i++) { if (roundsWonList[i] == 1) { winsLosses.wins++; } else { winsLosses.losses++; } } return winsLosses; } public static string GetPlayerName(PlayerData player) { return Regex.Replace(player.GeneralData.PublicUsername, "<.*?>|\\(.*?\\)|[^a-zA-Z0-9_ ]", ""); } } }