Added UDPWii (iPhone WiiMote) support.

git-svn-id: https://dolphin-emu.googlecode.com/svn/trunk@5351 8ced0084-cf51-0410-be5f-012b33b47a6e
This commit is contained in:
dapetcu21 2010-04-13 01:34:11 +00:00
parent 448af895d3
commit fe5fb76fd4
11 changed files with 485 additions and 31 deletions

View File

@ -810,6 +810,8 @@
B1EDF579106C2DAE0003EAE6 /* CoreAudio.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = B1EDF564106C2CD70003EAE6 /* CoreAudio.framework */; };
B1EDF582106C2E000003EAE6 /* Render.h in Headers */ = {isa = PBXBuildFile; fileRef = B1EDF581106C2E000003EAE6 /* Render.h */; };
B1EDF583106C2E000003EAE6 /* Render.h in Headers */ = {isa = PBXBuildFile; fileRef = B1EDF581106C2E000003EAE6 /* Render.h */; };
C1CE233A116A4C0200347EB3 /* UDPWiimote.cpp in Sources */ = {isa = PBXBuildFile; fileRef = C1CE2338116A4C0200347EB3 /* UDPWiimote.cpp */; };
C1CE233B116A4C0200347EB3 /* UDPWiimote.h in Headers */ = {isa = PBXBuildFile; fileRef = C1CE2339116A4C0200347EB3 /* UDPWiimote.h */; };
/* End PBXBuildFile section */
/* Begin PBXContainerItemProxy section */
@ -1925,6 +1927,8 @@
B1EDF55B106C2CBA0003EAE6 /* CoreAudioSoundStream.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CoreAudioSoundStream.h; sourceTree = "<group>"; };
B1EDF564106C2CD70003EAE6 /* CoreAudio.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreAudio.framework; path = /System/Library/Frameworks/CoreAudio.framework; sourceTree = "<absolute>"; };
B1EDF581106C2E000003EAE6 /* Render.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Render.h; sourceTree = "<group>"; };
C1CE2338116A4C0200347EB3 /* UDPWiimote.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = UDPWiimote.cpp; sourceTree = "<group>"; };
C1CE2339116A4C0200347EB3 /* UDPWiimote.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = UDPWiimote.h; sourceTree = "<group>"; };
/* End PBXFileReference section */
/* Begin PBXFrameworksBuildPhase section */
@ -2496,6 +2500,8 @@
B122DB4F1003548600D86E1A /* Src */ = {
isa = PBXGroup;
children = (
C1CE2338116A4C0200347EB3 /* UDPWiimote.cpp */,
C1CE2339116A4C0200347EB3 /* UDPWiimote.h */,
B122DB501003548600D86E1A /* Config.cpp */,
B122DB511003548600D86E1A /* Config.h */,
B122DB5A1003548600D86E1A /* DataReports.cpp */,
@ -3727,6 +3733,7 @@
B122DB841003548600D86E1A /* main.h in Headers */,
B122DB861003548600D86E1A /* wiimote_hid.h in Headers */,
B122DB881003548600D86E1A /* wiimote_real.h in Headers */,
C1CE233B116A4C0200347EB3 /* UDPWiimote.h in Headers */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@ -4702,6 +4709,7 @@
B122DB831003548600D86E1A /* main.cpp in Sources */,
B122DB851003548600D86E1A /* ReadWiimote.cpp in Sources */,
B122DB871003548600D86E1A /* wiimote_real.cpp in Sources */,
C1CE233A116A4C0200347EB3 /* UDPWiimote.cpp in Sources */,
);
runOnlyForDeploymentPostprocessing = 0;
};

View File

@ -324,6 +324,18 @@ void Config::Load()
iniFile.Get(SectionName, "Rumble", &WiiMoteEmu::WiiMapping[i].Rumble, false);
iniFile.Get(SectionName, "RumbleStrength", &WiiMoteEmu::WiiMapping[i].RumbleStrength, 80);
iniFile.Get(SectionName, "TriggerType", &WiiMoteEmu::WiiMapping[i].TriggerType, 0);
//UDPWii
iniFile.Get(SectionName, "UDPWii_Enable", &WiiMoteEmu::WiiMapping[i].UDPWM.enable, false);
std::string port;
char default_port[15];
sprintf(default_port,"%d",4432+i);
iniFile.Get(SectionName, "UDPWii_Port", &port, default_port);
strncpy(WiiMoteEmu::WiiMapping[i].UDPWM.port,port.c_str(),10);
iniFile.Get(SectionName, "UDPWii_EnableAccel", &WiiMoteEmu::WiiMapping[i].UDPWM.enableAccel, true);
iniFile.Get(SectionName, "UDPWii_EnableButtons", &WiiMoteEmu::WiiMapping[i].UDPWM.enableButtons, true);
iniFile.Get(SectionName, "UDPWii_EnableIR", &WiiMoteEmu::WiiMapping[i].UDPWM.enableIR, true);
iniFile.Get(SectionName, "UDPWii_EnableNunchuck", &WiiMoteEmu::WiiMapping[i].UDPWM.enableNunchuck, true);
}
iniFile.Load((std::string(File::GetUserPath(D_CONFIG_IDX)) + "Dolphin.ini").c_str());
@ -430,6 +442,14 @@ void Config::Save()
iniFile.Set(SectionName, "Rumble", WiiMoteEmu::WiiMapping[i].Rumble);
iniFile.Set(SectionName, "RumbleStrength", WiiMoteEmu::WiiMapping[i].RumbleStrength);
iniFile.Set(SectionName, "TriggerType", WiiMoteEmu::WiiMapping[i].TriggerType);
// UDPWii
iniFile.Set(SectionName, "UDPWii_Enable", WiiMoteEmu::WiiMapping[i].UDPWM.enable);
iniFile.Set(SectionName, "UDPWii_Port", WiiMoteEmu::WiiMapping[i].UDPWM.port);
iniFile.Set(SectionName, "UDPWii_EnableAccel", WiiMoteEmu::WiiMapping[i].UDPWM.enableAccel);
iniFile.Set(SectionName, "UDPWii_EnableButtons", WiiMoteEmu::WiiMapping[i].UDPWM.enableButtons);
iniFile.Set(SectionName, "UDPWii_EnableIR", WiiMoteEmu::WiiMapping[i].UDPWM.enableIR);
iniFile.Set(SectionName, "UDPWii_EnableNunchuck", WiiMoteEmu::WiiMapping[i].UDPWM.enableNunchuck);
}
iniFile.Save((std::string(File::GetUserPath(D_CONFIG_IDX)) + "Wiimote.ini").c_str());

View File

@ -45,6 +45,14 @@ BEGIN_EVENT_TABLE(WiimoteBasicConfigDialog,wxDialog)
EVT_CHECKBOX(IDC_WIIAUTORECONNECT, WiimoteBasicConfigDialog::GeneralSettingsChanged)
EVT_CHOICE(IDC_EXTCONNECTED, WiimoteBasicConfigDialog::GeneralSettingsChanged)
//UDPWii
EVT_CHECKBOX(IDC_UDPWIIENABLE, WiimoteBasicConfigDialog::UDPWiiSettingsChanged)
EVT_CHECKBOX(IDC_UDPWIIACCEL, WiimoteBasicConfigDialog::UDPWiiSettingsChanged)
EVT_CHECKBOX(IDC_UDPWIIBUTT, WiimoteBasicConfigDialog::UDPWiiSettingsChanged)
EVT_CHECKBOX(IDC_UDPWIIIR, WiimoteBasicConfigDialog::UDPWiiSettingsChanged)
EVT_CHECKBOX(IDC_UDPWIINUN, WiimoteBasicConfigDialog::UDPWiiSettingsChanged)
EVT_TEXT(IDT_UDPWIIPORT, WiimoteBasicConfigDialog::UDPWiiSettingsChanged)
// IR cursor
EVT_COMMAND_SCROLL(IDS_WIDTH, WiimoteBasicConfigDialog::IRCursorChanged)
EVT_COMMAND_SCROLL(IDS_HEIGHT, WiimoteBasicConfigDialog::IRCursorChanged)
@ -170,6 +178,22 @@ void WiimoteBasicConfigDialog::CreateGUIControls()
m_Extension[i] = new wxChoice(m_Controller[i], IDC_EXTCONNECTED, wxDefaultPosition, wxDefaultSize, arrayStringFor_extension, 0, wxDefaultValidator);
// UDPWii
m_UDPWiiEnable[i] = new wxCheckBox(m_Controller[i], IDC_UDPWIIENABLE, wxT("Enable UDPWii"));
m_UDPWiiEnable[i]->SetToolTip(wxT("Enable listening for wiimote data on the network. Requires emulation restart"));
m_UDPWiiAccel[i] = new wxCheckBox(m_Controller[i], IDC_UDPWIIACCEL, wxT("Update acceleration from UDPWii"));
m_UDPWiiAccel[i]->SetToolTip(wxT("Retrieve acceleration data from a device on the network"));
m_UDPWiiButt[i] = new wxCheckBox(m_Controller[i], IDC_UDPWIIBUTT, wxT("Update buttons from UDPWii"));
m_UDPWiiButt[i]->SetToolTip(wxT("Retrieve button data from a device on the network. This doesn't affect keyboard mappings"));
m_UDPWiiIR[i] = new wxCheckBox(m_Controller[i], IDC_UDPWIIIR, wxT("Update IR pointer from UDPWii"));
m_UDPWiiIR[i]->SetToolTip(wxT("Retrieve IR pointer from a device on the network. Disables using mouse as pointer"));
m_UDPWiiNun[i] = new wxCheckBox(m_Controller[i], IDC_UDPWIINUN, wxT("Update nunchuck from UDPWii"));
m_UDPWiiNun[i]->SetToolTip(wxT("Retrieve nunchuck data from a device on the network."));
m_UDPWiiPort[i] = new wxTextCtrl(m_Controller[i], IDT_UDPWIIPORT);
m_UDPWiiPort[i]->SetMaxLength(9);
m_TextUDPWiiPort[i] = new wxStaticText(m_Controller[i], wxID_ANY, wxT("UDP Port:"));
m_TextUDPWiiPort[i]->SetToolTip(wxT("The UDP port on witch UDPWii listens for this remote."));
m_PairUpRealWiimote[i] = new wxButton(m_Controller[i], IDB_PAIRUP_REAL, wxT("Pair Up Real Wiimotes"));
m_PairUpRealWiimote[i]->SetToolTip(wxT("Press the Buttons 1 and 2 on your Wiimote.\nThis might take a few seconds.\nIt only works if you are using Microsoft Bluetooth stack.")); // Only working with MS BT Stack.
#ifndef _WIN32
@ -216,6 +240,16 @@ void WiimoteBasicConfigDialog::CreateGUIControls()
m_SizeExtensions[i]->Add(m_WiiMotionPlusConnected[i], 0, wxEXPAND | wxALL, 5);
m_SizeExtensions[i]->Add(m_Extension[i], 0, wxEXPAND | wxALL, 5);
m_SizeUDPWii[i] = new wxStaticBoxSizer(wxVERTICAL, m_Controller[i], wxT("Emulated UDPWii"));
m_SizeUDPWii[i]->Add(m_UDPWiiEnable[i], 0, wxEXPAND | wxALL,1);
m_SizeUDPWiiPort[i]= new wxBoxSizer(wxHORIZONTAL);
m_SizeUDPWiiPort[i]->Add(m_TextUDPWiiPort[i], 0, wxEXPAND | wxALL,1);
m_SizeUDPWiiPort[i]->Add(m_UDPWiiPort[i], 0, wxEXPAND | wxALL,1);
m_SizeUDPWii[i]->Add(m_SizeUDPWiiPort[i], 0, wxEXPAND | wxALL,1);
m_SizeUDPWii[i]->Add(m_UDPWiiAccel[i], 0, wxEXPAND | wxALL,1);
m_SizeUDPWii[i]->Add(m_UDPWiiButt[i], 0, wxEXPAND | wxALL,1);
m_SizeUDPWii[i]->Add(m_UDPWiiIR[i], 0, wxEXPAND | wxALL,1);
m_SizeUDPWii[i]->Add(m_UDPWiiNun[i], 0, wxEXPAND | wxALL,1);
m_SizeReal[i] = new wxStaticBoxSizer(wxVERTICAL, m_Controller[i], wxT("Real Wiimote"));
m_SizeReal[i]->Add(m_PairUpRealWiimote[i], 0, wxEXPAND | wxALL, 5);
@ -255,6 +289,7 @@ void WiimoteBasicConfigDialog::CreateGUIControls()
m_SizeBasicGeneralLeft[i]->Add(m_SizeBasic[i], 0, wxEXPAND | (wxUP), 5);
m_SizeBasicGeneralLeft[i]->Add(m_SizeEmu[i], 0, wxEXPAND | (wxUP), 5);
m_SizeBasicGeneralLeft[i]->Add(m_SizeExtensions[i], 0, wxEXPAND | (wxUP), 5);
m_SizeBasicGeneralLeft[i]->Add(m_SizeUDPWii[i], 0, wxEXPAND | (wxUP), 5);
m_SizeBasicGeneralRight[i] = new wxBoxSizer(wxVERTICAL);
m_SizeBasicGeneralRight[i]->Add(m_SizeReal[i], 0, wxEXPAND | (wxUP), 5);
@ -462,6 +497,32 @@ void WiimoteBasicConfigDialog::IRCursorChanged(wxScrollEvent& event)
UpdateGUI();
}
void WiimoteBasicConfigDialog::UDPWiiSettingsChanged(wxCommandEvent &event)
{
switch(event.GetId())
{
case IDC_UDPWIIENABLE:
WiiMoteEmu::WiiMapping[m_Page].UDPWM.enable=m_UDPWiiEnable[m_Page]->GetValue();
break;
case IDC_UDPWIIACCEL:
WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableAccel=m_UDPWiiAccel[m_Page]->GetValue();
break;
case IDC_UDPWIIIR:
WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableIR=m_UDPWiiIR[m_Page]->GetValue();
break;
case IDC_UDPWIIBUTT:
WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableButtons=m_UDPWiiButt[m_Page]->GetValue();
break;
case IDC_UDPWIINUN:
WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableNunchuck=m_UDPWiiNun[m_Page]->GetValue();
break;
case IDT_UDPWIIPORT:
strncpy(WiiMoteEmu::WiiMapping[m_Page].UDPWM.port,(const char*)(m_UDPWiiPort[m_Page]->GetValue().mb_str(wxConvUTF8)),10);
break;
}
UpdateGUI();
}
void WiimoteBasicConfigDialog::UpdateGUI()
{
/* I have disabled this option during a running game because it's enough to be able to switch
@ -509,6 +570,16 @@ void WiimoteBasicConfigDialog::UpdateGUI()
m_SliderTop[m_Page]->SetValue(g_Config.iIRTop);
m_SliderIrLevel[m_Page]->SetValue(g_Config.iIRLevel);
//Update UDPWii
m_UDPWiiEnable[m_Page]->Enable(g_EmulatorState != PLUGIN_EMUSTATE_PLAY);
m_UDPWiiPort[m_Page]->Enable(g_EmulatorState != PLUGIN_EMUSTATE_PLAY);
m_UDPWiiEnable[m_Page]->SetValue(WiiMoteEmu::WiiMapping[m_Page].UDPWM.enable);
m_UDPWiiAccel[m_Page]->SetValue(WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableAccel);
m_UDPWiiButt[m_Page]->SetValue(WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableButtons);
m_UDPWiiIR[m_Page]->SetValue(WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableIR);
m_UDPWiiNun[m_Page]->SetValue(WiiMoteEmu::WiiMapping[m_Page].UDPWM.enableNunchuck);
m_UDPWiiPort[m_Page]->ChangeValue(wxString::FromAscii(WiiMoteEmu::WiiMapping[m_Page].UDPWM.port));
m_CheckAR43[m_Page]->SetValue(g_Config.bKeepAR43);
m_CheckAR169[m_Page]->SetValue(g_Config.bKeepAR169);
m_Crop[m_Page]->SetValue(g_Config.bCrop);

View File

@ -84,7 +84,12 @@ class WiimoteBasicConfigDialog : public wxDialog
*m_CheckAR43[MAX_WIIMOTES],
*m_CheckAR169[MAX_WIIMOTES],
*m_Crop[MAX_WIIMOTES],
*m_WiiAutoReconnect[MAX_WIIMOTES];
*m_WiiAutoReconnect[MAX_WIIMOTES],
*m_UDPWiiEnable[MAX_WIIMOTES],
*m_UDPWiiAccel[MAX_WIIMOTES],
*m_UDPWiiButt[MAX_WIIMOTES],
*m_UDPWiiIR[MAX_WIIMOTES],
*m_UDPWiiNun[MAX_WIIMOTES];
wxStaticText *m_TextScreenWidth[MAX_WIIMOTES],
*m_TextScreenHeight[MAX_WIIMOTES],
@ -92,7 +97,8 @@ class WiimoteBasicConfigDialog : public wxDialog
*m_TextScreenTop[MAX_WIIMOTES],
*m_TextScreenIrLevel[MAX_WIIMOTES],
*m_TextAR[MAX_WIIMOTES],
*m_TextFoundRealWiimote[MAX_WIIMOTES];
*m_TextFoundRealWiimote[MAX_WIIMOTES],
*m_TextUDPWiiPort[MAX_WIIMOTES];
wxBoxSizer *m_MainSizer,
*m_SizeBasicGeneral[MAX_WIIMOTES],
@ -101,13 +107,17 @@ class WiimoteBasicConfigDialog : public wxDialog
*m_SizerIRPointerWidth[MAX_WIIMOTES],
*m_SizerIRPointerHeight[MAX_WIIMOTES],
*m_SizerIRPointerScreen[MAX_WIIMOTES],
*m_SizerIRPointerSensitivity[MAX_WIIMOTES];
*m_SizerIRPointerSensitivity[MAX_WIIMOTES],
*m_SizeUDPWiiPort[MAX_WIIMOTES];
wxStaticBoxSizer *m_SizeBasic[MAX_WIIMOTES],
*m_SizeEmu[MAX_WIIMOTES],
*m_SizeReal[MAX_WIIMOTES],
*m_SizeExtensions[MAX_WIIMOTES],
*m_SizerIRPointer[MAX_WIIMOTES];
*m_SizerIRPointer[MAX_WIIMOTES],
*m_SizeUDPWii[MAX_WIIMOTES];
wxTextCtrl *m_UDPWiiPort[MAX_WIIMOTES];
enum
{
@ -131,6 +141,14 @@ class WiimoteBasicConfigDialog : public wxDialog
IDC_WIIAUTORECONNECT,
IDC_EXTCONNECTED,
//UDPWii
IDC_UDPWIIENABLE,
IDC_UDPWIIACCEL,
IDC_UDPWIIBUTT,
IDC_UDPWIIIR,
IDC_UDPWIINUN,
IDT_UDPWIIPORT,
// Real
IDB_PAIRUP_REAL,
IDB_REFRESH_REAL,
@ -147,6 +165,7 @@ class WiimoteBasicConfigDialog : public wxDialog
void NotebookPageChanged(wxNotebookEvent& event);
void GeneralSettingsChanged(wxCommandEvent& event);
void IRCursorChanged(wxScrollEvent& event);
void UDPWiiSettingsChanged(wxCommandEvent& event);
void DoRefreshReal(); // Real
void DoUseReal();

View File

@ -33,6 +33,8 @@
#include "wiimote_hid.h" // Local
#include "Encryption.h"
#include "UDPWiimote.h"
#if defined(HAVE_X11) && HAVE_X11
#include <X11/X.h>
#endif
@ -276,6 +278,16 @@ struct SMotion
STiltData TiltNC;
};
struct UDPWiiSettings
{
bool enable;
bool enableAccel;
bool enableButtons;
bool enableIR;
bool enableNunchuck;
char port[10];
UDPWiimote *instance;
};
struct CONTROLLER_MAPPING_WII // WII PAD MAPPING
{
@ -302,6 +314,8 @@ struct CONTROLLER_MAPPING_WII // WII PAD MAPPING
SStickMapping Stick;
int Button[LAST_CONSTANT];
SMotion Motion;
UDPWiiSettings UDPWM;
};
// Gamepad input

View File

@ -256,6 +256,10 @@ void TiltByKeyboard(STiltData &_TiltData, int Type)
void TiltWiimote(int &_x, int &_y, int &_z)
{
// Select input method and return the x, y, x values
if ((WiiMapping[g_ID].UDPWM.instance)&&(WiiMapping[g_ID].UDPWM.enableAccel))
WiiMapping[g_ID].UDPWM.instance->getAccel(_x,_y,_z);
else
{
if (WiiMapping[g_ID].Tilt.InputWM == FROM_KEYBOARD)
TiltByKeyboard(WiiMapping[g_ID].Motion.TiltWM, 0);
else
@ -267,7 +271,7 @@ void TiltWiimote(int &_x, int &_y, int &_z)
// Calculate the accelerometer value from this tilt angle
TiltToAccelerometer(_x, _y, _z,WiiMapping[g_ID].Motion.TiltWM);
}
//DEBUG_LOG(WIIMOTE, "Roll:%i, Pitch:%i, _x:%u, _y:%u, _z:%u", g_Wiimote_kbd.TiltData.Roll, g_Wiimote_kbd.TiltData.Pitch, _x, _y, _z);
}

View File

@ -344,6 +344,13 @@ void Shutdown()
if (SDL_WasInit(0))
SDL_Quit();
*/
for (int i=0; i<MAX_WIIMOTES; i++)
{
if (WiiMapping[i].UDPWM.instance)
delete WiiMapping[i].UDPWM.instance;
}
g_SearchDeviceDone = false;
}
@ -376,6 +383,10 @@ void Initialize()
memcpy(g_Eeprom[i] + 0x16D0, EepromData_16D0, sizeof(EepromData_16D0));
// Copy extension id and calibration to its register, g_Config.Load() is needed before this
UpdateExtRegisterBlocks(i);
if (WiiMapping[i].UDPWM.enable)
WiiMapping[i].UDPWM.instance=new UDPWiimote(WiiMapping[i].UDPWM.port);
else
WiiMapping[i].UDPWM.instance=NULL;
}
// The emulated Wiimote is initialized

View File

@ -374,29 +374,36 @@ void FillReportInfo(wm_core& _core)
// Check that Dolphin is in focus
if (!IsFocus()) return;
u32 mask=0;
if (WiiMapping[g_ID].UDPWM.instance)
WiiMapping[g_ID].UDPWM.instance->update();
if ((WiiMapping[g_ID].UDPWM.instance)&&(WiiMapping[g_ID].UDPWM.enableButtons))
mask=WiiMapping[g_ID].UDPWM.instance->getButtons();
// Allow both mouse buttons and keyboard to press a and b
_core.a = IsKey(EWM_A);
_core.b = IsKey(EWM_B);
_core.one = IsKey(EWM_ONE);
_core.two = IsKey(EWM_TWO);
_core.plus = IsKey(EWM_P);
_core.minus = IsKey(EWM_M);
_core.home = IsKey(EWM_H);
_core.a = IsKey(EWM_A)||(mask&UDPWM_BA);
_core.b = IsKey(EWM_B)||(mask&UDPWM_BB);
_core.one = IsKey(EWM_ONE)||(mask&UDPWM_B1);
_core.two = IsKey(EWM_TWO)||(mask&UDPWM_B2);
_core.plus = IsKey(EWM_P)||(mask&UDPWM_BP);
_core.minus = IsKey(EWM_M)||(mask&UDPWM_BM);
_core.home = IsKey(EWM_H)||(mask&UDPWM_BH);
/* Sideways controls (for example for Wario Land) if the Wiimote is intended to be held sideways */
if(WiiMapping[g_ID].bSideways)
{
_core.left = IsKey(EWM_D);
_core.up = IsKey(EWM_L);
_core.right = IsKey(EWM_U);
_core.down = IsKey(EWM_R);
_core.left = IsKey(EWM_D)||(mask&UDPWM_BL);
_core.up = IsKey(EWM_L)||(mask&UDPWM_BU);
_core.right = IsKey(EWM_U)||(mask&UDPWM_BR);
_core.down = IsKey(EWM_R)||(mask&UDPWM_BU);
}
else
{
_core.left = IsKey(EWM_L);
_core.up = IsKey(EWM_U);
_core.right = IsKey(EWM_R);
_core.down = IsKey(EWM_D);
_core.left = IsKey(EWM_L)||(mask&UDPWM_BL);
_core.up = IsKey(EWM_U)||(mask&UDPWM_BU);
_core.right = IsKey(EWM_R)||(mask&UDPWM_BR);
_core.down = IsKey(EWM_D)||(mask&UDPWM_BD);
}
}
@ -435,7 +442,10 @@ void FillReportAcc(wm_accel& _acc)
int acc_y = _acc.y;
int acc_z = _acc.z;
if (IsKey(EWM_SHAKE) && !WiiMapping[g_ID].Motion.TiltWM.Shake)
if (((WiiMapping[g_ID].UDPWM.instance)&&
(WiiMapping[g_ID].UDPWM.enableButtons)&&
(WiiMapping[g_ID].UDPWM.instance->getButtons()&UDPWM_SK))
||(IsKey(EWM_SHAKE))&& !WiiMapping[g_ID].Motion.TiltWM.Shake)
WiiMapping[g_ID].Motion.TiltWM.Shake = 1;
// Step the shake simulation one step
@ -555,6 +565,9 @@ void FillReportIR(wm_ir_extended& _ir0, wm_ir_extended& _ir1)
memset(&_ir1, 0xff, sizeof(wm_ir_extended));
float MouseX, MouseY;
if ((WiiMapping[g_ID].UDPWM.instance)&&(WiiMapping[g_ID].UDPWM.enableIR))
WiiMapping[g_ID].UDPWM.instance->getIR(MouseX,MouseY);
else
GetMousePos(MouseX, MouseY);
// If we are outside the screen leave the values at 0xff
@ -633,6 +646,9 @@ void FillReportIRBasic(wm_ir_basic& _ir0, wm_ir_basic& _ir1)
memset(&_ir1, 0xff, sizeof(wm_ir_basic));
float MouseX, MouseY;
if ((WiiMapping[g_ID].UDPWM.instance)&&(WiiMapping[g_ID].UDPWM.enableIR))
WiiMapping[g_ID].UDPWM.instance->getIR(MouseX,MouseY);
else
GetMousePos(MouseX, MouseY);
// If we are outside the screen leave the values at 0xff
@ -752,6 +768,29 @@ void FillReportExtension(wm_extension& _ext)
_ext.ay = acc_y;
_ext.az = acc_z;
if ((WiiMapping[g_ID].UDPWM.instance)&&(WiiMapping[g_ID].UDPWM.enableNunchuck))
{
float x,y;
u8 b;
WiiMapping[g_ID].UDPWM.instance->getNunchuck(x,y,b);
//NOTICE_LOG(WIIMOTE,"%f %f %x",x,y,b);
//x
int factNeg= + g_nu.jx.center - g_nu.jx.min;
int factPoz= - g_nu.jx.center + g_nu.jx.max;
if (x==0) _ext.jx=g_nu.jx.center;
if (x>0) _ext.jx=(int)(x*factPoz+g_nu.jx.center);
if (x<0) _ext.jx=(int)(x*factNeg+g_nu.jx.center);
//y
factNeg= + g_nu.jy.center - g_nu.jy.min;
factPoz= - g_nu.jy.center + g_nu.jy.max;
if (y==0) _ext.jy=g_nu.jy.center;
if (y>0) _ext.jy=(int)(y*factPoz+g_nu.jy.center);
if (y<0) _ext.jy=(int)(y*factNeg+g_nu.jy.center);
//buttons
if(IsKey(ENC_C)||(b&UDPWM_NC)) _ext.bt &= ~0x02;
if(IsKey(ENC_Z)||(b&UDPWM_NZ)) _ext.bt &= ~0x01;
} else
{
// Update the analog stick
if (WiiMapping[g_ID].Stick.NC == FROM_KEYBOARD)
{
@ -836,6 +875,7 @@ void FillReportExtension(wm_extension& _ext)
if(IsKey(ENC_C)) _ext.bt &= ~0x02;
if(IsKey(ENC_Z)) _ext.bt &= ~0x01;
}
}
/* Here we encrypt the report */

View File

@ -17,6 +17,7 @@ files = [
"Encryption.cpp",
"main.cpp",
"Rumble.cpp",
"UDPWiimote.cpp"
]
if wmenv['HAVE_WX']:
files += [

View File

@ -0,0 +1,222 @@
#include "UDPWiimote.h"
#ifdef _WIN32
#include <winsock2.h>
#include <ws2tcpip.h>
#define sock_t SOCKET
#define ERRNO WSAGetLastError()
#define EWOULDBLOCK WSAEWOULDBLOCK
#define BAD_SOCK INVALID_SOCKET
#define close(x) closesocket(x)
#define cleanup do {noinst--; if (noinst==0) WSACleanup();} while (0)
#define blockingoff(sock) ioctlsocket(sock, FIONBIO, &iMode)
#define dataz char*
#ifdef _MSC_VER
#pragma comment (lib, "Ws2_32.lib")
#endif
#else
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include <unistd.h>
#include <fcntl.h>
#define BAD_SOCK -1
#define ERRNO errno
#define cleanup noinst--
#define blockingoff(sock) fcntl(sock, F_SETFL, O_NONBLOCK)
#define dataz void*
#define sock_t int
#endif
#include "EmuMain.h"
#include <stdio.h>
#include <string.h>
struct UDPWiimote::_d
{
sock_t sockfd;
};
int UDPWiimote::noinst=0;
UDPWiimote::UDPWiimote(const char *port) : d(new _d) ,x(0),y(0),z(0),nunX(0),nunY(0),mask(0),nunMask(0),pointerX(-0.1),pointerY(-0.1)
{
#ifdef _WIN32
u_long iMode = 1;
#endif
struct addrinfo hints, *servinfo, *p;
int rv;
#ifdef _WIN32
if (noinst==0)
{
WORD sockVersion;
WSADATA wsaData;
sockVersion = MAKEWORD(2, 2);
WSAStartup(sockVersion, &wsaData);
}
#endif
noinst++;
memset(&hints, 0, sizeof hints);
hints.ai_family = AF_INET;
hints.ai_socktype = SOCK_DGRAM;
hints.ai_flags = AI_PASSIVE; // use my IP
if ((rv = getaddrinfo(NULL, port, &hints, &servinfo)) != 0) {
// fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(rv));
cleanup;
this->err=-1;
return;
}
// loop through all the results and bind to the first we can
for(p = servinfo; p != NULL; p = p->ai_next) {
if (((d->sockfd = socket(p->ai_family, p->ai_socktype, p->ai_protocol)),d->sockfd) == BAD_SOCK) {
continue;
}
if (bind(d->sockfd, p->ai_addr, p->ai_addrlen) == -1) {
close(d->sockfd);
continue;
}
break;
}
if (p == NULL) {
cleanup;
this->err=-2;
return;
}
freeaddrinfo(servinfo);
blockingoff(d->sockfd);
this->err=0;
return;
}
UDPWiimote::~UDPWiimote()
{
close(d->sockfd);
cleanup;
delete d;
}
int UDPWiimote::readPack(void * data, int *size)
{
int numbytes;
size_t addr_len;
struct sockaddr_storage their_addr;
addr_len = sizeof their_addr;
if ((numbytes = recvfrom(d->sockfd, (dataz)data, (*size) , 0,
(struct sockaddr *)&their_addr, (socklen_t*)&addr_len)) == -1) {
if (ERRNO==EWOULDBLOCK)
return -1;
return -2;
} else
(*size)=numbytes;
return 0;
}
#define ACCEL_FLAG (1<<0)
#define BUTT_FLAG (1<<1)
#define IR_FLAG (1<<2)
#define NUN_FLAG (1<<3)
void UDPWiimote::update()
{
u8 bf[64];
int size=60;
int res=0;
u8 time=0;
int nopack=0;
for (int i=0; (res=readPack(&bf,&size)),(i<100)&&(res!=-1); (res<-1)?i++:0)
{
if (res==0)
{
if (bf[0]==0xde)
{
if (bf[1]==0)
time=0;
if (bf[1]>=time) //packet timestamp. assures order is maintained
{
nopack++;
time=bf[1];
u32 *p=(u32*)(&bf[3]);
if (bf[2]&ACCEL_FLAG)
{
double ux,uy,uz;
ux=(double)((s32)ntohl(*p)); p++;
uy=(double)((s32)ntohl(*p)); p++;
uz=(double)((s32)ntohl(*p)); p++;
this->x=ux/1048576; //packet accel data
this->y=uy/1048576;
this->z=uz/1048576;
}
if (bf[2]&BUTT_FLAG)
{
mask=ntohl(*p); p++;
}
if (bf[2]&IR_FLAG)
{
this->pointerX=((double)((s32)ntohl(*p)))/1048576; p++;
this->pointerY=((double)((s32)ntohl(*p)))/1048576; p++;
}
if (bf[2]&NUN_FLAG)
{
this->nunMask=*((u8*)p); p=(u32*)(((u8*)p)+1);
this->nunX=((double)((s32)ntohl(*p)))/1048576; p++;
this->nunY=((double)((s32)ntohl(*p)))/1048576; p++;
}
}
}
}
if (res==-2)
{
ERROR_LOG(WIIMOTE,"UDPWii Packet error");
}
}
//NOTICE_LOG(WIIMOTE,"UDPWii update result:np:%d x:%f y:%f z:%f nx:%f ny:%f px:%f py:%f bmask:%x nmask:%x",
// nopack,this->x,this->y,this->z,this->nunX, this->nunY,this->pointerX,this->pointerY, this->mask, this->nunMask);
}
void UDPWiimote::getAccel(int &x, int &y, int &z)
{
//NOTICE_LOG(WIIMOTE,"%lf %lf %lf",this->x, this-y, this->z);
float xg = WiiMoteEmu::g_wm.cal_g.x;
float yg = WiiMoteEmu::g_wm.cal_g.y;
float zg = WiiMoteEmu::g_wm.cal_g.z;
x = WiiMoteEmu::g_wm.cal_zero.x + (int)(xg * this->x);
y = WiiMoteEmu::g_wm.cal_zero.y + (int)(yg * this->y);
z = WiiMoteEmu::g_wm.cal_zero.z + (int)(zg * this->z);
}
u32 UDPWiimote::getButtons()
{
return mask;
}
void UDPWiimote::getIR(float &x, float &y)
{
x=(float)this->pointerX;
y=(float)this->pointerY;
}
void UDPWiimote::getNunchuck(float &x, float &y, u8 &mask)
{
x=(float)this->nunX;
y=(float)this->nunY;
mask=this->nunMask;
}

View File

@ -0,0 +1,44 @@
#ifndef UDPWIIMOTE_H
#define UDPWIIMOTE_H
#include "Common.h"
#define UDPWM_B1 (1<<0)
#define UDPWM_B2 (1<<1)
#define UDPWM_BA (1<<2)
#define UDPWM_BB (1<<3)
#define UDPWM_BP (1<<4)
#define UDPWM_BM (1<<5)
#define UDPWM_BH (1<<6)
#define UDPWM_BU (1<<7)
#define UDPWM_BD (1<<8)
#define UDPWM_BL (1<<9)
#define UDPWM_BR (1<<10)
#define UDPWM_SK (1<<11)
#define UDPWM_NC (1<<0)
#define UDPWM_NZ (1<<1)
class UDPWiimote
{
public:
UDPWiimote(const char * port);
virtual ~UDPWiimote();
void update();
void getAccel(int &x, int &y, int &z);
u32 getButtons();
void getNunchuck(float &x, float &y, u8 &mask);
void getIR(float &x, float &y);
int getErrNo() {return err;};
private:
int readPack(void * data, int *size);
struct _d; //using pimpl because SOCKET on windows is defined in Winsock2.h, witch doesen't have include guards
_d *d;
double x,y,z;
double nunX,nunY;
double pointerX,pointerY;
u8 nunMask;
u32 mask;
int err;
static int noinst;
};
#endif