added base UI
This commit is contained in:
parent
81e74ebd86
commit
c4c0ad5837
58 changed files with 3477 additions and 57 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -121,6 +121,7 @@ ClientBin/
|
|||
*.publishsettings
|
||||
packages/*
|
||||
*.config
|
||||
*.glide~
|
||||
|
||||
# RIA/Silverlight projects
|
||||
Generated_Code/
|
||||
|
|
|
@ -20,5 +20,7 @@ namespace Ryujinx.Audio
|
|||
void Stop(int Track);
|
||||
|
||||
PlaybackState GetState(int Track);
|
||||
|
||||
void Close();
|
||||
}
|
||||
}
|
|
@ -360,6 +360,10 @@ namespace Ryujinx.Audio.OpenAL
|
|||
return PlaybackState.Stopped;
|
||||
}
|
||||
|
||||
|
||||
public void Close()
|
||||
{
|
||||
KeepPolling = false;
|
||||
Context.Dispose();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,4 +1,7 @@
|
|||
//TODO: This is only used by Config, it doesn't belong to Core.
|
||||
using System.ComponentModel;
|
||||
using Newtonsoft.Json;
|
||||
using OpenTK.Input;
|
||||
|
||||
namespace Ryujinx.Core.Input
|
||||
{
|
||||
public struct JoyConLeft
|
||||
|
|
|
@ -43,6 +43,16 @@ namespace Ryujinx.Core.Logging
|
|||
EnabledClasses[(int)Class] = Enabled;
|
||||
}
|
||||
|
||||
public bool IsEnabled(LogLevel Level)
|
||||
{
|
||||
return EnabledLevels[(int)Level];
|
||||
}
|
||||
|
||||
public bool IsEnabled(LogClass Class)
|
||||
{
|
||||
return EnabledClasses[(int)Class];
|
||||
}
|
||||
|
||||
internal void PrintDebug(LogClass Class, string Message, [CallerMemberName] string Caller = "")
|
||||
{
|
||||
Print(LogLevel.Debug, Class, GetFormattedMessage(Class, Message, Caller));
|
||||
|
|
|
@ -167,6 +167,19 @@ namespace Ryujinx.Core.OsHle
|
|||
}
|
||||
}
|
||||
|
||||
public void ShutDown()
|
||||
{
|
||||
foreach(var Process in Processes)
|
||||
{
|
||||
Process.Value.StopAllThreadsAsync();
|
||||
Process.Value.Dispose();
|
||||
}
|
||||
Processes.Clear();
|
||||
Ns.OnFinish(EventArgs.Empty);
|
||||
Ns.Gpu.Close();
|
||||
Ns.AudioOut.Close();
|
||||
}
|
||||
|
||||
internal bool TryGetProcess(int ProcessId, out Process Process)
|
||||
{
|
||||
return Processes.TryGetValue(ProcessId, out Process);
|
||||
|
|
|
@ -12,6 +12,10 @@
|
|||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Newtonsoft.Json" Version="11.0.2" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\ChocolArm64\ChocolArm64.csproj" />
|
||||
<ProjectReference Include="..\Ryujinx.Audio\Ryujinx.Audio.csproj" />
|
||||
|
|
|
@ -70,5 +70,10 @@ namespace Ryujinx.Graphics.Gpu
|
|||
Thread.Yield();
|
||||
}
|
||||
}
|
||||
|
||||
public void Close()
|
||||
{
|
||||
KeepRunning = false;
|
||||
}
|
||||
}
|
||||
}
|
25
Ryujinx.UI/Configuration.cs
Normal file
25
Ryujinx.UI/Configuration.cs
Normal file
|
@ -0,0 +1,25 @@
|
|||
using Ryujinx.Core.Input;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using Newtonsoft.Json;
|
||||
using Ryujinx.Core.Logging;
|
||||
|
||||
namespace Ryujinx.UI
|
||||
{
|
||||
public class Configuration
|
||||
{
|
||||
public bool EnableMemoryChecks { get; set; }
|
||||
public bool LoggingEnableInfo { get; set; }
|
||||
public bool LoggingEnableDebug { get; set; }
|
||||
public bool LoggingEnableWarn { get; set; }
|
||||
public bool LoggingEnableError { get; set; }
|
||||
public bool LoggingEnableStub { get; set; }
|
||||
|
||||
public string LoggingFilteredClasses { get; set; }
|
||||
|
||||
public JoyCon EmulatedJoyCon { get; set; }
|
||||
}
|
||||
}
|
BIN
Ryujinx.UI/Dependencies/libbz2-1.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libbz2-1.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libcairo-2.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libcairo-2.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libepoxy-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libepoxy-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libexpat-1.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libexpat-1.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libffi-6.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libffi-6.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libfontconfig-1.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libfontconfig-1.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libfreetype-6.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libfreetype-6.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libgcc_s_seh-1.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libgcc_s_seh-1.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libgdk-3-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libgdk-3-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libgdk_pixbuf-2.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libgdk_pixbuf-2.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libglib-2.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libglib-2.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libgobject-2.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libgobject-2.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libgraphite2.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libgraphite2.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libgthread-2.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libgthread-2.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libgtk-3-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libgtk-3-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libharfbuzz-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libharfbuzz-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libiconv-2.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libiconv-2.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libintl-8.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libintl-8.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libpango-1.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libpango-1.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libpangocairo-1.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libpangocairo-1.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libpangoft2-1.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libpangoft2-1.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libpangowin32-1.0-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libpangowin32-1.0-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libpcre32-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libpcre32-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libpixman-1-0.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libpixman-1-0.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libpng16-16.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libpng16-16.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libstdc++-6.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libstdc++-6.dll
Normal file
Binary file not shown.
BIN
Ryujinx.UI/Dependencies/libwinpthread-1.dll
Normal file
BIN
Ryujinx.UI/Dependencies/libwinpthread-1.dll
Normal file
Binary file not shown.
70
Ryujinx.UI/EmulationController.cs
Normal file
70
Ryujinx.UI/EmulationController.cs
Normal file
|
@ -0,0 +1,70 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using Ryujinx.Graphics.Gal;
|
||||
|
||||
namespace Ryujinx.Core
|
||||
{
|
||||
public class EmutionController
|
||||
{
|
||||
private Thread EmulationThread;
|
||||
private Switch Ns;
|
||||
private IGalRenderer Renderer;
|
||||
private bool IsPaused = false;
|
||||
|
||||
public EmutionController(Switch Ns, IGalRenderer Renderer)
|
||||
{
|
||||
this.Ns = Ns;
|
||||
this.Renderer = Renderer;
|
||||
}
|
||||
|
||||
public void Start()
|
||||
{
|
||||
EmulationThread = new Thread(new ThreadStart(() =>
|
||||
{
|
||||
using (GLScreen Screen = new GLScreen(Ns, Renderer))
|
||||
{
|
||||
Ns.Finish += (Sender, Args) =>
|
||||
{
|
||||
Screen?.Exit();
|
||||
};
|
||||
|
||||
Screen.Closed += (Sender, Args) =>
|
||||
{
|
||||
Stop();
|
||||
};
|
||||
|
||||
Screen.Run(60.0);
|
||||
}
|
||||
}));
|
||||
|
||||
EmulationThread.Start();
|
||||
}
|
||||
|
||||
public void Stop()
|
||||
{
|
||||
IsPaused = false;
|
||||
Ns.Os.ShutDown();
|
||||
}
|
||||
|
||||
public async void Pause()
|
||||
{
|
||||
IsPaused = true;
|
||||
lock (Ns)
|
||||
{
|
||||
while (IsPaused)
|
||||
{
|
||||
Thread.Sleep(1000);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void Continue()
|
||||
{
|
||||
IsPaused = false;
|
||||
}
|
||||
}
|
||||
}
|
237
Ryujinx.UI/MainWindow.cs
Normal file
237
Ryujinx.UI/MainWindow.cs
Normal file
|
@ -0,0 +1,237 @@
|
|||
using System;
|
||||
using System.Threading.Tasks;
|
||||
using Gtk;
|
||||
using GUI = Gtk.Builder.ObjectAttribute;
|
||||
using Ryujinx.Audio;
|
||||
using Ryujinx.Audio.OpenAL;
|
||||
using Ryujinx.Core;
|
||||
using System.Threading;
|
||||
using Ryujinx.Graphics.Gal;
|
||||
using Ryujinx.Graphics.Gal.OpenGL;
|
||||
using System.IO;
|
||||
using System.Reflection;
|
||||
using Ryujinx.Core.Logging;
|
||||
|
||||
namespace Ryujinx.UI
|
||||
{
|
||||
class MainWindow : Window
|
||||
{
|
||||
//UI Controls
|
||||
[GUI] MenuItem LoadFileMenuItem;
|
||||
[GUI] MenuItem LoadFolderMenuItem;
|
||||
[GUI] MenuItem ExitMenuItem;
|
||||
[GUI] MenuItem OptionMenuItem;
|
||||
[GUI] MenuItem ShowDebugMenuItem;
|
||||
[GUI] MenuItem ContinueMenuItem;
|
||||
[GUI] MenuItem PauseMenuItem;
|
||||
[GUI] MenuItem StopMenuItem;
|
||||
[GUI] MenuItem AboutMenuItem;
|
||||
|
||||
bool DebugWindowActive = false;
|
||||
|
||||
Core.Switch Ns;
|
||||
|
||||
IAalOutput AudioOut = new OpenALAudioOut();
|
||||
|
||||
IGalRenderer Renderer;
|
||||
|
||||
EmutionController EmulationController;
|
||||
|
||||
public MainWindow() : this(new Builder("MainWindow.glade")) { }
|
||||
|
||||
private MainWindow(Builder builder) : base(builder.GetObject("MainWindow").Handle)
|
||||
{
|
||||
builder.Autoconnect(this);
|
||||
|
||||
//Load Icon
|
||||
using (Stream stream = Assembly.GetExecutingAssembly().GetManifestResourceStream("Ryujinx.UI.ryujinxicon.png"))
|
||||
using (StreamReader reader = new StreamReader(stream))
|
||||
{
|
||||
Icon = new Gdk.Pixbuf(stream);
|
||||
}
|
||||
|
||||
InitializeSwitch();
|
||||
|
||||
//Register Events
|
||||
DeleteEvent += Window_DeleteEvent;
|
||||
LoadFileMenuItem.Activated += LoadFileMenuItem_Activated;
|
||||
LoadFolderMenuItem.Activated += LoadFolderMenuItem_Activated;
|
||||
ExitMenuItem.Activated += ExitMenuItem_Activated;
|
||||
OptionMenuItem.Activated += OptionMenuItem_Activated;
|
||||
ShowDebugMenuItem.Activated += ShowDebugMenuItem_Activated;
|
||||
ContinueMenuItem.Activated += ContinueMenuItem_Activated;
|
||||
PauseMenuItem.Activated += PauseMenuItem_Activated;
|
||||
StopMenuItem.Activated += StopMenuItem_Activated;
|
||||
AboutMenuItem.Activated += AboutMenuItem_Activated;
|
||||
|
||||
PauseMenuItem.Sensitive = false;
|
||||
ContinueMenuItem.Sensitive = false;
|
||||
StopMenuItem.Sensitive = false;
|
||||
|
||||
//Initialize Ryujinx
|
||||
Console.Title = "Ryujinx Console";
|
||||
}
|
||||
|
||||
private void AboutMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
AboutDialog AboutDialog = new AboutDialog
|
||||
{
|
||||
Title = "Ryujinx",
|
||||
Logo = Icon,
|
||||
Comments = "This is a free switch emulator",
|
||||
Copyright = "2018 - Ryujinx Team"
|
||||
};
|
||||
|
||||
AboutDialog.Run();
|
||||
AboutDialog.Destroy();
|
||||
}
|
||||
|
||||
private void LoadFolderMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
FileChooserDialog ContentLoader = new FileChooserDialog("Open Game Folder", this, FileChooserAction.SelectFolder,
|
||||
"Cancel", Gtk.ResponseType.Cancel,
|
||||
"Open", Gtk.ResponseType.Accept
|
||||
);
|
||||
if (ContentLoader.Run() == (int)Gtk.ResponseType.Accept)
|
||||
{
|
||||
if (Directory.Exists(ContentLoader.Filename))
|
||||
{
|
||||
InitializeSwitch();
|
||||
|
||||
string FolderName = ContentLoader.Filename;
|
||||
|
||||
ContentLoader.Destroy();
|
||||
|
||||
string[] RomFsFiles = Directory.GetFiles(FolderName, "*.istorage");
|
||||
|
||||
if (RomFsFiles.Length == 0)
|
||||
{
|
||||
RomFsFiles = Directory.GetFiles(FolderName, "*.romfs");
|
||||
}
|
||||
|
||||
if (RomFsFiles.Length > 0)
|
||||
{
|
||||
Console.WriteLine("Loading as cart with RomFS.");
|
||||
|
||||
Ns.LoadCart(FolderName, RomFsFiles[0]);
|
||||
}
|
||||
else
|
||||
{
|
||||
Console.WriteLine("Loading as cart WITHOUT RomFS.");
|
||||
|
||||
Ns.LoadCart(FolderName);
|
||||
}
|
||||
|
||||
Start();
|
||||
}
|
||||
}
|
||||
else
|
||||
ContentLoader.Destroy();
|
||||
}
|
||||
|
||||
void InitializeSwitch()
|
||||
{
|
||||
Renderer = new OpenGLRenderer();
|
||||
|
||||
IAalOutput AudioOut = new OpenALAudioOut();
|
||||
|
||||
Ns = new Core.Switch(Renderer, AudioOut);
|
||||
|
||||
Settings.Read(Ns.Log);
|
||||
}
|
||||
|
||||
private void StopMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
EmulationController?.Stop();
|
||||
PauseMenuItem.Sensitive = false;
|
||||
ContinueMenuItem.Sensitive = false;
|
||||
StopMenuItem.Sensitive = false;
|
||||
EmulationController = null;
|
||||
}
|
||||
|
||||
private void PauseMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
new Thread(()=>EmulationController?.Pause()).Start();
|
||||
PauseMenuItem.Sensitive = false;
|
||||
ContinueMenuItem.Sensitive = true;
|
||||
StopMenuItem.Sensitive = true;
|
||||
}
|
||||
|
||||
private void ContinueMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
EmulationController?.Continue();
|
||||
PauseMenuItem.Sensitive = true;
|
||||
ContinueMenuItem.Sensitive = false;
|
||||
StopMenuItem.Sensitive = true;
|
||||
}
|
||||
|
||||
private void ShowDebugMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
UI.Debugging.Debugger debugger = new UI.Debugging.Debugger();
|
||||
debugger.DeleteEvent += Debugger_DeleteEvent;
|
||||
DebugWindowActive = true;
|
||||
debugger.Show();
|
||||
}
|
||||
|
||||
private void Debugger_DeleteEvent(object o, DeleteEventArgs args)
|
||||
{
|
||||
DebugWindowActive = false;
|
||||
}
|
||||
|
||||
private void OptionMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
UI.ConfigurationWindow configurationWindow = new UI.ConfigurationWindow(Ns.Log);
|
||||
|
||||
if (configurationWindow.Run() == (int)ResponseType.Accept)
|
||||
{
|
||||
Settings.Write(Ns.Log);
|
||||
}
|
||||
else
|
||||
Settings.Read(Ns.Log);
|
||||
|
||||
configurationWindow.Destroy();
|
||||
}
|
||||
|
||||
private void ExitMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
Environment.Exit(0);
|
||||
}
|
||||
|
||||
private void LoadFileMenuItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
FileChooserDialog ContentLoader = new FileChooserDialog("Open Package", this, FileChooserAction.Open,
|
||||
"Cancel", Gtk.ResponseType.Cancel,
|
||||
"Open", Gtk.ResponseType.Accept
|
||||
);
|
||||
if (ContentLoader.Run() == (int)Gtk.ResponseType.Accept)
|
||||
{
|
||||
if (File.Exists(ContentLoader.Filename))
|
||||
{
|
||||
InitializeSwitch();
|
||||
|
||||
Ns.LoadProgram(ContentLoader.Filename);
|
||||
|
||||
ContentLoader.Destroy();
|
||||
Start();
|
||||
}
|
||||
}
|
||||
else
|
||||
ContentLoader.Destroy();
|
||||
}
|
||||
|
||||
private void Window_DeleteEvent(object sender, DeleteEventArgs a)
|
||||
{
|
||||
EmulationController?.Stop();
|
||||
Environment.Exit(0);
|
||||
}
|
||||
|
||||
void Start()
|
||||
{
|
||||
EmulationController = new EmutionController(Ns, Renderer);
|
||||
EmulationController.Start();
|
||||
PauseMenuItem.Sensitive = true;
|
||||
ContinueMenuItem.Sensitive = false;
|
||||
StopMenuItem.Sensitive = true;
|
||||
}
|
||||
}
|
||||
}
|
35
Ryujinx.UI/Program.cs
Normal file
35
Ryujinx.UI/Program.cs
Normal file
|
@ -0,0 +1,35 @@
|
|||
using Gtk;
|
||||
using System;
|
||||
using System.Reflection;
|
||||
using System.Linq;
|
||||
using Ryujinx.Core;
|
||||
using Ryujinx.Core.Logging;
|
||||
|
||||
namespace Ryujinx.UI
|
||||
{
|
||||
class Program
|
||||
{
|
||||
[STAThread]
|
||||
public static void Main(string[] args)
|
||||
{
|
||||
Application.Init();
|
||||
|
||||
Console.Title = "Ryujinx Console";
|
||||
|
||||
if (Environment.OSVersion.Platform == PlatformID.Win32NT)
|
||||
AppDomain.CurrentDomain.AppendPrivatePath(@"Dependencies\");
|
||||
|
||||
Console.SetOut(UI.Debugging.LogPage.LogWriter);
|
||||
|
||||
var resourceNames = Assembly.GetExecutingAssembly().GetManifestResourceNames();
|
||||
var app = new Application("org.Ryujinx.UI.Ryujinx.UI", GLib.ApplicationFlags.None);
|
||||
app.Register(GLib.Cancellable.Current);
|
||||
|
||||
var win = new MainWindow();
|
||||
app.AddWindow(win);
|
||||
|
||||
win.Show();
|
||||
Application.Run();
|
||||
}
|
||||
}
|
||||
}
|
131
Ryujinx.UI/Ryujinx.UI.csproj
Normal file
131
Ryujinx.UI/Ryujinx.UI.csproj
Normal file
|
@ -0,0 +1,131 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<OutputType>WinExe</OutputType>
|
||||
<TargetFramework>netcoreapp2.0</TargetFramework>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Remove="**\*.glade" />
|
||||
<EmbeddedResource Include="**\*.glade">
|
||||
<LogicalName>%(Filename)%(Extension)</LogicalName>
|
||||
</EmbeddedResource>
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Remove="ryujinxicon.png" />
|
||||
<None Remove="UI\style.css" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<EmbeddedResource Include="ryujinxicon.png" />
|
||||
<EmbeddedResource Include="UI\style.css">
|
||||
<CopyToOutputDirectory>Never</CopyToOutputDirectory>
|
||||
</EmbeddedResource>
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="GtkSharp" Version="3.22.24.36" />
|
||||
<PackageReference Include="Newtonsoft.Json" Version="11.0.2" />
|
||||
<PackageReference Include="OpenTK.NETCore" Version="1.1.2749.6433" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\ChocolArm64\ChocolArm64.csproj" />
|
||||
<ProjectReference Include="..\Ryujinx.Audio\Ryujinx.Audio.csproj" />
|
||||
<ProjectReference Include="..\Ryujinx.Core\Ryujinx.Core.csproj" />
|
||||
<ProjectReference Include="..\Ryujinx.Graphics\Ryujinx.Graphics.csproj" />
|
||||
<ProjectReference Include="..\Ryujinx\Ryujinx.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<EmbeddedResource Update="UI\GeneralPage.glade">
|
||||
<LogicalName>%(Filename)%(Extension)</LogicalName>
|
||||
</EmbeddedResource>
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Update="Dependencies\libbz2-1.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libcairo-2.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libepoxy-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libexpat-1.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libffi-6.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libfontconfig-1.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libfreetype-6.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libgcc_s_seh-1.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libgdk-3-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libgdk_pixbuf-2.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libglib-2.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libgobject-2.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libgraphite2.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libgthread-2.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libgtk-3-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libharfbuzz-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libiconv-2.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libintl-8.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libpango-1.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libpangocairo-1.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libpangoft2-1.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libpangowin32-1.0-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libpcre32-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libpixman-1-0.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libpng16-16.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libstdc++-6.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Update="Dependencies\libwinpthread-1.dll">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
164
Ryujinx.UI/Settings.cs
Normal file
164
Ryujinx.UI/Settings.cs
Normal file
|
@ -0,0 +1,164 @@
|
|||
using System;
|
||||
using System.Reflection;
|
||||
using System.IO;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using Ryujinx.Core;
|
||||
using Ryujinx.Core.Input;
|
||||
using Newtonsoft.Json;
|
||||
using Ryujinx.Core.Logging;
|
||||
|
||||
namespace Ryujinx.UI
|
||||
{
|
||||
public static class Settings
|
||||
{
|
||||
private static string ConfigPath;
|
||||
|
||||
static Settings()
|
||||
{
|
||||
var IniFolder = Path.GetDirectoryName(Assembly.GetEntryAssembly().Location);
|
||||
ConfigPath = Path.Combine(IniFolder, "RyujinxUI.json");
|
||||
}
|
||||
|
||||
public static void Read(Logger Log)
|
||||
{
|
||||
JsonParser JsonParser = new JsonParser(ConfigPath);
|
||||
var Configuration = JsonParser.Load();
|
||||
|
||||
Config.FakeJoyCon = Configuration.EmulatedJoyCon;
|
||||
|
||||
AOptimizations.DisableMemoryChecks = !Configuration.EnableMemoryChecks;
|
||||
|
||||
Log.SetEnable(LogLevel.Info, Configuration.LoggingEnableInfo);
|
||||
Log.SetEnable(LogLevel.Debug, Configuration.LoggingEnableDebug);
|
||||
Log.SetEnable(LogLevel.Error, Configuration.LoggingEnableError);
|
||||
Log.SetEnable(LogLevel.Warning, Configuration.LoggingEnableWarn);
|
||||
Log.SetEnable(LogLevel.Stub, Configuration.LoggingEnableStub);
|
||||
|
||||
Configuration.LoggingFilteredClasses = Configuration.LoggingFilteredClasses != null ?
|
||||
Configuration.LoggingFilteredClasses : string.Empty;
|
||||
string[] FilteredLogClasses = Configuration.LoggingFilteredClasses.Split('\n');
|
||||
|
||||
//When the classes are specified on the list, we only
|
||||
//enable the classes that are on the list.
|
||||
//So, first disable everything, then enable
|
||||
//the classes that the user added to the list.
|
||||
if (FilteredLogClasses.Length > 0)
|
||||
{
|
||||
foreach (LogClass Class in Enum.GetValues(typeof(LogClass)))
|
||||
{
|
||||
Log.SetEnable(Class, false);
|
||||
}
|
||||
}
|
||||
|
||||
foreach (string LogClass in FilteredLogClasses)
|
||||
{
|
||||
if (!string.IsNullOrEmpty(LogClass.Trim()))
|
||||
{
|
||||
foreach (LogClass Class in Enum.GetValues(typeof(LogClass)))
|
||||
{
|
||||
if (Class.ToString().ToLower().Contains(LogClass.Trim().ToLower()))
|
||||
{
|
||||
Log.SetEnable(Class, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void Write(Logger Logger)
|
||||
{
|
||||
Configuration Configuration = new Configuration
|
||||
{
|
||||
EmulatedJoyCon = Config.FakeJoyCon,
|
||||
EnableMemoryChecks = !AOptimizations.DisableMemoryChecks,
|
||||
LoggingEnableDebug = (bool)Logger?.IsEnabled(LogLevel.Debug),
|
||||
LoggingEnableInfo = (bool)Logger?.IsEnabled(LogLevel.Info),
|
||||
LoggingEnableWarn = (bool)Logger?.IsEnabled(LogLevel.Warning),
|
||||
LoggingEnableError = (bool)Logger?.IsEnabled(LogLevel.Error),
|
||||
LoggingEnableStub = (bool)Logger?.IsEnabled(LogLevel.Stub)
|
||||
};
|
||||
|
||||
lock (ConfigPath)
|
||||
{
|
||||
JsonParser JsonParser = new JsonParser(ConfigPath);
|
||||
JsonParser.Save(Configuration);
|
||||
}
|
||||
}
|
||||
|
||||
public static void LoadDefault()
|
||||
{
|
||||
Configuration configuration = new Configuration();
|
||||
Config.FakeJoyCon = new JoyCon();
|
||||
var Joycon = configuration.EmulatedJoyCon;
|
||||
|
||||
Joycon.Left.StickUp = (int)OpenTK.Input.Key.W;
|
||||
Joycon.Left.StickDown = (int)OpenTK.Input.Key.S;
|
||||
Joycon.Left.StickLeft = (int)OpenTK.Input.Key.A;
|
||||
Joycon.Left.StickRight = (int)OpenTK.Input.Key.D;
|
||||
Joycon.Left.StickButton = (int)OpenTK.Input.Key.F;
|
||||
Joycon.Left.DPadUp = (int)OpenTK.Input.Key.Up;
|
||||
Joycon.Left.DPadDown = (int)OpenTK.Input.Key.Down;
|
||||
Joycon.Left.DPadLeft = (int)OpenTK.Input.Key.Left;
|
||||
Joycon.Left.DPadRight = (int)OpenTK.Input.Key.Right;
|
||||
Joycon.Left.ButtonMinus = (int)OpenTK.Input.Key.Minus;
|
||||
Joycon.Left.ButtonL = (int)OpenTK.Input.Key.E;
|
||||
Joycon.Left.ButtonZL = (int)OpenTK.Input.Key.Q;
|
||||
Joycon.Right.StickUp = (int)OpenTK.Input.Key.I;
|
||||
Joycon.Right.StickDown = (int)OpenTK.Input.Key.K;
|
||||
Joycon.Right.StickLeft = (int)OpenTK.Input.Key.J;
|
||||
Joycon.Right.StickRight = (int)OpenTK.Input.Key.L;
|
||||
Joycon.Right.StickButton = (int)OpenTK.Input.Key.H;
|
||||
Joycon.Right.ButtonA = (int)OpenTK.Input.Key.Z;
|
||||
Joycon.Right.ButtonB = (int)OpenTK.Input.Key.X;
|
||||
Joycon.Right.ButtonX = (int)OpenTK.Input.Key.C;
|
||||
Joycon.Right.ButtonY = (int)OpenTK.Input.Key.V;
|
||||
Joycon.Right.ButtonPlus = (int)OpenTK.Input.Key.Plus;
|
||||
Joycon.Right.ButtonR = (int)OpenTK.Input.Key.U;
|
||||
Joycon.Right.ButtonZR = (int)OpenTK.Input.Key.O;
|
||||
|
||||
Config.FakeJoyCon = Joycon;
|
||||
|
||||
Write(null);
|
||||
}
|
||||
}
|
||||
|
||||
public class JsonParser
|
||||
{
|
||||
private string ConfigPath;
|
||||
|
||||
public JsonParser(string Path)
|
||||
{
|
||||
ConfigPath = Path;
|
||||
if (!File.Exists(ConfigPath))
|
||||
{
|
||||
File.CreateText(ConfigPath).Close();
|
||||
Settings.LoadDefault();
|
||||
}
|
||||
}
|
||||
|
||||
private string Serialize<T>(T obj)
|
||||
{
|
||||
return JsonConvert.SerializeObject(obj, typeof(T),Formatting.Indented ,null);
|
||||
}
|
||||
|
||||
private T Deserialize<T>(string serialized_string)
|
||||
{
|
||||
return (T)JsonConvert.DeserializeObject<T>(serialized_string);
|
||||
}
|
||||
|
||||
public void Save(Configuration Configuration)
|
||||
{
|
||||
string SerializeText = Serialize(Configuration);
|
||||
File.WriteAllText(ConfigPath, SerializeText);
|
||||
}
|
||||
|
||||
public Configuration Load()
|
||||
{
|
||||
if (!File.Exists(ConfigPath))
|
||||
File.Create(ConfigPath).Close();
|
||||
string Config = File.ReadAllText(ConfigPath);
|
||||
return Deserialize<Configuration>(Config);
|
||||
}
|
||||
}
|
||||
}
|
56
Ryujinx.UI/UI/ConfigurationWindow.cs
Normal file
56
Ryujinx.UI/UI/ConfigurationWindow.cs
Normal file
|
@ -0,0 +1,56 @@
|
|||
using Gtk;
|
||||
using System;
|
||||
using System.Reflection;
|
||||
using Ryujinx.Core.Logging;
|
||||
using GUI = Gtk.Builder.ObjectAttribute;
|
||||
|
||||
namespace Ryujinx.UI.UI
|
||||
{
|
||||
public class ConfigurationWindow : Dialog
|
||||
{
|
||||
Logger Log;
|
||||
[GUI] Notebook OptionNotebook;
|
||||
[GUI] Button OptionAcceptButton;
|
||||
[GUI] Button OptionCancelButton;
|
||||
|
||||
public ConfigurationWindow(Logger Log) : this(new Builder("ConfigurationWindow.glade"))
|
||||
{
|
||||
this.Log = Log;
|
||||
}
|
||||
|
||||
private ConfigurationWindow(Builder builder) : base(builder.GetObject("ConfigurationWindow").Handle)
|
||||
{
|
||||
builder.Autoconnect(this);
|
||||
|
||||
//Saves current configuration
|
||||
Settings.Write(Log);
|
||||
|
||||
//Loads Parser
|
||||
var iniFolder = System.IO.Path.GetDirectoryName(Assembly.GetEntryAssembly().Location);
|
||||
var iniPath = System.IO.Path.Combine(iniFolder, "Ryujinx.conf");
|
||||
|
||||
//Add pages
|
||||
Label GeneralLabel = new Label("General");
|
||||
GeneralPage GeneralPage = new GeneralPage();
|
||||
OptionNotebook.AppendPage(GeneralPage.GetWidget(), GeneralLabel);
|
||||
Label InputLabel = new Label("Input");
|
||||
InputPage InputPage = new InputPage();
|
||||
OptionNotebook.AppendPage(InputPage.GetWidget(), InputLabel);
|
||||
|
||||
//Register Events
|
||||
OptionAcceptButton.Clicked += OptionAcceptButton_Clicked;
|
||||
OptionCancelButton.Clicked += OptionCancelButton_Clicked;
|
||||
|
||||
}
|
||||
|
||||
private void OptionCancelButton_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
this.Respond(ResponseType.Cancel);
|
||||
}
|
||||
|
||||
private void OptionAcceptButton_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
this.Respond(ResponseType.Accept);
|
||||
}
|
||||
}
|
||||
}
|
72
Ryujinx.UI/UI/ConfigurationWindow.glade
Normal file
72
Ryujinx.UI/UI/ConfigurationWindow.glade
Normal file
|
@ -0,0 +1,72 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.21.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.20"/>
|
||||
<object class="GtkDialog" id="ConfigurationWindow">
|
||||
<property name="width_request">-1</property>
|
||||
<property name="height_request">-1</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="title" translatable="yes">Configuration</property>
|
||||
<property name="type_hint">dialog</property>
|
||||
<child internal-child="vbox">
|
||||
<object class="GtkBox">
|
||||
<property name="can_focus">False</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<property name="spacing">2</property>
|
||||
<child internal-child="action_area">
|
||||
<object class="GtkButtonBox">
|
||||
<property name="can_focus">False</property>
|
||||
<property name="layout_style">end</property>
|
||||
<child>
|
||||
<object class="GtkButton" id="OptionAcceptButton">
|
||||
<property name="label" translatable="yes">OK</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkButton" id="OptionCancelButton">
|
||||
<property name="label" translatable="yes">Cancel</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">False</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkNotebook" id="OptionNotebook">
|
||||
<property name="width_request">-1</property>
|
||||
<property name="height_request">-1</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
25
Ryujinx.UI/UI/Debugging/Debugger.cs
Normal file
25
Ryujinx.UI/UI/Debugging/Debugger.cs
Normal file
|
@ -0,0 +1,25 @@
|
|||
using Gtk;
|
||||
using System;
|
||||
using System.Reflection;
|
||||
using GUI = Gtk.Builder.ObjectAttribute;
|
||||
|
||||
|
||||
namespace Ryujinx.UI.UI.Debugging
|
||||
{
|
||||
public class Debugger : Gtk.Window
|
||||
{
|
||||
[GUI] Notebook DebuggerNotebook;
|
||||
|
||||
public Debugger() : this(new Builder("Debugger.glade")) { }
|
||||
|
||||
public Debugger(Builder builder) : base(builder.GetObject("Debugger").Handle)
|
||||
{
|
||||
builder.Autoconnect(this);
|
||||
|
||||
//Add Pages
|
||||
Label LogLabel = new Label("Log");
|
||||
LogPage LogPage = new LogPage();
|
||||
DebuggerNotebook.AppendPage(LogPage.Widget, LogLabel);
|
||||
}
|
||||
}
|
||||
}
|
19
Ryujinx.UI/UI/Debugging/Debugger.glade
Normal file
19
Ryujinx.UI/UI/Debugging/Debugger.glade
Normal file
|
@ -0,0 +1,19 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.21.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.20"/>
|
||||
<object class="GtkWindow" id="Debugger">
|
||||
<property name="can_focus">False</property>
|
||||
<property name="title" translatable="yes">Debugger</property>
|
||||
<child>
|
||||
<object class="GtkNotebook" id="DebuggerNotebook">
|
||||
<property name="height_request">500</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child type="titlebar">
|
||||
<placeholder/>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
200
Ryujinx.UI/UI/Debugging/LogPage.cs
Normal file
200
Ryujinx.UI/UI/Debugging/LogPage.cs
Normal file
|
@ -0,0 +1,200 @@
|
|||
using Gtk;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Reflection;
|
||||
using System.Text;
|
||||
using Ryujinx.Core.Logging;
|
||||
using GUI = Gtk.Builder.ObjectAttribute;
|
||||
namespace Ryujinx.UI.UI.Debugging
|
||||
{
|
||||
public class LogPage : Box
|
||||
{
|
||||
Logger Log;
|
||||
|
||||
public static LogWriter LogWriter = new LogWriter();
|
||||
|
||||
Builder builder = new Builder("LogPage.glade");
|
||||
|
||||
Box LogBox;
|
||||
|
||||
//UI elements
|
||||
[GUI] Button SaveButton;
|
||||
[GUI] TextView LogTextView;
|
||||
[GUI] TextView LogClassesBox;
|
||||
[GUI] CheckButton InfoLogEnable;
|
||||
[GUI] CheckButton DebugLogEnable;
|
||||
[GUI] CheckButton ErrorLogEnable;
|
||||
[GUI] CheckButton StubLogEnable;
|
||||
[GUI] CheckButton WarnLogEnable;
|
||||
|
||||
public LogPage() : base(Orientation.Horizontal, 0)
|
||||
{
|
||||
//Load styles
|
||||
CssProvider provider = new CssProvider();
|
||||
using (Stream stream = Assembly.GetExecutingAssembly().GetManifestResourceStream("Ryujinx.UI.UI.style.css"))
|
||||
using (StreamReader reader = new StreamReader(stream))
|
||||
{
|
||||
provider.LoadFromData(reader.ReadToEnd());
|
||||
}
|
||||
|
||||
builder.Autoconnect(this);
|
||||
|
||||
LogBox = (Box)builder.GetObject("MainBox");
|
||||
|
||||
//Style the log text box
|
||||
LogTextView.StyleContext.AddProvider(provider,1000);
|
||||
|
||||
//Register Events
|
||||
InfoLogEnable.Toggled += InfoLogEnable_Toggled;
|
||||
DebugLogEnable.Toggled += DebugLogEnable_Toggled;
|
||||
ErrorLogEnable.Toggled += ErrorLogEnable_Toggled;
|
||||
WarnLogEnable.Toggled += WarnLogEnable_Toggled;
|
||||
StubLogEnable.Toggled += StubLogEnable_Toggled;
|
||||
SaveButton.Clicked += SaveButton_Clicked;
|
||||
LogClassesBox.Buffer.InsertText += Buffer_InsertText;
|
||||
|
||||
//Set values
|
||||
LogTextView.Buffer = LogWriter.LogBuffer;
|
||||
}
|
||||
|
||||
private void SaveButton_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (Log != null)
|
||||
Settings.Write(Log);
|
||||
}
|
||||
|
||||
public void UpdateSettings(Logger Log)
|
||||
{
|
||||
this.Log = Log;
|
||||
|
||||
InfoLogEnable.Active = Log.IsEnabled(LogLevel.Info);
|
||||
DebugLogEnable.Active = Log.IsEnabled(LogLevel.Debug);
|
||||
ErrorLogEnable.Active = Log.IsEnabled(LogLevel.Error);
|
||||
WarnLogEnable.Active = Log.IsEnabled(LogLevel.Warning);
|
||||
StubLogEnable.Active = Log.IsEnabled(LogLevel.Stub);
|
||||
|
||||
string EnabledClasses = string.Empty;
|
||||
foreach(var logClass in Enum.GetNames(typeof(LogClass)))
|
||||
{
|
||||
if (Log.IsEnabled(Enum.Parse<LogClass>(logClass)))
|
||||
EnabledClasses += logClass + Environment.NewLine;
|
||||
}
|
||||
|
||||
LogClassesBox.Buffer.Text = EnabledClasses;
|
||||
}
|
||||
|
||||
private void Buffer_InsertText(object o, InsertTextArgs args)
|
||||
{
|
||||
string[] FilteredLogClasses = LogClassesBox.Buffer.Text.Split('\n');
|
||||
|
||||
if (FilteredLogClasses.Length > 0)
|
||||
{
|
||||
foreach (LogClass Class in Enum.GetValues(typeof(LogClass)))
|
||||
{
|
||||
Log.SetEnable(Class, false);
|
||||
}
|
||||
}
|
||||
|
||||
foreach (string LogClass in FilteredLogClasses)
|
||||
{
|
||||
if (!string.IsNullOrEmpty(LogClass.Trim()))
|
||||
{
|
||||
foreach (LogClass Class in Enum.GetValues(typeof(LogClass)))
|
||||
{
|
||||
if (Class.ToString().ToLower().Contains(LogClass.Trim().ToLower()))
|
||||
{
|
||||
Log.SetEnable(Class, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void StubLogEnable_Toggled(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is CheckButton LogCheckButton)
|
||||
{
|
||||
Log.SetEnable(LogLevel.Stub,LogCheckButton.Active);
|
||||
}
|
||||
}
|
||||
|
||||
private void WarnLogEnable_Toggled(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is CheckButton LogCheckButton)
|
||||
{
|
||||
Log.SetEnable(LogLevel.Warning, LogCheckButton.Active);
|
||||
}
|
||||
}
|
||||
|
||||
private void ErrorLogEnable_Toggled(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is CheckButton LogCheckButton)
|
||||
{
|
||||
Log.SetEnable(LogLevel.Error, LogCheckButton.Active);
|
||||
}
|
||||
}
|
||||
|
||||
private void DebugLogEnable_Toggled(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is CheckButton LogCheckButton)
|
||||
{
|
||||
Log.SetEnable(LogLevel.Debug, LogCheckButton.Active);
|
||||
}
|
||||
}
|
||||
|
||||
private void InfoLogEnable_Toggled(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is CheckButton LogCheckButton)
|
||||
{
|
||||
Log.SetEnable(LogLevel.Info, LogCheckButton.Active);
|
||||
}
|
||||
}
|
||||
|
||||
public Widget Widget
|
||||
{
|
||||
get => LogBox;
|
||||
}
|
||||
}
|
||||
|
||||
public class LogWriter : TextWriter
|
||||
{
|
||||
public override Encoding Encoding => Encoding.UTF8;
|
||||
public TextBuffer LogBuffer { get; private set; }
|
||||
private TextIter EndIter;
|
||||
|
||||
public LogWriter()
|
||||
{
|
||||
LogBuffer = new TextBuffer(null);
|
||||
EndIter = LogBuffer.EndIter;
|
||||
|
||||
//Add color tags
|
||||
LogBuffer.TagTable.Add(new TextTag("Red") { Foreground = "red" });
|
||||
LogBuffer.TagTable.Add(new TextTag("Gray") { Foreground = "grey" });
|
||||
LogBuffer.TagTable.Add(new TextTag("Yellow") { Foreground = "yellow" });
|
||||
LogBuffer.TagTable.Add(new TextTag("Magenta") { Foreground = "magenta" });
|
||||
LogBuffer.TagTable.Add(new TextTag("White") { Foreground = "white" });
|
||||
LogBuffer.TagTable.Add(new TextTag("DarkYellow") { Foreground = "orange" });
|
||||
LogBuffer.TagTable.Add(new TextTag("DarkGray") { Foreground = "darkgray" });
|
||||
}
|
||||
|
||||
public override void Write(string value)
|
||||
{
|
||||
string consoleColor = Console.ForegroundColor.ToString();
|
||||
Gtk.Application.Invoke(delegate
|
||||
{
|
||||
LogBuffer.InsertWithTagsByName(ref EndIter, value, consoleColor);
|
||||
});
|
||||
}
|
||||
|
||||
public override void WriteLine(string value)
|
||||
{
|
||||
string consoleColor = Console.ForegroundColor.ToString();
|
||||
Gtk.Application.Invoke(delegate
|
||||
{
|
||||
LogBuffer.InsertWithTagsByName(ref EndIter, value + Environment.NewLine, consoleColor);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
254
Ryujinx.UI/UI/Debugging/LogPage.glade
Normal file
254
Ryujinx.UI/UI/Debugging/LogPage.glade
Normal file
|
@ -0,0 +1,254 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.21.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.20"/>
|
||||
<object class="GtkBox" id="MainBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkScrolledWindow">
|
||||
<property name="width_request">400</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="margin_left">5</property>
|
||||
<property name="margin_right">5</property>
|
||||
<property name="margin_top">10</property>
|
||||
<property name="margin_bottom">10</property>
|
||||
<property name="shadow_type">in</property>
|
||||
<property name="propagate_natural_width">True</property>
|
||||
<property name="propagate_natural_height">True</property>
|
||||
<child>
|
||||
<object class="GtkTextView" id="LogTextView">
|
||||
<property name="width_request">400</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="editable">False</property>
|
||||
<property name="wrap_mode">word</property>
|
||||
<style>
|
||||
<class name="log_text_box"/>
|
||||
</style>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="width_request">200</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="margin_left">5</property>
|
||||
<property name="margin_right">5</property>
|
||||
<property name="margin_bottom">5</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkFrame" id="LogLevelFrame">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="margin_left">5</property>
|
||||
<property name="margin_right">10</property>
|
||||
<property name="label_xalign">0</property>
|
||||
<property name="shadow_type">none</property>
|
||||
<child>
|
||||
<object class="GtkAlignment">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="left_padding">12</property>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="margin_right">20</property>
|
||||
<property name="margin_bottom">5</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="InfoLogEnable">
|
||||
<property name="label" translatable="yes">Info</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="DebugLogEnable">
|
||||
<property name="label" translatable="yes">Debug</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="ErrorLogEnable">
|
||||
<property name="label" translatable="yes">Error</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">2</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="TraceLogEnable">
|
||||
<property name="label" translatable="yes">Trace</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">3</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="FatalLogEnable">
|
||||
<property name="label" translatable="yes">Fatal</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">4</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="StubLogEnable">
|
||||
<property name="label" translatable="yes">Stub</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">5</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="WarnLogEnable">
|
||||
<property name="label" translatable="yes">Warn</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">6</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child type="label">
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Log Levels</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkFrame">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="margin_left">5</property>
|
||||
<property name="margin_right">10</property>
|
||||
<property name="hexpand">True</property>
|
||||
<property name="label_xalign">0</property>
|
||||
<property name="shadow_type">none</property>
|
||||
<child>
|
||||
<object class="GtkAlignment">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="left_padding">12</property>
|
||||
<child>
|
||||
<object class="GtkScrolledWindow">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="margin_right">5</property>
|
||||
<property name="margin_bottom">5</property>
|
||||
<property name="shadow_type">in</property>
|
||||
<child>
|
||||
<object class="GtkTextView" id="LogClassesBox">
|
||||
<property name="width_request">200</property>
|
||||
<property name="height_request">300</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child type="label">
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Log Classes</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkButton" id="SaveButton">
|
||||
<property name="label" translatable="yes">button</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">True</property>
|
||||
<property name="margin_left">10</property>
|
||||
<property name="margin_right">10</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">3</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
36
Ryujinx.UI/UI/GeneralPage.cs
Normal file
36
Ryujinx.UI/UI/GeneralPage.cs
Normal file
|
@ -0,0 +1,36 @@
|
|||
using Gtk;
|
||||
using System;
|
||||
using GUI = Gtk.Builder.ObjectAttribute;
|
||||
|
||||
namespace Ryujinx.UI.UI
|
||||
{
|
||||
public class GeneralPage : Alignment
|
||||
{
|
||||
Alignment Alignment;
|
||||
|
||||
[GUI] CheckButton MemoryChecksToggle;
|
||||
|
||||
Builder builder = new Builder("GeneralPage.glade");
|
||||
|
||||
public GeneralPage(): base(0.5f, 0.5f, 1, 1)
|
||||
{
|
||||
builder.Autoconnect(this);
|
||||
|
||||
Alignment = (Alignment)builder.GetObject("GeneralLayout");
|
||||
|
||||
MemoryChecksToggle.Toggled += MemoryChecksToggle_Toggled;
|
||||
|
||||
MemoryChecksToggle.Active = !AOptimizations.DisableMemoryChecks;
|
||||
}
|
||||
|
||||
private void MemoryChecksToggle_Toggled(object sender, EventArgs e)
|
||||
{
|
||||
AOptimizations.DisableMemoryChecks = !MemoryChecksToggle.Active;
|
||||
}
|
||||
|
||||
public Widget GetWidget()
|
||||
{
|
||||
return Alignment;
|
||||
}
|
||||
}
|
||||
}
|
68
Ryujinx.UI/UI/GeneralPage.glade
Normal file
68
Ryujinx.UI/UI/GeneralPage.glade
Normal file
|
@ -0,0 +1,68 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.21.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.10"/>
|
||||
<object class="GtkAlignment" id="GeneralLayout">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="left_padding">10</property>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="margin_right">10</property>
|
||||
<property name="margin_top">10</property>
|
||||
<property name="margin_bottom">10</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkFrame">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label_xalign">0</property>
|
||||
<property name="shadow_type">none</property>
|
||||
<child>
|
||||
<object class="GtkAlignment">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="left_padding">12</property>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkCheckButton" id="MemoryChecksToggle">
|
||||
<property name="label" translatable="yes">Enable Memory Checks</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="receives_default">False</property>
|
||||
<property name="draw_indicator">True</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child type="label">
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">CPU</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
495
Ryujinx.UI/UI/InputPage.cs
Normal file
495
Ryujinx.UI/UI/InputPage.cs
Normal file
|
@ -0,0 +1,495 @@
|
|||
using Gtk;
|
||||
using Ryujinx.Core;
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
using System.Globalization;
|
||||
using GUI = Gtk.Builder.ObjectAttribute;
|
||||
|
||||
namespace Ryujinx.UI.UI
|
||||
{
|
||||
public class InputPage : Notebook
|
||||
{
|
||||
Notebook Notebook;
|
||||
//Buttons
|
||||
[GUI] Button LeftAnalogUp;
|
||||
[GUI] Button LeftAnalogDown;
|
||||
[GUI] Button LeftAnalogLeft;
|
||||
[GUI] Button LeftAnalogRight;
|
||||
[GUI] Button LeftAnalogStick;
|
||||
[GUI] Button RightAnalogUp;
|
||||
[GUI] Button RightAnalogDown;
|
||||
[GUI] Button RightAnalogLeft;
|
||||
[GUI] Button RightAnalogRight;
|
||||
[GUI] Button RightAnalogStick;
|
||||
[GUI] Button DPadUp;
|
||||
[GUI] Button DPadDown;
|
||||
[GUI] Button DPadLeft;
|
||||
[GUI] Button DPadRight;
|
||||
[GUI] Button ButtonA;
|
||||
[GUI] Button ButtonB;
|
||||
[GUI] Button ButtonX;
|
||||
[GUI] Button ButtonY;
|
||||
[GUI] Button ButtonL;
|
||||
[GUI] Button ButtonR;
|
||||
[GUI] Button ButtonZL;
|
||||
[GUI] Button ButtonZR;
|
||||
[GUI] Button ButtonMinus;
|
||||
[GUI] Button ButtonPlus;
|
||||
|
||||
Gdk.Key CurrentKeyPressed;
|
||||
bool IsPressed;
|
||||
bool CancelCurrentEvent;
|
||||
|
||||
Builder builder = new Builder("InputPage.glade");
|
||||
|
||||
public InputPage()
|
||||
{
|
||||
builder.Autoconnect(this);
|
||||
|
||||
Notebook = (Notebook)builder.GetObject("InputNotebook");
|
||||
|
||||
//Register Events
|
||||
LeftAnalogUp.Clicked += LeftAnalogUp_Clicked;
|
||||
LeftAnalogDown.Clicked += LeftAnalogDown_Clicked;
|
||||
LeftAnalogLeft.Clicked += LeftAnalogLeft_Clicked;
|
||||
LeftAnalogRight.Clicked += LeftAnalogRight_Clicked;
|
||||
LeftAnalogStick.Clicked += LeftAnalogStick_Clicked;
|
||||
|
||||
RightAnalogUp.Clicked += RightAnalogUp_Clicked;
|
||||
RightAnalogDown.Clicked += RightAnalogDown_Clicked;
|
||||
RightAnalogLeft.Clicked += RightAnalogLeft_Clicked;
|
||||
RightAnalogRight.Clicked += RightAnalogRight_Clicked;
|
||||
RightAnalogStick.Clicked += RightAnalogStick_Clicked;
|
||||
|
||||
DPadUp.Clicked += DPadUp_Clicked;
|
||||
DPadDown.Clicked += DPadDown_Clicked;
|
||||
DPadLeft.Clicked += DPadLeft_Clicked;
|
||||
DPadRight.Clicked += DPadRight_Clicked;
|
||||
|
||||
ButtonA.Clicked += ButtonA_Clicked;
|
||||
ButtonB.Clicked += ButtonB_Clicked;
|
||||
ButtonX.Clicked += ButtonX_Clicked;
|
||||
ButtonY.Clicked += ButtonY_Clicked;
|
||||
ButtonZL.Clicked += ButtonZL_Clicked;
|
||||
ButtonZR.Clicked += ButtonZR_Clicked;
|
||||
ButtonMinus.Clicked += ButtonMinus_Clicked;
|
||||
ButtonPlus.Clicked += ButtonPlus_Clicked;
|
||||
|
||||
// Load Values
|
||||
LeftAnalogUp.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.StickUp).ToString();
|
||||
LeftAnalogDown.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.StickDown).ToString();
|
||||
LeftAnalogLeft.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.StickLeft).ToString();
|
||||
LeftAnalogRight.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.StickRight).ToString();
|
||||
LeftAnalogStick.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.StickButton).ToString();
|
||||
|
||||
RightAnalogUp.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.StickUp).ToString();
|
||||
RightAnalogDown.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.StickDown).ToString();
|
||||
RightAnalogLeft.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.StickLeft).ToString();
|
||||
RightAnalogRight.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.StickRight).ToString();
|
||||
RightAnalogStick.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.StickButton).ToString();
|
||||
|
||||
DPadUp.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.DPadUp).ToString();
|
||||
DPadDown.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.DPadDown).ToString();
|
||||
DPadLeft.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.DPadLeft).ToString();
|
||||
DPadRight.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.DPadRight).ToString();
|
||||
|
||||
ButtonA.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.ButtonA).ToString();
|
||||
ButtonB.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.ButtonB).ToString();
|
||||
ButtonX.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.ButtonX).ToString();
|
||||
ButtonY.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.ButtonY).ToString();
|
||||
ButtonL.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.ButtonL).ToString();
|
||||
ButtonR.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.ButtonR).ToString();
|
||||
ButtonZL.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.ButtonZL).ToString();
|
||||
ButtonZR.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.ButtonZR).ToString();
|
||||
ButtonMinus.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Left.ButtonMinus).ToString();
|
||||
ButtonPlus.Label = ((OpenTK.Input.Key)Config.FakeJoyCon.Right.ButtonPlus).ToString();
|
||||
}
|
||||
|
||||
private async void ButtonPlus_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.ButtonPlus = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void ButtonMinus_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.ButtonMinus = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void ButtonZR_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.ButtonZR = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void ButtonZL_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.ButtonZL = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void ButtonY_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.ButtonY = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void ButtonX_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.ButtonX = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void ButtonB_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.ButtonB = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void ButtonA_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.ButtonA = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void DPadRight_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.DPadRight = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void DPadLeft_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.DPadLeft = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void DPadDown_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.DPadDown = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void DPadUp_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.DPadUp = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void RightAnalogStick_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.StickButton = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void RightAnalogRight_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.StickRight = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void RightAnalogLeft_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.StickLeft = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void RightAnalogDown_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.StickDown = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void RightAnalogUp_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Right.StickUp = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void LeftAnalogStick_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.StickButton = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void LeftAnalogRight_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.StickRight = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void LeftAnalogLeft_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.StickLeft = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void LeftAnalogDown_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.StickDown = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async void LeftAnalogUp_Clicked(object sender, EventArgs e)
|
||||
{
|
||||
if (sender is Button ClickedButton)
|
||||
{
|
||||
OpenTK.Input.Key key = await GetKeyPress(ClickedButton);
|
||||
if (key != default(OpenTK.Input.Key))
|
||||
{
|
||||
var joycon = Config.FakeJoyCon;
|
||||
joycon.Left.StickUp = (int)key;
|
||||
Config.FakeJoyCon = joycon;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void InputPage_KeyPressEvent(object o, KeyPressEventArgs args)
|
||||
{
|
||||
CurrentKeyPressed = args.Event.Key;
|
||||
IsPressed = true;
|
||||
}
|
||||
|
||||
public async Task<OpenTK.Input.Key> GetKeyPress(Button ClickedButton)
|
||||
{
|
||||
string oldLabel = ClickedButton.Label;
|
||||
try
|
||||
{
|
||||
ClickedButton.IsFocus = true;
|
||||
ClickedButton.Label = "Enter Key";
|
||||
ClickedButton.KeyPressEvent += InputPage_KeyPressEvent;
|
||||
ClickedButton.FocusOutEvent += ClickedButton_FocusOutEvent;
|
||||
|
||||
|
||||
ClickedButton.KeyPressEvent -= InputPage_KeyPressEvent;
|
||||
while (!IsPressed)
|
||||
{
|
||||
if (CancelCurrentEvent)
|
||||
return default(OpenTK.Input.Key);
|
||||
await Task.Delay(1);
|
||||
}
|
||||
|
||||
IsPressed = false;
|
||||
string KeyCode = CultureInfo.CurrentCulture.TextInfo.ToTitleCase(CurrentKeyPressed.ToString());
|
||||
|
||||
//Convert certain GTK Keys to OpenTK
|
||||
switch (CurrentKeyPressed)
|
||||
{
|
||||
case Gdk.Key.Shift_L:
|
||||
KeyCode = "LShift";
|
||||
break;
|
||||
case Gdk.Key.Shift_R:
|
||||
KeyCode = "RShift";
|
||||
break;
|
||||
case Gdk.Key.Alt_L:
|
||||
KeyCode = "LAlt";
|
||||
break;
|
||||
case Gdk.Key.Alt_R:
|
||||
KeyCode = "RAlt";
|
||||
break;
|
||||
case Gdk.Key.Control_L:
|
||||
KeyCode = "LControl";
|
||||
break;
|
||||
case Gdk.Key.Control_R:
|
||||
KeyCode = "RControl";
|
||||
break;
|
||||
case Gdk.Key.dead_tilde:
|
||||
KeyCode = "Tilde";
|
||||
break;
|
||||
}
|
||||
|
||||
return (OpenTK.Input.Key)Enum.Parse(typeof(OpenTK.Input.Key), KeyCode, true);
|
||||
}
|
||||
finally
|
||||
{
|
||||
CancelCurrentEvent = false;
|
||||
Gtk.Application.Invoke(delegate
|
||||
{
|
||||
ClickedButton.FocusOutEvent -= ClickedButton_FocusOutEvent;
|
||||
ClickedButton.KeyPressEvent -= InputPage_KeyPressEvent;
|
||||
ClickedButton.Label = ClickedButton.Label.Equals("Enter Key") ? oldLabel : ClickedButton.Label;
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private void ClickedButton_FocusOutEvent(object o, FocusOutEventArgs args)
|
||||
{
|
||||
CancelCurrentEvent = true;
|
||||
IsPressed = false;
|
||||
}
|
||||
|
||||
public Widget GetWidget()
|
||||
{
|
||||
return Notebook;
|
||||
}
|
||||
}
|
||||
}
|
1234
Ryujinx.UI/UI/InputPage.glade
Normal file
1234
Ryujinx.UI/UI/InputPage.glade
Normal file
File diff suppressed because it is too large
Load diff
196
Ryujinx.UI/UI/MainWindow.glade
Normal file
196
Ryujinx.UI/UI/MainWindow.glade
Normal file
|
@ -0,0 +1,196 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.21.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.12"/>
|
||||
<object class="GtkImage" id="AboutImage">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="stock">gtk-about</property>
|
||||
</object>
|
||||
<object class="GtkImage" id="FileImage">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="stock">gtk-file</property>
|
||||
</object>
|
||||
<object class="GtkImage" id="FolderImage">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="stock">gtk-open</property>
|
||||
</object>
|
||||
<object class="GtkWindow" id="MainWindow">
|
||||
<property name="width_request">1027</property>
|
||||
<property name="height_request">640</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="title" translatable="yes">RyujinxUI</property>
|
||||
<property name="destroy_with_parent">True</property>
|
||||
<child>
|
||||
<object class="GtkBox" id="MainBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkMenuBar" id="MainMenu">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="valign">start</property>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="FileMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Game</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu" id="menu1">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem" id="LoadFileMenuItem">
|
||||
<property name="label">Load Package</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="image">FileImage</property>
|
||||
<property name="use_stock">False</property>
|
||||
<property name="always_show_image">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem" id="LoadFolderMenuItem">
|
||||
<property name="label" translatable="yes">Load Game Folder</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="image">FolderImage</property>
|
||||
<property name="use_stock">False</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkSeparatorMenuItem" id="separatormenuitem1">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem" id="ExitMenuItem">
|
||||
<property name="label">gtk-close</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
<property name="always_show_image">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Emulation</property>
|
||||
<property name="use_underline">True</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="ContinueMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Continue</property>
|
||||
<property name="use_underline">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="PauseMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Pause</property>
|
||||
<property name="use_underline">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="StopMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Stop</property>
|
||||
<property name="use_underline">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkSeparatorMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="OptionMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Configuration</property>
|
||||
<property name="use_underline">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">View</property>
|
||||
<property name="use_underline">True</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="ShowDebugMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Show Debug Window</property>
|
||||
<property name="use_underline">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="HelpMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Help</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu" id="menu3">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem" id="AboutMenuItem">
|
||||
<property name="label">About Ryujinx</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="image">AboutImage</property>
|
||||
<property name="use_stock">False</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child type="titlebar">
|
||||
<placeholder/>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
50
Ryujinx.UI/UI/MiscPage.glade
Normal file
50
Ryujinx.UI/UI/MiscPage.glade
Normal file
|
@ -0,0 +1,50 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.21.0 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.10"/>
|
||||
<object class="GtkNotebook">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
<child type="tab">
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">page 1</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="tab_fill">False</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
<child type="tab">
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">page 2</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="position">1</property>
|
||||
<property name="tab_fill">False</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
<child type="tab">
|
||||
<object class="GtkLabel">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">page 3</property>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="position">2</property>
|
||||
<property name="tab_fill">False</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
5
Ryujinx.UI/UI/style.css
Normal file
5
Ryujinx.UI/UI/style.css
Normal file
|
@ -0,0 +1,5 @@
|
|||
*
|
||||
{
|
||||
background-color:black;
|
||||
color:blue;
|
||||
}
|
BIN
Ryujinx.UI/ryujinxicon.png
Normal file
BIN
Ryujinx.UI/ryujinxicon.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 4.8 KiB |
|
@ -1,7 +1,7 @@
|
|||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio 15
|
||||
VisualStudioVersion = 15.0.26730.8
|
||||
VisualStudioVersion = 15.0.27130.2036
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ryujinx", "Ryujinx\Ryujinx.csproj", "{074045D4-3ED2-4711-9169-E385F2BFB5A0}"
|
||||
EndProject
|
||||
|
@ -15,6 +15,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ryujinx.Graphics", "Ryujinx
|
|||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ryujinx.Audio", "Ryujinx.Audio\Ryujinx.Audio.csproj", "{5C1D818E-682A-46A5-9D54-30006E26C270}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Ryujinx.UI", "Ryujinx.UI\Ryujinx.UI.csproj", "{367E79AF-9A28-4E34-8589-A0F2CF32E2BF}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
|
@ -45,6 +47,10 @@ Global
|
|||
{5C1D818E-682A-46A5-9D54-30006E26C270}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{5C1D818E-682A-46A5-9D54-30006E26C270}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{5C1D818E-682A-46A5-9D54-30006E26C270}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{367E79AF-9A28-4E34-8589-A0F2CF32E2BF}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{367E79AF-9A28-4E34-8589-A0F2CF32E2BF}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{367E79AF-9A28-4E34-8589-A0F2CF32E2BF}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{367E79AF-9A28-4E34-8589-A0F2CF32E2BF}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
|
|
@ -22,11 +22,11 @@ namespace Ryujinx
|
|||
|
||||
AOptimizations.DisableMemoryChecks = !Convert.ToBoolean(Parser.Value("Enable_Memory_Checks"));
|
||||
|
||||
Log.SetEnable(LogLevel.Debug, Convert.ToBoolean(Parser.Value("Logging_Enable_Debug")));
|
||||
Log.SetEnable(LogLevel.Stub, Convert.ToBoolean(Parser.Value("Logging_Enable_Stub")));
|
||||
Log.SetEnable(LogLevel.Info, Convert.ToBoolean(Parser.Value("Logging_Enable_Info")));
|
||||
Log.SetEnable(LogLevel.Debug, Convert.ToBoolean(Parser.Value("Logging_Enable_Debug")));
|
||||
Log.SetEnable(LogLevel.Stub, Convert.ToBoolean(Parser.Value("Logging_Enable_Stub")));
|
||||
Log.SetEnable(LogLevel.Info, Convert.ToBoolean(Parser.Value("Logging_Enable_Info")));
|
||||
Log.SetEnable(LogLevel.Warning, Convert.ToBoolean(Parser.Value("Logging_Enable_Warn")));
|
||||
Log.SetEnable(LogLevel.Error, Convert.ToBoolean(Parser.Value("Logging_Enable_Error")));
|
||||
Log.SetEnable(LogLevel.Error, Convert.ToBoolean(Parser.Value("Logging_Enable_Error")));
|
||||
|
||||
string[] FilteredLogClasses = Parser.Value("Logging_Filtered_Classes").Split(',', StringSplitOptions.RemoveEmptyEntries);
|
||||
|
||||
|
@ -60,34 +60,34 @@ namespace Ryujinx
|
|||
{
|
||||
Left = new JoyConLeft
|
||||
{
|
||||
StickUp = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Up")),
|
||||
StickDown = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Down")),
|
||||
StickLeft = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Left")),
|
||||
StickRight = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Right")),
|
||||
StickUp = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Up")),
|
||||
StickDown = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Down")),
|
||||
StickLeft = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Left")),
|
||||
StickRight = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Right")),
|
||||
StickButton = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Stick_Button")),
|
||||
DPadUp = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Up")),
|
||||
DPadDown = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Down")),
|
||||
DPadLeft = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Left")),
|
||||
DPadRight = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Right")),
|
||||
DPadUp = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Up")),
|
||||
DPadDown = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Down")),
|
||||
DPadLeft = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Left")),
|
||||
DPadRight = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_DPad_Right")),
|
||||
ButtonMinus = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Button_Minus")),
|
||||
ButtonL = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Button_L")),
|
||||
ButtonZL = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Button_ZL"))
|
||||
ButtonL = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Button_L")),
|
||||
ButtonZL = Convert.ToInt16(Parser.Value("Controls_Left_FakeJoycon_Button_ZL"))
|
||||
},
|
||||
|
||||
Right = new JoyConRight
|
||||
{
|
||||
StickUp = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Up")),
|
||||
StickDown = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Down")),
|
||||
StickLeft = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Left")),
|
||||
StickRight = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Right")),
|
||||
StickUp = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Up")),
|
||||
StickDown = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Down")),
|
||||
StickLeft = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Left")),
|
||||
StickRight = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Right")),
|
||||
StickButton = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Stick_Button")),
|
||||
ButtonA = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_A")),
|
||||
ButtonB = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_B")),
|
||||
ButtonX = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_X")),
|
||||
ButtonY = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_Y")),
|
||||
ButtonPlus = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_Plus")),
|
||||
ButtonR = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_R")),
|
||||
ButtonZR = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_ZR"))
|
||||
ButtonA = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_A")),
|
||||
ButtonB = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_B")),
|
||||
ButtonX = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_X")),
|
||||
ButtonY = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_Y")),
|
||||
ButtonPlus = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_Plus")),
|
||||
ButtonR = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_R")),
|
||||
ButtonZR = Convert.ToInt16(Parser.Value("Controls_Right_FakeJoycon_Button_ZR"))
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
@ -10,10 +10,10 @@ namespace Ryujinx
|
|||
{
|
||||
public class GLScreen : GameWindow
|
||||
{
|
||||
private const int TouchScreenWidth = 1280;
|
||||
private const int TouchScreenWidth = 1280;
|
||||
private const int TouchScreenHeight = 720;
|
||||
|
||||
private const float TouchScreenRatioX = (float)TouchScreenWidth / TouchScreenHeight;
|
||||
private const float TouchScreenRatioX = (float)TouchScreenWidth / TouchScreenHeight;
|
||||
private const float TouchScreenRatioY = (float)TouchScreenHeight / TouchScreenWidth;
|
||||
|
||||
private Switch Ns;
|
||||
|
@ -26,11 +26,11 @@ namespace Ryujinx
|
|||
DisplayDevice.Default, 3, 3,
|
||||
GraphicsContextFlags.ForwardCompatible)
|
||||
{
|
||||
this.Ns = Ns;
|
||||
this.Ns = Ns;
|
||||
this.Renderer = Renderer;
|
||||
|
||||
Location = new Point(
|
||||
(DisplayDevice.Default.Width / 2) - (Width / 2),
|
||||
(DisplayDevice.Default.Width / 2) - (Width / 2),
|
||||
(DisplayDevice.Default.Height / 2) - (Height / 2));
|
||||
}
|
||||
|
||||
|
@ -55,36 +55,36 @@ namespace Ryujinx
|
|||
int RightJoystickDY = 0;
|
||||
|
||||
//RightJoystick
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickUp]) LeftJoystickDY = short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickDown]) LeftJoystickDY = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickLeft]) LeftJoystickDX = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickUp]) LeftJoystickDY = short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickDown]) LeftJoystickDY = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickLeft]) LeftJoystickDX = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickRight]) LeftJoystickDX = short.MaxValue;
|
||||
|
||||
//LeftButtons
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.StickButton]) CurrentButton |= HidControllerButtons.KEY_LSTICK;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadUp]) CurrentButton |= HidControllerButtons.KEY_DUP;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadDown]) CurrentButton |= HidControllerButtons.KEY_DDOWN;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadLeft]) CurrentButton |= HidControllerButtons.KEY_DLEFT;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadRight]) CurrentButton |= HidControllerButtons.KEY_DRIGHT;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadUp]) CurrentButton |= HidControllerButtons.KEY_DUP;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadDown]) CurrentButton |= HidControllerButtons.KEY_DDOWN;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadLeft]) CurrentButton |= HidControllerButtons.KEY_DLEFT;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.DPadRight]) CurrentButton |= HidControllerButtons.KEY_DRIGHT;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.ButtonMinus]) CurrentButton |= HidControllerButtons.KEY_MINUS;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.ButtonL]) CurrentButton |= HidControllerButtons.KEY_L;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.ButtonZL]) CurrentButton |= HidControllerButtons.KEY_ZL;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.ButtonL]) CurrentButton |= HidControllerButtons.KEY_L;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Left.ButtonZL]) CurrentButton |= HidControllerButtons.KEY_ZL;
|
||||
|
||||
//RightJoystick
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickUp]) RightJoystickDY = short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickDown]) RightJoystickDY = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickLeft]) RightJoystickDX = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickUp]) RightJoystickDY = short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickDown]) RightJoystickDY = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickLeft]) RightJoystickDX = -short.MaxValue;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickRight]) RightJoystickDX = short.MaxValue;
|
||||
|
||||
//RightButtons
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.StickButton]) CurrentButton |= HidControllerButtons.KEY_RSTICK;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonA]) CurrentButton |= HidControllerButtons.KEY_A;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonB]) CurrentButton |= HidControllerButtons.KEY_B;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonX]) CurrentButton |= HidControllerButtons.KEY_X;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonY]) CurrentButton |= HidControllerButtons.KEY_Y;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonPlus]) CurrentButton |= HidControllerButtons.KEY_PLUS;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonR]) CurrentButton |= HidControllerButtons.KEY_R;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonZR]) CurrentButton |= HidControllerButtons.KEY_ZR;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonA]) CurrentButton |= HidControllerButtons.KEY_A;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonB]) CurrentButton |= HidControllerButtons.KEY_B;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonX]) CurrentButton |= HidControllerButtons.KEY_X;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonY]) CurrentButton |= HidControllerButtons.KEY_Y;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonPlus]) CurrentButton |= HidControllerButtons.KEY_PLUS;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonR]) CurrentButton |= HidControllerButtons.KEY_R;
|
||||
if (Keyboard[(Key)Config.FakeJoyCon.Right.ButtonZR]) CurrentButton |= HidControllerButtons.KEY_ZR;
|
||||
|
||||
LeftJoystick = new HidJoystickPosition
|
||||
{
|
||||
|
@ -104,7 +104,7 @@ namespace Ryujinx
|
|||
//OpenTK always captures mouse events, even if out of focus, so check if window is focused.
|
||||
if (Focused && Mouse?.GetState().LeftButton == ButtonState.Pressed)
|
||||
{
|
||||
int ScrnWidth = Width;
|
||||
int ScrnWidth = Width;
|
||||
int ScrnHeight = Height;
|
||||
|
||||
if (Width > Height * TouchScreenRatioX)
|
||||
|
@ -116,7 +116,7 @@ namespace Ryujinx
|
|||
ScrnHeight = (int)(Width * TouchScreenRatioY);
|
||||
}
|
||||
|
||||
int StartX = (Width - ScrnWidth) >> 1;
|
||||
int StartX = (Width - ScrnWidth) >> 1;
|
||||
int StartY = (Height - ScrnHeight) >> 1;
|
||||
|
||||
int EndX = StartX + ScrnWidth;
|
||||
|
@ -124,13 +124,13 @@ namespace Ryujinx
|
|||
|
||||
if (Mouse.X >= StartX &&
|
||||
Mouse.Y >= StartY &&
|
||||
Mouse.X < EndX &&
|
||||
Mouse.Y < EndY)
|
||||
Mouse.X < EndX &&
|
||||
Mouse.Y < EndY)
|
||||
{
|
||||
int ScrnMouseX = Mouse.X - StartX;
|
||||
int ScrnMouseY = Mouse.Y - StartY;
|
||||
|
||||
int MX = (int)(((float)ScrnMouseX / ScrnWidth) * TouchScreenWidth);
|
||||
int MX = (int)(((float)ScrnMouseX / ScrnWidth) * TouchScreenWidth);
|
||||
int MY = (int)(((float)ScrnMouseY / ScrnHeight) * TouchScreenHeight);
|
||||
|
||||
HidTouchPoint CurrentPoint = new HidTouchPoint
|
||||
|
@ -141,7 +141,7 @@ namespace Ryujinx
|
|||
//Placeholder values till more data is acquired
|
||||
DiameterX = 10,
|
||||
DiameterY = 10,
|
||||
Angle = 90
|
||||
Angle = 90
|
||||
};
|
||||
|
||||
HasTouch = true;
|
||||
|
|
Loading…
Reference in a new issue