Skip to content

Commit

Permalink
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Slot2: Add Slide Controller
Browse files Browse the repository at this point in the history
windwakr committed Oct 10, 2023
1 parent 0b027d8 commit c927f8a
Showing 15 changed files with 357 additions and 33 deletions.
1 change: 1 addition & 0 deletions desmume/src/Makefile.am
Original file line number Diff line number Diff line change
@@ -96,6 +96,7 @@ libdesmume_a_SOURCES = \
addons/slot2_rumblepak.cpp \
addons/slot2_guitarGrip.cpp \
addons/slot2_hcv1000.cpp \
addons/slot2_slideController.cpp \
addons/slot2_expMemory.cpp \
addons/slot2_piano.cpp \
addons/slot2_passme.cpp \
264 changes: 264 additions & 0 deletions desmume/src/addons/slot2_slideController.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,264 @@
/*
Copyright (C) 2023 DeSmuME team
This file is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 2 of the License, or
(at your option) any later version.
This file is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with the this software. If not, see <http://www.gnu.org/licenses/>.
*/

//Absolute barebones implementation of the Slide Controller add-on. Rumble is not implemented.
//The game does a bunch of mystery reads of various sizes which have not been investigated at all.

#include "../slot2.h"
#include "../emufile.h"

#define SC_BITIN(X, Y) \
do { \
X = (X << 1) | (Y & 1); \
bitsWritten++; \
} while (0)

#define SC_BITOUT(X, Y) \
do { \
X = ((Y >> 7 - bitsRead) & 1); \
bitsRead++; \
} while(0)

u8 motionStatus;
u8 xMotion;
u8 yMotion;

class Slot2_SlideController : public ISlot2Interface
{
private:
u8 prevClock;
u8 bitsWritten;
u8 bitsRead;
u8 inByte;
u16 regSel;

u8 configBits;
u8 framePeriodLower;
u8 framePeriodUpper;
public:

virtual Slot2Info const* info()
{
static Slot2InfoSimple info("Slide Controller", "Slide Controller add-on", 0x0A);
return &info;
}

virtual void connect()
{
prevClock = 0;
bitsWritten = 0;
bitsRead = 0;
inByte = 0;
regSel = 0xFFFF;

motionStatus = 0;
xMotion = 0;
yMotion = 0;
configBits = 0;
framePeriodLower = 0x20;
framePeriodUpper = 0xD1;
}

virtual void writeWord(u8 PROCNUM, u32 addr, u16 val)
{
if (addr == 0x081E0000)
{
if ((prevClock == 0) && (val & 0x2) && (val & 0x8))
{
SC_BITIN(inByte, val);
if (bitsWritten == 8)
{
bitsWritten = 0;
if (regSel == 0xFFFF) //First byte written
{
regSel = inByte;
}
else //Second byte written
{
//printf("WRITE TO REG: %02X = %02X\n", regSel & 0x7F , inByte);
switch (regSel & 0x7F)
{
case 0x0A: //Config bits
configBits = inByte;
break;
case 0x10: //Frame period (lower)
framePeriodLower = inByte;
break;
case 0x11: //Frame period(upper)
framePeriodUpper = inByte;
break;
}
regSel = 0xFFFF;
}
}
}
prevClock = (val & 0x2) >> 1;
}

if (configBits & 0x80) //Reset
{
motionStatus = 0;
xMotion = 0;
yMotion = 0;
configBits = 0;
framePeriodLower = 0x20;
framePeriodUpper = 0xD1;

prevClock = 0;
bitsWritten = 0;
bitsRead = 0;
inByte = 0;
regSel = 0xFFFF;
}
}

virtual u8 readByte(u8 PROCNUM, u32 addr)
{
if (addr == 0x080000B2)
{
return 0x96;
}
return 0xFF;
}

virtual u16 readWord(u8 PROCNUM, u32 addr)
{
u16 outWord = 0;

if (addr < 0x08000100)
{
outWord = 0xFEF0;
}

if (addr == 0x081E0000)
{
switch (regSel)
{
case 0x00: //Product ID
SC_BITOUT(outWord, 0x3);
break;
case 0x01: //Revision ID
SC_BITOUT(outWord, 0x20); //Is this correct?
break;
case 0x02: //Motion status
SC_BITOUT(outWord, motionStatus);
if (bitsRead == 8) motionStatus = 0;
break;
case 0x03: //X motion delta
SC_BITOUT(outWord, xMotion);
if (bitsRead == 8) xMotion = 0;
break;
case 0x04: //Y motion delta
SC_BITOUT(outWord, yMotion);
if (bitsRead == 8) yMotion = 0;
break;
case 0x05: //Surface quality
SC_BITOUT(outWord, 128);
break;
case 0x06: //Average pixel
SC_BITOUT(outWord, 32);
break;
case 0x07: //Maximum pixel
SC_BITOUT(outWord, 63);
break;
case 0x0A: //Configuration bits
SC_BITOUT(outWord, configBits);
break;
case 0x0C: //Data out (lower)
SC_BITOUT(outWord, 0);
break;
case 0x0D: //Data out (upper)
SC_BITOUT(outWord, 0);
break;
case 0x0E: //Shutter value (lower)
SC_BITOUT(outWord, 64);
break;
case 0x0F: //Shutter value (upper)
SC_BITOUT(outWord, 0);
break;
case 0x10: //Frame period (lower)
SC_BITOUT(outWord, framePeriodLower);
break;
case 0x11: //Frame period (upper)
SC_BITOUT(outWord, framePeriodUpper);
break;
}

if (bitsRead == 8)
{
bitsRead = 0;
//printf("READ FROM REG: %02X\n", regSel);
regSel = 0xFFFF;
}
}

return outWord;
}

virtual void savestate(EMUFILE& os)
{
s32 version = 0;
os.write_32LE(version);

os.write_u8(prevClock);
os.write_u8(bitsWritten);
os.write_u8(bitsRead);
os.write_u8(inByte);
os.write_16LE(regSel);

os.write_u8(configBits);
os.write_u8(framePeriodLower);
os.write_u8(framePeriodUpper);
os.write_u8(motionStatus);
os.write_u8(xMotion);
os.write_u8(yMotion);
}

virtual void loadstate(EMUFILE& is)
{
s32 version = is.read_s32LE();

if (version == 0)
{
is.read_u8(prevClock);
is.read_u8(bitsWritten);
is.read_u8(bitsRead);
is.read_u8(inByte);
is.read_16LE(regSel);

is.read_u8(configBits);
is.read_u8(framePeriodLower);
is.read_u8(framePeriodUpper);
is.read_u8(motionStatus);
is.read_u8(xMotion);
is.read_u8(yMotion);
}
}
};

ISlot2Interface* construct_Slot2_SlideController() { return new Slot2_SlideController(); }

void slideController_updateMotion(s8 x, s8 y)
{
xMotion = (u8)x;
yMotion = (u8)y;
if (xMotion || yMotion)
motionStatus = 0x80;
}

#undef SC_BITIN
#undef SC_BITOUT
2 changes: 1 addition & 1 deletion desmume/src/frontend/interface/meson.build
Original file line number Diff line number Diff line change
@@ -109,7 +109,7 @@ libdesmume_src += [
'../../utils/tinyxml/tinyxmlerror.cpp',
'../../utils/tinyxml/tinyxmlparser.cpp',
'../../utils/colorspacehandler/colorspacehandler.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_slideController.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../cheatSystem.cpp',
'../../texcache.cpp', '../../rasterize.cpp',
'../../metaspu/metaspu.cpp',
Original file line number Diff line number Diff line change
@@ -269,6 +269,7 @@
<ClCompile Include="..\..\..\addons\slot2_gbagame.cpp" />
<ClCompile Include="..\..\..\addons\slot2_guitarGrip.cpp" />
<ClCompile Include="..\..\..\addons\slot2_hcv1000.cpp" />
<ClCompile Include="..\..\..\addons\slot2_slideController.cpp" />
<ClCompile Include="..\..\..\addons\slot2_none.cpp" />
<ClCompile Include="..\..\..\addons\slot2_rumblepak.cpp" />
<ClCompile Include="..\..\..\utils\guid.cpp" />
Original file line number Diff line number Diff line change
@@ -135,6 +135,9 @@
<ClCompile Include="..\..\..\addons\slot2_hcv1000.cpp">
<Filter>addons</Filter>
</ClCompile>
<ClCompile Include="..\..\..\addons\slot2_slideController.cpp">
<Filter>addons</Filter>
</ClCompile>
<ClCompile Include="..\..\..\addons\slot2_none.cpp">
<Filter>addons</Filter>
</ClCompile>
2 changes: 1 addition & 1 deletion desmume/src/frontend/posix/Makefile.am
Original file line number Diff line number Diff line change
@@ -98,7 +98,7 @@ libdesmume_a_SOURCES = \
../../utils/tinyxml/tinyxmlparser.cpp \
../../utils/glcorearb.h \
../../utils/colorspacehandler/colorspacehandler.cpp ../../utils/colorspacehandler/colorspacehandler.h \
../../addons/slot2_auto.cpp ../../addons/slot2_mpcf.cpp ../../addons/slot2_paddle.cpp ../../addons/slot2_gbagame.cpp ../../addons/slot2_none.cpp ../../addons/slot2_rumblepak.cpp ../../addons/slot2_guitarGrip.cpp ../../addons/slot2_hcv1000.cpp ../../addons/slot2_expMemory.cpp ../../addons/slot2_piano.cpp ../../addons/slot2_passme.cpp ../../addons/slot1_none.cpp ../../addons/slot1_r4.cpp ../../addons/slot1_retail_nand.cpp ../../addons/slot1_retail_auto.cpp ../../addons/slot1_retail_mcrom.cpp ../../addons/slot1_retail_mcrom_debug.cpp ../../addons/slot1comp_mc.cpp ../../addons/slot1comp_mc.h ../../addons/slot1comp_rom.h ../../addons/slot1comp_rom.cpp ../../addons/slot1comp_protocol.h ../../addons/slot1comp_protocol.cpp \
../../addons/slot2_auto.cpp ../../addons/slot2_mpcf.cpp ../../addons/slot2_paddle.cpp ../../addons/slot2_gbagame.cpp ../../addons/slot2_none.cpp ../../addons/slot2_rumblepak.cpp ../../addons/slot2_guitarGrip.cpp ../../addons/slot2_hcv1000.cpp ../../addons/slot2_slideController.cpp ../../addons/slot2_expMemory.cpp ../../addons/slot2_piano.cpp ../../addons/slot2_passme.cpp ../../addons/slot1_none.cpp ../../addons/slot1_r4.cpp ../../addons/slot1_retail_nand.cpp ../../addons/slot1_retail_auto.cpp ../../addons/slot1_retail_mcrom.cpp ../../addons/slot1_retail_mcrom_debug.cpp ../../addons/slot1comp_mc.cpp ../../addons/slot1comp_mc.h ../../addons/slot1comp_rom.h ../../addons/slot1comp_rom.cpp ../../addons/slot1comp_protocol.h ../../addons/slot1comp_protocol.cpp \
../../cheatSystem.cpp ../../cheatSystem.h \
../../texcache.cpp ../../texcache.h ../../rasterize.cpp ../../rasterize.h \
../../metaspu/metaspu.cpp ../../metaspu/metaspu.h \
2 changes: 1 addition & 1 deletion desmume/src/frontend/posix/meson.build
Original file line number Diff line number Diff line change
@@ -104,7 +104,7 @@ libdesmume_src = [
'../../utils/tinyxml/tinyxmlerror.cpp',
'../../utils/tinyxml/tinyxmlparser.cpp',
'../../utils/colorspacehandler/colorspacehandler.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../addons/slot2_auto.cpp', '../../addons/slot2_mpcf.cpp', '../../addons/slot2_paddle.cpp', '../../addons/slot2_gbagame.cpp', '../../addons/slot2_none.cpp', '../../addons/slot2_rumblepak.cpp', '../../addons/slot2_guitarGrip.cpp', '../../addons/slot2_hcv1000.cpp', '../../addons/slot2_slideController.cpp', '../../addons/slot2_expMemory.cpp', '../../addons/slot2_piano.cpp', '../../addons/slot2_passme.cpp', '../../addons/slot1_none.cpp', '../../addons/slot1_r4.cpp', '../../addons/slot1_retail_nand.cpp', '../../addons/slot1_retail_auto.cpp', '../../addons/slot1_retail_mcrom.cpp', '../../addons/slot1_retail_mcrom_debug.cpp', '../../addons/slot1comp_mc.cpp', '../../addons/slot1comp_rom.cpp', '../../addons/slot1comp_protocol.cpp',
'../../cheatSystem.cpp',
'../../texcache.cpp', '../../rasterize.cpp',
'../../metaspu/metaspu.cpp',
1 change: 1 addition & 0 deletions desmume/src/frontend/windows/DeSmuME.vcxproj
Original file line number Diff line number Diff line change
@@ -73,6 +73,7 @@
<ClCompile Include="..\..\addons\slot1_retail_nand.cpp" />
<ClCompile Include="..\..\addons\slot2_mpcf.cpp" />
<ClCompile Include="..\..\addons\slot2_paddle.cpp" />
<ClCompile Include="..\..\addons\slot2_slideController.cpp" />
<ClCompile Include="..\..\arm_instructions.cpp" />
<ClCompile Include="..\..\armcpu.cpp" />
<ClCompile Include="..\..\arm_jit.cpp" />
3 changes: 3 additions & 0 deletions desmume/src/frontend/windows/DeSmuME.vcxproj.filters
Original file line number Diff line number Diff line change
@@ -933,6 +933,9 @@
<ClCompile Include="..\..\addons\slot2_hcv1000.cpp">
<Filter>addons</Filter>
</ClCompile>
<ClCompile Include="..\..\addons\slot2_slideController.cpp">
<Filter>addons</Filter>
</ClCompile>
</ItemGroup>
<ItemGroup>
<ClInclude Include="..\..\utils\guid.h">
17 changes: 11 additions & 6 deletions desmume/src/frontend/windows/gbaslot_config.cpp
Original file line number Diff line number Diff line change
@@ -526,11 +526,12 @@ u32 GBAslot_IDDs[NDS_SLOT2_COUNT] = {
IDD_GBASLOT_RUMBLEPAK,
IDD_GBASLOT_GBAGAME,
IDD_GBASLOT_GUITARGRIP,
IDD_GBASLOT_NONE, //expmem
IDD_GBASLOT_NONE, //expmem
IDD_GBASLOT_PIANO,
IDD_GBASLOT_PADDLE, //paddle
IDD_GBASLOT_NONE, //PassME
IDD_GBASLOT_HCV1000, //HCV-1000
IDD_GBASLOT_PADDLE, //paddle
IDD_GBASLOT_NONE, //PassME
IDD_GBASLOT_HCV1000, //HCV-1000
IDD_GBASLOT_NONE, //Slide Controller
};

DLGPROC GBAslot_Procs[NDS_SLOT2_COUNT] = {
@@ -540,11 +541,12 @@ DLGPROC GBAslot_Procs[NDS_SLOT2_COUNT] = {
GbaSlotRumblePak,
GbaSlotGBAgame,
GbaSlotGuitarGrip,
GbaSlotNone, //expmem
GbaSlotNone, //expmem
GbaSlotPiano,
GbaSlotPaddle,
GbaSlotNone, // PassME
GbaSlotNone, // PassME
GbaSlotHCV1000, //HCV-1000
GbaSlotNone, //Slide Controller
};


@@ -696,6 +698,8 @@ void GBAslotDialog(HWND hwnd)
WritePrivateProfileString("Slot2.HCV1000", "barcode", tmp_hcv1000_barcode, IniName);
WritePrivateProfileInt("Slot2.HCV1000", "scankey", HCV1000.SCANKEY, IniName);
break;
case NDS_SLOT2_SLIDECONTROLLER:
break;
default:
return;
}
@@ -708,6 +712,7 @@ void GBAslotDialog(HWND hwnd)
Piano.Enabled = (slot2_GetCurrentType() == NDS_SLOT2_EASYPIANO)?true:false;
Paddle.Enabled = (slot2_GetCurrentType() == NDS_SLOT2_PADDLE)?true:false;
HCV1000.Enabled = (slot2_GetCurrentType() == NDS_SLOT2_HCV1000)?true:false;
SlideController.Enabled = (slot2_GetCurrentType() == NDS_SLOT2_SLIDECONTROLLER)?true:false;
}
}

2 changes: 2 additions & 0 deletions desmume/src/frontend/windows/inputdx.cpp
Original file line number Diff line number Diff line change
@@ -261,6 +261,8 @@ SPaddle DefaultPaddle = { false, 'K', 'L' };
SHCV1000 HCV1000;
SHCV1000 DefaultHCV1000 = { false, 'L'};

SSLIDECONTROLLER SlideController;

bool killStylusTopScreen = false;
bool killStylusOffScreen = false;
bool allowUpAndDown = false;
Loading

0 comments on commit c927f8a

Please sign in to comment.