First commit

This commit is contained in:
EnderIce2
2020-10-25 16:19:43 +02:00
parent 9d78d84acb
commit b91db81473
73 changed files with 7634 additions and 0 deletions

View File

@ -0,0 +1,14 @@
using DiscordRPC.Logging;
namespace DiscordRPC.Registry
{
internal interface IUriSchemeCreator
{
/// <summary>
/// Registers the URI scheme. If Steam ID is passed, the application will be launched through steam instead of directly.
/// <para>Additional arguments can be supplied if required.</para>
/// </summary>
/// <param name="register">The register context.</param>
bool RegisterUriScheme(UriSchemeRegister register);
}
}

View File

@ -0,0 +1,54 @@
using DiscordRPC.Logging;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Text;
namespace DiscordRPC.Registry
{
internal class MacUriSchemeCreator : IUriSchemeCreator
{
private ILogger logger;
public MacUriSchemeCreator(ILogger logger)
{
this.logger = logger;
}
public bool RegisterUriScheme(UriSchemeRegister register)
{
//var home = Environment.GetEnvironmentVariable("HOME");
//if (string.IsNullOrEmpty(home)) return; //TODO: Log Error
string exe = register.ExecutablePath;
if (string.IsNullOrEmpty(exe))
{
logger.Error("Failed to register because the application could not be located.");
return false;
}
logger.Trace("Registering Steam Command");
//Prepare the command
string command = exe;
if (register.UsingSteamApp) command = "steam://rungameid/" + register.SteamAppID;
else logger.Warning("This library does not fully support MacOS URI Scheme Registration.");
//get the folder ready
string filepath = "~/Library/Application Support/discord/games";
var directory = Directory.CreateDirectory(filepath);
if (!directory.Exists)
{
logger.Error("Failed to register because {0} does not exist", filepath);
return false;
}
//Write the contents to file
File.WriteAllText(filepath + "/" + register.ApplicationID + ".json", "{ \"command\": \"" + command + "\" }");
logger.Trace("Registered {0}, {1}", filepath + "/" + register.ApplicationID + ".json", command);
return true;
}
}
}

View File

@ -0,0 +1,99 @@
using DiscordRPC.Logging;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Text;
namespace DiscordRPC.Registry
{
internal class UnixUriSchemeCreator : IUriSchemeCreator
{
private ILogger logger;
public UnixUriSchemeCreator(ILogger logger)
{
this.logger = logger;
}
public bool RegisterUriScheme(UriSchemeRegister register)
{
var home = Environment.GetEnvironmentVariable("HOME");
if (string.IsNullOrEmpty(home))
{
logger.Error("Failed to register because the HOME variable was not set.");
return false;
}
string exe = register.ExecutablePath;
if (string.IsNullOrEmpty(exe))
{
logger.Error("Failed to register because the application was not located.");
return false;
}
//Prepare the command
string command = null;
if (register.UsingSteamApp)
{
//A steam command isntead
command = "xdg-open steam://rungameid/" + register.SteamAppID;
}
else
{
//Just a regular discord command
command = exe;
}
//Prepare the file
string desktopFileFormat =
@"[Desktop Entry]
Name=Game {0}
Exec={1} %u
Type=Application
NoDisplay=true
Categories=Discord;Games;
MimeType=x-scheme-handler/discord-{2}";
string file = string.Format(desktopFileFormat, register.ApplicationID, command, register.ApplicationID);
//Prepare the path
string filename = "/discord-" + register.ApplicationID + ".desktop";
string filepath = home + "/.local/share/applications";
var directory = Directory.CreateDirectory(filepath);
if (!directory.Exists)
{
logger.Error("Failed to register because {0} does not exist", filepath);
return false;
}
//Write the file
File.WriteAllText(filepath + filename, file);
//Register the Mime type
if (!RegisterMime(register.ApplicationID))
{
logger.Error("Failed to register because the Mime failed.");
return false;
}
logger.Trace("Registered {0}, {1}, {2}", filepath + filename, file, command);
return true;
}
private bool RegisterMime(string appid)
{
//Format the arguments
string format = "default discord-{0}.desktop x-scheme-handler/discord-{0}";
string arguments = string.Format(format, appid);
//Run the process and wait for response
Process process = Process.Start("xdg-mime", arguments);
process.WaitForExit();
//Return if succesful
return process.ExitCode >= 0;
}
}
}

View File

@ -0,0 +1,89 @@
using DiscordRPC.Logging;
using System;
using System.Diagnostics;
namespace DiscordRPC.Registry
{
internal class UriSchemeRegister
{
/// <summary>
/// The ID of the Discord App to register
/// </summary>
public string ApplicationID { get; set; }
/// <summary>
/// Optional Steam App ID to register. If given a value, then the game will launch through steam instead of Discord.
/// </summary>
public string SteamAppID { get; set; }
/// <summary>
/// Is this register using steam?
/// </summary>
public bool UsingSteamApp { get { return !string.IsNullOrEmpty(SteamAppID) && SteamAppID != ""; } }
/// <summary>
/// The full executable path of the application.
/// </summary>
public string ExecutablePath { get; set; }
private ILogger _logger;
public UriSchemeRegister(ILogger logger, string applicationID, string steamAppID = null, string executable = null)
{
_logger = logger;
ApplicationID = applicationID.Trim();
SteamAppID = steamAppID != null ? steamAppID.Trim() : null;
ExecutablePath = executable ?? GetApplicationLocation();
}
/// <summary>
/// Registers the URI scheme, using the correct creator for the correct platform
/// </summary>
public bool RegisterUriScheme()
{
//Get the creator
IUriSchemeCreator creator = null;
switch(Environment.OSVersion.Platform)
{
case PlatformID.Win32Windows:
case PlatformID.Win32S:
case PlatformID.Win32NT:
case PlatformID.WinCE:
_logger.Trace("Creating Windows Scheme Creator");
creator = new WindowsUriSchemeCreator(_logger);
break;
case PlatformID.Unix:
_logger.Trace("Creating Unix Scheme Creator");
creator = new UnixUriSchemeCreator(_logger);
break;
case PlatformID.MacOSX:
_logger.Trace("Creating MacOSX Scheme Creator");
creator = new MacUriSchemeCreator(_logger);
break;
default:
_logger.Error("Unkown Platform: " + Environment.OSVersion.Platform);
throw new PlatformNotSupportedException("Platform does not support registration.");
}
//Regiser the app
if (creator.RegisterUriScheme(this))
{
_logger.Info("URI scheme registered.");
return true;
}
return false;
}
/// <summary>
/// Gets the FileName for the currently executing application
/// </summary>
/// <returns></returns>
public static string GetApplicationLocation()
{
return Process.GetCurrentProcess().MainModule.FileName;
}
}
}

View File

@ -0,0 +1,87 @@
using DiscordRPC.Logging;
using System;
namespace DiscordRPC.Registry
{
internal class WindowsUriSchemeCreator : IUriSchemeCreator
{
private ILogger logger;
public WindowsUriSchemeCreator(ILogger logger)
{
this.logger = logger;
}
public bool RegisterUriScheme(UriSchemeRegister register)
{
if (Environment.OSVersion.Platform == PlatformID.Unix || Environment.OSVersion.Platform == PlatformID.MacOSX)
{
throw new PlatformNotSupportedException("URI schemes can only be registered on Windows");
}
//Prepare our location
string location = register.ExecutablePath;
if (location == null)
{
logger.Error("Failed to register application because the location was null.");
return false;
}
//Prepare the Scheme, Friendly name, default icon and default command
string scheme = "discord-" + register.ApplicationID;
string friendlyName = "Run game " + register.ApplicationID + " protocol";
string defaultIcon = location;
string command = location;
//We have a steam ID, so attempt to replce the command with a steam command
if (register.UsingSteamApp)
{
//Try to get the steam location. If found, set the command to a run steam instead.
string steam = GetSteamLocation();
if (steam != null)
command = string.Format("\"{0}\" steam://rungameid/{1}", steam, register.SteamAppID);
}
//Okay, now actually register it
CreateUriScheme(scheme, friendlyName, defaultIcon, command);
return true;
}
/// <summary>
/// Creates the actual scheme
/// </summary>
/// <param name="scheme"></param>
/// <param name="friendlyName"></param>
/// <param name="defaultIcon"></param>
/// <param name="command"></param>
private void CreateUriScheme(string scheme, string friendlyName, string defaultIcon, string command)
{
using (var key = Microsoft.Win32.Registry.CurrentUser.CreateSubKey("SOFTWARE\\Classes\\" + scheme))
{
key.SetValue("", "URL:" + friendlyName);
key.SetValue("URL Protocol", "");
using (var iconKey = key.CreateSubKey("DefaultIcon"))
iconKey.SetValue("", defaultIcon);
using (var commandKey = key.CreateSubKey("shell\\open\\command"))
commandKey.SetValue("", command);
}
logger.Trace("Registered {0}, {1}, {2}", scheme, friendlyName, command);
}
/// <summary>
/// Gets the current location of the steam client
/// </summary>
/// <returns></returns>
public string GetSteamLocation()
{
using (var key = Microsoft.Win32.Registry.CurrentUser.OpenSubKey("Software\\Valve\\Steam"))
{
if (key == null) return null;
return key.GetValue("SteamExe") as string;
}
}
}
}