@@ -0,0 +1,12 @@ | |||
using System; | |||
namespace Discord | |||
{ | |||
public partial class ActivityManager | |||
{ | |||
public void RegisterCommand() | |||
{ | |||
RegisterCommand(null); | |||
} | |||
} | |||
} |
@@ -0,0 +1,9 @@ | |||
using System; | |||
namespace Discord | |||
{ | |||
static class Constants | |||
{ | |||
public const string DllName = "discord_game_sdk"; | |||
} | |||
} |
@@ -0,0 +1,53 @@ | |||
using System; | |||
using System.Runtime.InteropServices; | |||
#if UNITY_EDITOR || UNITY_STANDALONE | |||
using UnityEngine; | |||
#endif | |||
namespace Discord | |||
{ | |||
public partial struct ImageHandle | |||
{ | |||
static public ImageHandle User(Int64 id) | |||
{ | |||
return User(id, 128); | |||
} | |||
static public ImageHandle User(Int64 id, UInt32 size) | |||
{ | |||
return new ImageHandle | |||
{ | |||
Type = ImageType.User, | |||
Id = id, | |||
Size = size, | |||
}; | |||
} | |||
} | |||
public partial class ImageManager | |||
{ | |||
public void Fetch(ImageHandle handle, FetchHandler callback) | |||
{ | |||
Fetch(handle, false, callback); | |||
} | |||
public byte[] GetData(ImageHandle handle) | |||
{ | |||
var dimensions = GetDimensions(handle); | |||
var data = new byte[dimensions.Width * dimensions.Height * 4]; | |||
GetData(handle, data); | |||
return data; | |||
} | |||
#if UNITY_EDITOR || UNITY_STANDALONE | |||
public Texture2D GetTexture(ImageHandle handle) | |||
{ | |||
var dimensions = GetDimensions(handle); | |||
var texture = new Texture2D((int)dimensions.Width, (int)dimensions.Height, TextureFormat.RGBA32, false, true); | |||
texture.LoadRawTextureData(GetData(handle)); | |||
texture.Apply(); | |||
return texture; | |||
} | |||
#endif | |||
} | |||
} |
@@ -0,0 +1,26 @@ | |||
using System; | |||
using System.Runtime.InteropServices; | |||
using System.Collections.Generic; | |||
using System.Text; | |||
namespace Discord | |||
{ | |||
public partial class LobbyManager | |||
{ | |||
public IEnumerable<User> GetMemberUsers(Int64 lobbyID) | |||
{ | |||
var memberCount = MemberCount(lobbyID); | |||
var members = new List<User>(); | |||
for (var i = 0; i < memberCount; i++) | |||
{ | |||
members.Add(GetMemberUser(lobbyID, GetMemberUserId(lobbyID, i))); | |||
} | |||
return members; | |||
} | |||
public void SendLobbyMessage(Int64 lobbyID, string data, SendLobbyMessageHandler handler) | |||
{ | |||
SendLobbyMessage(lobbyID, Encoding.UTF8.GetBytes(data), handler); | |||
} | |||
} | |||
} |
@@ -0,0 +1,20 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Text; | |||
namespace Discord | |||
{ | |||
public partial class StorageManager | |||
{ | |||
public IEnumerable<FileStat> Files() | |||
{ | |||
var fileCount = Count(); | |||
var files = new List<FileStat>(); | |||
for (var i = 0; i < fileCount; i++) | |||
{ | |||
files.Add(StatAt(i)); | |||
} | |||
return files; | |||
} | |||
} | |||
} |
@@ -0,0 +1,32 @@ | |||
using System; | |||
using System.Runtime.InteropServices; | |||
using System.Collections.Generic; | |||
using System.Text; | |||
namespace Discord | |||
{ | |||
public partial class StoreManager | |||
{ | |||
public IEnumerable<Entitlement> GetEntitlements() | |||
{ | |||
var count = CountEntitlements(); | |||
var entitlements = new List<Entitlement>(); | |||
for (var i = 0; i < count; i++) | |||
{ | |||
entitlements.Add(GetEntitlementAt(i)); | |||
} | |||
return entitlements; | |||
} | |||
public IEnumerable<Sku> GetSkus() | |||
{ | |||
var count = CountSkus(); | |||
var skus = new List<Sku>(); | |||
for (var i = 0; i < count; i++) | |||
{ | |||
skus.Add(GetSkuAt(i)); | |||
} | |||
return skus; | |||
} | |||
} | |||
} |
@@ -0,0 +1,29 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Linq; | |||
using System.Text; | |||
using System.Threading.Tasks; | |||
using GamecraftModdingAPI.Events; | |||
using Svelto.ECS; | |||
using RobocraftX.Common; | |||
namespace GamecraftRPC.Events | |||
{ | |||
class EditPresenceHandler : SimpleEventHandlerEngine | |||
{ | |||
public static readonly string HandlerName = "GamecraftRPCEditPresenceEventHandler"; | |||
//private Discord.Discord discordRPC = null; | |||
public static void OnAdd(Discord.Discord discordRPC) | |||
{ | |||
Plugin.SetDiscordActivity(discordRPC, state: "In-Game", details: $"Editing {GameMode.SaveGameDetails.Name}", start: GamePresenceHandler.GameStart); | |||
} | |||
public EditPresenceHandler(Discord.Discord _discordRPC) : base((db) => { OnAdd(_discordRPC); }, (db) => { }, EventType.BuildSwitchedTo, HandlerName) | |||
{ | |||
//this.discordRPC = _discordRPC; | |||
} | |||
} | |||
} |
@@ -0,0 +1,32 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Linq; | |||
using System.Text; | |||
using System.Threading.Tasks; | |||
using GamecraftModdingAPI.Events; | |||
using Svelto.ECS; | |||
using RobocraftX.Common; | |||
namespace GamecraftRPC.Events | |||
{ | |||
class GamePresenceHandler : SimpleEventHandlerEngine | |||
{ | |||
public static readonly string HandlerName = "GamecraftRPCGamePresenceEventHandler"; | |||
//private Discord.Discord discordRPC = null; | |||
public static int GameStart = 0; | |||
public static void OnAdd(Discord.Discord discordRPC) | |||
{ | |||
GameStart = (int)(DateTime.UtcNow.Subtract(new DateTime(1970, 1, 1))).TotalSeconds; | |||
Plugin.SetDiscordActivity(discordRPC, state: "In-Game", details: $"Editing {GameMode.SaveGameDetails.Name}", start: GameStart); | |||
} | |||
public GamePresenceHandler(Discord.Discord _discordRPC) : base((db) => { OnAdd(_discordRPC); }, (db) => { }, EventType.GameSwitchedTo, HandlerName) | |||
{ | |||
//this.discordRPC = _discordRPC; | |||
} | |||
} | |||
} |
@@ -0,0 +1,28 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Linq; | |||
using System.Text; | |||
using System.Threading.Tasks; | |||
using GamecraftModdingAPI.Events; | |||
using Svelto.ECS; | |||
namespace GamecraftRPC.Events | |||
{ | |||
class MenuPresenceHandler : SimpleEventHandlerEngine | |||
{ | |||
public static readonly string HandlerName = "GamecraftRPCMenuPresenceEventHandler"; | |||
//private Discord.Discord discordRPC = null; | |||
public static void OnAdd(Discord.Discord discordRPC) | |||
{ | |||
Plugin.SetDiscordActivity(discordRPC, state: "On menu screen", details: "", start: (int)(DateTime.UtcNow.Subtract(new DateTime(1970, 1, 1))).TotalSeconds); | |||
} | |||
public MenuPresenceHandler(Discord.Discord _discordRPC) : base((db) => { OnAdd(_discordRPC); }, (db) => { }, EventType.Menu, HandlerName) | |||
{ | |||
//this.discordRPC = _discordRPC; | |||
} | |||
} | |||
} |
@@ -0,0 +1,29 @@ | |||
using System; | |||
using System.Collections.Generic; | |||
using System.Linq; | |||
using System.Text; | |||
using System.Threading.Tasks; | |||
using GamecraftModdingAPI.Events; | |||
using Svelto.ECS; | |||
using RobocraftX.Common; | |||
namespace GamecraftRPC.Events | |||
{ | |||
class SimulatePresenceHandler : SimpleEventHandlerEngine | |||
{ | |||
public static readonly string HandlerName = "GamecraftRPCSimulatePresenceEventHandler"; | |||
//private Discord.Discord discordRPC = null; | |||
public static void OnAdd(Discord.Discord discordRPC) | |||
{ | |||
Plugin.SetDiscordActivity(discordRPC, state: "In-Game", details: $"Playing {GameMode.SaveGameDetails.Name}", start: GamePresenceHandler.GameStart); | |||
} | |||
public SimulatePresenceHandler(Discord.Discord _discordRPC) : base((db) => { OnAdd(_discordRPC); }, (db) => { }, EventType.SimulationSwitchedTo, HandlerName) | |||
{ | |||
//this.discordRPC = _discordRPC; | |||
} | |||
} | |||
} |
@@ -1,4 +1,4 @@ | |||
<Project Sdk="Microsoft.NET.Sdk"> | |||
<Project Sdk="Microsoft.NET.Sdk"> | |||
<PropertyGroup> | |||
<TargetFramework>net472</TargetFramework> | |||
@@ -12,7 +12,6 @@ | |||
<ItemGroup> | |||
<PackageReference Include="Lib.Harmony" Version="1.2.0.1" /> | |||
<PackageReference Include="DiscordRichPresence" Version="1.0.150" /> | |||
</ItemGroup> | |||
<!--Start Dependencies--> | |||
@@ -1,90 +0,0 @@ | |||
using System; | |||
using System.Reflection; | |||
using IllusionPlugin; | |||
// using GamecraftModdingAPI; | |||
using GamecraftModdingAPI.Commands; | |||
using DiscordRPC; | |||
namespace GamecraftRPC | |||
{ | |||
public class MyPlugin : IPlugin // the Illusion Plugin Architecture (IPA) will ignore classes that don't implement IPlugin' | |||
{ | |||
public string Name { get; } = Assembly.GetExecutingAssembly().GetName().Name; | |||
public string Version { get; } = Assembly.GetExecutingAssembly().GetName().Version.ToString(); | |||
private static readonly string CLIENT_ID = "692733325902872619"; | |||
private DiscordRpcClient discordRPC; | |||
// called when Gamecraft shuts down | |||
public void OnApplicationQuit() | |||
{ | |||
// Shutdown this mod | |||
GamecraftModdingAPI.Utility.Logging.LogDebug($"{Name} has shutdown"); | |||
// Shutdown the Gamecraft modding API last | |||
GamecraftModdingAPI.Main.Shutdown(); | |||
} | |||
// called when Gamecraft starts up | |||
public void OnApplicationStart() | |||
{ | |||
// Initialize the Gamecraft modding API first | |||
GamecraftModdingAPI.Main.Init(); | |||
// Initialize this mod | |||
SimpleCustomCommandEngine rpcCommand = new SimpleCustomCommandEngine( | |||
() => { }, // TODO: command action | |||
// also try using CommandLogWarning or CommandLogError instead of CommandLog | |||
"RPC", // command name (used to invoke it in the console) | |||
"DiscordRPC Experimental command" // command description (displayed when help command is executed) | |||
); // this command can also be executed using the Command Computer | |||
// register the command so the modding API knows about it | |||
CommandManager.AddCommand(rpcCommand); | |||
discordRPC = new DiscordRpcClient(CLIENT_ID); | |||
discordRPC.OnReady += (sender, e) => | |||
{ | |||
GamecraftModdingAPI.Utility.Logging.LogDebug($"Received Ready from user {e.User.Username}"); | |||
}; | |||
discordRPC.OnPresenceUpdate += (sender, e) => | |||
{ | |||
GamecraftModdingAPI.Utility.Logging.LogDebug($"Received Update! {e.Presence}"); | |||
}; | |||
discordRPC.Initialize(); | |||
discordRPC.SetPresence(new RichPresence() | |||
{ | |||
Details = "Gamecraft Rich Presence", | |||
State = "Gamecraft RPC test", | |||
Assets = new DiscordRPC.Assets() | |||
{ | |||
LargeImageKey = "image_large", | |||
LargeImageText = "Testing stuff", | |||
SmallImageKey = "image_small" | |||
} | |||
}); | |||
GamecraftModdingAPI.Utility.Logging.LogDebug($"{Name} has started up"); | |||
} | |||
// unused methods | |||
public void OnFixedUpdate() { } // called once per physics update | |||
public void OnLevelWasInitialized(int level) { } // called after a level is initialized | |||
public void OnLevelWasLoaded(int level) { } // called after a level is loaded | |||
public void OnUpdate() // called once per rendered frame (frame update) | |||
{ | |||
if (discordRPC != null ) discordRPC.Invoke(); | |||
} | |||
} | |||
} |
@@ -0,0 +1,102 @@ | |||
using System; | |||
using System.Reflection; | |||
using IllusionPlugin; | |||
using GamecraftModdingAPI.Events; | |||
using GamecraftModdingAPI.Commands; | |||
using Discord; | |||
namespace GamecraftRPC | |||
{ | |||
public class Plugin : IPlugin // the Illusion Plugin Architecture (IPA) will ignore classes that don't implement IPlugin' | |||
{ | |||
public string Name { get; } = Assembly.GetExecutingAssembly().GetName().Name; | |||
public string Version { get; } = Assembly.GetExecutingAssembly().GetName().Version.ToString(); | |||
private static readonly long CLIENT_ID = 692733325902872619; | |||
private Discord.Discord discordRPC; | |||
// called when Gamecraft shuts down | |||
public void OnApplicationQuit() | |||
{ | |||
// Shutdown this mod | |||
GamecraftModdingAPI.Utility.Logging.LogDebug($"{Name} has shutdown"); | |||
// Shutdown the Gamecraft modding API last | |||
GamecraftModdingAPI.Main.Shutdown(); | |||
} | |||
// called when Gamecraft starts up | |||
public void OnApplicationStart() | |||
{ | |||
// Initialize the Gamecraft modding API first | |||
GamecraftModdingAPI.Main.Init(); | |||
// Initialize this mod | |||
discordRPC = new Discord.Discord(CLIENT_ID, (UInt64)Discord.CreateFlags.Default); | |||
SetDiscordActivity(discordRPC, state: "Loading...", details: "Initializing Gamecraft", start: (int)(DateTime.UtcNow.Subtract(new DateTime(1970, 1, 1))).TotalSeconds); | |||
EventManager.AddEventHandler(new Events.GamePresenceHandler(discordRPC)); | |||
EventManager.AddEventHandler(new Events.MenuPresenceHandler(discordRPC)); | |||
EventManager.AddEventHandler(new Events.EditPresenceHandler(discordRPC)); | |||
EventManager.AddEventHandler(new Events.SimulatePresenceHandler(discordRPC)); | |||
SimpleCustomCommandEngine<string> rpcCommand = new SimpleCustomCommandEngine<string>( | |||
(s) => { SetDiscordActivity(discordRPC, state: s); }, // TODO: command action | |||
"SetRichPresence", // command name (used to invoke it in the console) | |||
"Set Discord status (experimental)" // command description (displayed when help command is executed) | |||
); // this command can also be executed using the Command Computer | |||
// register the command so the modding API knows about it | |||
CommandManager.AddCommand(rpcCommand); | |||
GamecraftModdingAPI.Utility.Logging.LogDebug($"{Name} has started up"); | |||
} | |||
// unused methods | |||
public void OnFixedUpdate() { } // called once per physics update | |||
public void OnLevelWasInitialized(int level) { } // called after a level is initialized | |||
public void OnLevelWasLoaded(int level) { } // called after a level is loaded | |||
public void OnUpdate() // called once per rendered frame (frame update) | |||
{ | |||
if (discordRPC != null ) discordRPC.RunCallbacks(); | |||
} | |||
public static void SetDiscordActivity(Discord.Discord discordRPC, string state = null, string details = null, int start = 0, int end = 0, string largeImg = "gamecraft-logo-g", string largeTxt = "Gamecraft", string smallImg = "exmods-logo-xm2", string smallTxt = "Exmods", bool instance = true) | |||
{ | |||
if (discordRPC == null) return; | |||
Activity activity = new Activity | |||
{ | |||
Instance = instance, | |||
}; | |||
if (state != null) activity.State = state; | |||
if (details != null) activity.Details = details; | |||
if (start != 0) activity.Timestamps.Start = start; | |||
if (end != 0) activity.Timestamps.End = end; | |||
if (!string.IsNullOrEmpty(largeImg)) | |||
{ | |||
activity.Assets.LargeImage = largeImg; | |||
activity.Assets.LargeText = largeTxt; | |||
} | |||
if (!string.IsNullOrEmpty(smallImg)) | |||
{ | |||
activity.Assets.SmallImage = smallImg; | |||
activity.Assets.SmallText = smallTxt; | |||
} | |||
discordRPC.GetActivityManager().UpdateActivity(activity, result => | |||
{ | |||
GamecraftModdingAPI.Utility.Logging.MetaLog($"Update Activity Result: {result}"); | |||
}); | |||
} | |||
} | |||
} |