BizHawk/BizHawk.Emulation.Cores/Consoles/Nintendo/NDS/DeSmuME.cs

123 lines
3.9 KiB
C#

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Runtime.InteropServices;
using BizHawk.Emulation.Common;
namespace BizHawk.Emulation.Cores.Consoles.Nintendo.NDS
{
[Core("DeSmuME", "DeSmuME Team")]
unsafe partial class DeSmuME : IEmulator
{
private BasicServiceProvider _serviceProvider;
public IEmulatorServiceProvider ServiceProvider => _serviceProvider;
public ControllerDefinition ControllerDefinition { get; private set; }
public int Frame => GetFrameCount();
public string SystemId => "NDS";
public bool DeterministicEmulation => true;
public CoreComm CoreComm { get; private set; }
public void Dispose()
{
DeInit_NDS();
inited = false;
}
public bool FrameAdvance(IController controller, bool render, bool rendersound = true)
{
int buttons = (controller.IsPressed("Left") ? 1 : 0) | (controller.IsPressed("Right") ? 2 : 0)
| (controller.IsPressed("Up") ? 4 : 0) | (controller.IsPressed("Down") ? 8 : 0)
| (controller.IsPressed("A") ? 0x10 : 0) | (controller.IsPressed("B") ? 0x20 : 0)
| (controller.IsPressed("X") ? 0x40 : 0) | (controller.IsPressed("Y") ? 0x80 : 0)
| (controller.IsPressed("L") ? 0x100 : 0) | (controller.IsPressed("R") ? 0x200 : 0)
| (controller.IsPressed("Start") ? 0x400 : 0) | (controller.IsPressed("Select") ? 0x800 : 0)
| (controller.IsPressed("Debug") ? 0x1000 : 0) | (controller.IsPressed("Lid") ? 0x2000 : 0)
| (controller.IsPressed("Touch") ? 0x4000 : 0);
SetInput((short)buttons, (byte)controller.GetFloat("TouchX"), (byte)controller.GetFloat("TouchY"));
FrameAdvance();
return true;
}
public void ResetCounters()
{
ResetCounters();
}
// debug path/build for easier testing
//const string dllPath = "../../desmume/desmume/src/frontend/windows/__bins/DesHawk-VS2017-x64-Debug.dll";
const string dllPath = "DesHawk.dll";
[DllImport(dllPath)]
private static extern void Init_NDS();
[DllImport(dllPath)]
private static extern void DeInit_NDS();
[DllImport(dllPath)]
private static extern int GetFrameCount();
[DllImport(dllPath)]
private static extern void ResetFrameCounters();
[DllImport(dllPath)]
private static extern bool LoadROM(byte* file, int fileSize);
[DllImport(dllPath)]
private static extern void SetInput(short buttons, byte touchX, byte touchY);
[DllImport(dllPath)]
private static extern void FrameAdvance();
private static bool inited = false;
[CoreConstructor("NDS")]
public DeSmuME(byte[] file)
{
if (inited)
throw new InvalidOperationException("Only one instance of DeSmuME can exist.");
inited = true;
_serviceProvider = new BasicServiceProvider(this);
ControllerDefinition = new ControllerDefinition();
ControllerDefinition.Name = "NDS";
ControllerDefinition.BoolButtons.Add("Left");
ControllerDefinition.BoolButtons.Add("Right");
ControllerDefinition.BoolButtons.Add("Up");
ControllerDefinition.BoolButtons.Add("Down");
ControllerDefinition.BoolButtons.Add("A");
ControllerDefinition.BoolButtons.Add("B");
ControllerDefinition.BoolButtons.Add("X");
ControllerDefinition.BoolButtons.Add("Y");
ControllerDefinition.BoolButtons.Add("L");
ControllerDefinition.BoolButtons.Add("R");
ControllerDefinition.BoolButtons.Add("Start");
ControllerDefinition.BoolButtons.Add("Select");
ControllerDefinition.BoolButtons.Add("Debug");
ControllerDefinition.BoolButtons.Add("Lid");
ControllerDefinition.BoolButtons.Add("Touch");
ControllerDefinition.FloatControls.Add("TouchX");
ControllerDefinition.FloatRanges.Add(new ControllerDefinition.FloatRange(0, 128, 255));
ControllerDefinition.FloatControls.Add("TouchY");
ControllerDefinition.FloatRanges.Add(new ControllerDefinition.FloatRange(0, 96, 191));
CoreComm = new CoreComm(null, null);
CoreComm.NominalWidth = 256;
CoreComm.NominalHeight = 192;
Init_NDS();
fixed (byte* f = file)
{
LoadROM(f, file.Length);
}
}
}
}