Added 2nd device FFB for Outrunners
This commit is contained in:
parent
d5bef2b65b
commit
2e355445a1
@ -6,6 +6,7 @@ struct EffectTriggers {
|
|||||||
void(*Spring)(double strength);
|
void(*Spring)(double strength);
|
||||||
void(*Friction)(double strength);
|
void(*Friction)(double strength);
|
||||||
void(*Sine)(UINT16 period, UINT16 fadePeriod, double strength);
|
void(*Sine)(UINT16 period, UINT16 fadePeriod, double strength);
|
||||||
|
void(*SineDevice2)(UINT16 period, UINT16 fadePeriod, double strength);
|
||||||
void(*Rumble)(double lowfrequency, double highfrequency, double length);
|
void(*Rumble)(double lowfrequency, double highfrequency, double length);
|
||||||
void(*RumbleDevice2)(double lowfrequency, double highfrequency, double length);
|
void(*RumbleDevice2)(double lowfrequency, double highfrequency, double length);
|
||||||
void(*LeftRight)(double smallstrength, double largestrength, double length);
|
void(*LeftRight)(double smallstrength, double largestrength, double length);
|
||||||
@ -28,6 +29,7 @@ public:
|
|||||||
int effect_friction_id;
|
int effect_friction_id;
|
||||||
int effect_leftright_id;
|
int effect_leftright_id;
|
||||||
int effect_sine_id;
|
int effect_sine_id;
|
||||||
|
int effect_sine_id_device2;
|
||||||
int effect_spring_id;
|
int effect_spring_id;
|
||||||
int effect_vibration_id;
|
int effect_vibration_id;
|
||||||
int effect_inertia_id;
|
int effect_inertia_id;
|
||||||
|
@ -240,6 +240,16 @@ FeedbackLength=500
|
|||||||
|
|
||||||
[Output Reading]
|
[Output Reading]
|
||||||
GameId=22
|
GameId=22
|
||||||
|
Device2GUID=
|
||||||
|
MinForceDevice2=0
|
||||||
|
MaxForceDevice2=100
|
||||||
|
EnableRumbleDevice2=1
|
||||||
|
ReverseRumbleDevice2=0
|
||||||
|
AlternativeFFBDevice2=0
|
||||||
|
AlternativeMinForceLeftDevice2=0
|
||||||
|
AlternativeMaxForceLeftDevice2=-100
|
||||||
|
AlternativeMinForceRightDevice2=0
|
||||||
|
AlternativeMaxForceRightDevice2=100
|
||||||
|
|
||||||
[Outrun 2 Special Tours Deluxe Custom]
|
[Outrun 2 Special Tours Deluxe Custom]
|
||||||
GameId=12
|
GameId=12
|
||||||
|
106
DllMain.cpp
106
DllMain.cpp
@ -867,6 +867,15 @@ int configAlternativeMaxForceLeft = GetPrivateProfileInt(TEXT("Settings"), TEXT(
|
|||||||
int configAlternativeMinForceRight = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMinForceRight"), 0, settingsFilename);
|
int configAlternativeMinForceRight = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMinForceRight"), 0, settingsFilename);
|
||||||
int configAlternativeMaxForceRight = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMaxForceRight"), 100, settingsFilename);
|
int configAlternativeMaxForceRight = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMaxForceRight"), 100, settingsFilename);
|
||||||
int ForceShowDeviceGUIDMessageBox = GetPrivateProfileInt(TEXT("Settings"), TEXT("ForceShowDeviceGUIDMessageBox"), 0, settingsFilename);
|
int ForceShowDeviceGUIDMessageBox = GetPrivateProfileInt(TEXT("Settings"), TEXT("ForceShowDeviceGUIDMessageBox"), 0, settingsFilename);
|
||||||
|
int configMinForceDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("MinForceDevice2"), 0, settingsFilename);
|
||||||
|
int configMaxForceDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("MaxForceDevice2"), 100, settingsFilename);
|
||||||
|
int EnableRumbleDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("EnableRumbleDevice2"), 0, settingsFilename);
|
||||||
|
int ReverseRumbleDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("ReverseRumbleDevice2"), 0, settingsFilename);
|
||||||
|
int AlternativeFFBDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeFFB"), 0, settingsFilename);
|
||||||
|
int configAlternativeMinForceLeftDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMinForceLeftDevice2"), 0, settingsFilename);
|
||||||
|
int configAlternativeMaxForceLeftDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMaxForceLeftDevice2"), 100, settingsFilename);
|
||||||
|
int configAlternativeMinForceRightDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMinForceRightDevice2"), 0, settingsFilename);
|
||||||
|
int configAlternativeMaxForceRightDevice2 = GetPrivateProfileInt(TEXT("Settings"), TEXT("AlternativeMaxForceRightDevice2"), 100, settingsFilename);
|
||||||
|
|
||||||
char chainedDLL[256];
|
char chainedDLL[256];
|
||||||
|
|
||||||
@ -1071,6 +1080,17 @@ void Initialize(int device_index)
|
|||||||
tempEffect.condition.length = 5000;
|
tempEffect.condition.length = 5000;
|
||||||
effects.effect_sawtoothdown_id = SDL_HapticNewEffect(haptic, &tempEffect);
|
effects.effect_sawtoothdown_id = SDL_HapticNewEffect(haptic, &tempEffect);
|
||||||
|
|
||||||
|
if (haptic2 != NULL)
|
||||||
|
{
|
||||||
|
SDL_HapticEffect tempEffect2;
|
||||||
|
SDL_memset(&tempEffect2, 0, sizeof(SDL_HapticEffect));
|
||||||
|
tempEffect2 = SDL_HapticEffect();
|
||||||
|
tempEffect2.type = SDL_HAPTIC_SINE;
|
||||||
|
tempEffect2.constant.direction.type = SDL_HAPTIC_CARTESIAN;
|
||||||
|
effects.effect_sine_id_device2 = SDL_HapticNewEffect(haptic2, &tempEffect2);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// TODO: why don't we just define this as hackFix = true in the other file?
|
// TODO: why don't we just define this as hackFix = true in the other file?
|
||||||
// Was there a reason to put it here?
|
// Was there a reason to put it here?
|
||||||
// extern bool hackFix;
|
// extern bool hackFix;
|
||||||
@ -1080,8 +1100,11 @@ void Initialize(int device_index)
|
|||||||
|
|
||||||
using namespace std::chrono;
|
using namespace std::chrono;
|
||||||
std::chrono::milliseconds timeOfLastSineEffect = duration_cast<milliseconds>(system_clock::now().time_since_epoch());
|
std::chrono::milliseconds timeOfLastSineEffect = duration_cast<milliseconds>(system_clock::now().time_since_epoch());
|
||||||
|
std::chrono::milliseconds timeOfLastSineEffectDevice2 = duration_cast<milliseconds>(system_clock::now().time_since_epoch());
|
||||||
double lastSineEffectStrength = 0;
|
double lastSineEffectStrength = 0;
|
||||||
|
double lastSineEffectStrengthDevice2 = 0;
|
||||||
double lastSineEffectPeriod = 0;
|
double lastSineEffectPeriod = 0;
|
||||||
|
double lastSineEffectPeriodDevice2 = 0;
|
||||||
void TriggerConstantEffect(int direction, double strength)
|
void TriggerConstantEffect(int direction, double strength)
|
||||||
{
|
{
|
||||||
SDL_HapticEffect tempEffect;
|
SDL_HapticEffect tempEffect;
|
||||||
@ -1433,6 +1456,80 @@ void TriggerSineEffect(UINT16 period, UINT16 fadePeriod, double strength)
|
|||||||
lastSineEffectPeriod = period;
|
lastSineEffectPeriod = period;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void TriggerSineEffectDevice2(UINT16 period, UINT16 fadePeriod, double strength)
|
||||||
|
{
|
||||||
|
std::chrono::milliseconds now = duration_cast<milliseconds>(system_clock::now().time_since_epoch());
|
||||||
|
long long elapsedTime = (std::chrono::duration_cast<std::chrono::milliseconds>(now - timeOfLastSineEffectDevice2)).count();
|
||||||
|
|
||||||
|
int direction = 1;
|
||||||
|
if (strength < -0.001) {
|
||||||
|
strength *= -1;
|
||||||
|
direction = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// if no strength, we do nothing
|
||||||
|
if (strength <= 0.001) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// we ignore the new effect until the last one is completed, unless the new one is significantly stronger
|
||||||
|
if (elapsedTime < lastSineEffectPeriodDevice2 && strength < (lastSineEffectStrengthDevice2 * 1.5)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
SDL_HapticEffect tempEffect;
|
||||||
|
SDL_memset(&tempEffect, 0, sizeof(SDL_HapticEffect));
|
||||||
|
hlp.log("Doing Device2 sine...");
|
||||||
|
tempEffect.type = SDL_HAPTIC_SINE;
|
||||||
|
tempEffect.periodic.direction.type = SDL_HAPTIC_CARTESIAN;
|
||||||
|
tempEffect.periodic.direction.dir[0] = direction;
|
||||||
|
tempEffect.constant.direction.dir[1] = 0; //Y Position
|
||||||
|
tempEffect.periodic.period = period;
|
||||||
|
|
||||||
|
int confMinForce = configMinForceDevice2;
|
||||||
|
int confMaxForce = configMaxForceDevice2;
|
||||||
|
if (AlternativeFFBDevice2 == 1)
|
||||||
|
{
|
||||||
|
if (direction == -1)
|
||||||
|
{
|
||||||
|
confMinForce = configAlternativeMinForceLeftDevice2;
|
||||||
|
confMaxForce = configAlternativeMaxForceLeftDevice2;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
confMinForce = configAlternativeMinForceRightDevice2;
|
||||||
|
confMaxForce = configAlternativeMaxForceRightDevice2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
SHORT minForce = (SHORT)(strength > 0.001 ? (confMinForce / 100.0 * 32767.0) : 0); // strength is a double so we do an epsilon check of 0.001 instead of > 0.
|
||||||
|
SHORT maxForce = (SHORT)(confMaxForce / 100.0 * 32767.0);
|
||||||
|
SHORT range = maxForce - minForce;
|
||||||
|
SHORT magnitude = (SHORT)(strength * range + minForce);
|
||||||
|
if (range > 0 && magnitude < 0)
|
||||||
|
{
|
||||||
|
magnitude = 32767;
|
||||||
|
}
|
||||||
|
else if (range < 0 && magnitude > 0)
|
||||||
|
{
|
||||||
|
magnitude = -32767;
|
||||||
|
}
|
||||||
|
|
||||||
|
tempEffect.periodic.magnitude = (SHORT)(magnitude);
|
||||||
|
tempEffect.periodic.length = period;
|
||||||
|
tempEffect.periodic.attack_length = fadePeriod;
|
||||||
|
tempEffect.periodic.fade_length = fadePeriod;
|
||||||
|
|
||||||
|
SDL_HapticUpdateEffect(haptic2, effects.effect_sine_id_device2, &tempEffect);
|
||||||
|
SDL_HapticRunEffect(haptic2, effects.effect_sine_id_device2, 1);
|
||||||
|
|
||||||
|
/*int supported = SDL_HapticEffectSupported(haptic, &tempEffect);
|
||||||
|
hlp.log((char *)std::to_string(supported).c_str());*/
|
||||||
|
|
||||||
|
timeOfLastSineEffectDevice2 = now;
|
||||||
|
lastSineEffectStrengthDevice2 = strength;
|
||||||
|
lastSineEffectPeriodDevice2 = period;
|
||||||
|
}
|
||||||
|
|
||||||
void TriggerSpringEffectWithDefaultOption(double strength, bool isDefault)
|
void TriggerSpringEffectWithDefaultOption(double strength, bool isDefault)
|
||||||
{
|
{
|
||||||
SDL_HapticEffect tempEffect;
|
SDL_HapticEffect tempEffect;
|
||||||
@ -1607,7 +1704,7 @@ void TriggerRumbleEffect(double highfrequency, double lowfrequency, double lengt
|
|||||||
|
|
||||||
void TriggerRumbleEffectDevice2(double highfrequency, double lowfrequency, double length)
|
void TriggerRumbleEffectDevice2(double highfrequency, double lowfrequency, double length)
|
||||||
{
|
{
|
||||||
if (EnableRumble == 1)
|
if (EnableRumbleDevice2 == 1)
|
||||||
{
|
{
|
||||||
DWORD minForceLow = (DWORD)(lowfrequency > 0.001 ? (configMinForce / 100.0 * 65535.0) : 0);
|
DWORD minForceLow = (DWORD)(lowfrequency > 0.001 ? (configMinForce / 100.0 * 65535.0) : 0);
|
||||||
DWORD minForceHigh = (DWORD)(highfrequency > 0.001 ? (configMinForce / 100.0 * 65535.0) : 0);
|
DWORD minForceHigh = (DWORD)(highfrequency > 0.001 ? (configMinForce / 100.0 * 65535.0) : 0);
|
||||||
@ -1617,12 +1714,12 @@ void TriggerRumbleEffectDevice2(double highfrequency, double lowfrequency, doubl
|
|||||||
DWORD LowMotor = (DWORD)(lowfrequency * rangeLow + minForceLow);
|
DWORD LowMotor = (DWORD)(lowfrequency * rangeLow + minForceLow);
|
||||||
DWORD HighMotor = (DWORD)(highfrequency * rangeHigh + minForceHigh);
|
DWORD HighMotor = (DWORD)(highfrequency * rangeHigh + minForceHigh);
|
||||||
|
|
||||||
if (ReverseRumble == 1)
|
if (ReverseRumbleDevice2 == 1)
|
||||||
{
|
{
|
||||||
int ReverseRumble2 = SDL_JoystickRumble(GameController2, HighMotor, LowMotor, length);
|
int ReverseRumble2 = SDL_JoystickRumble(GameController2, HighMotor, LowMotor, length);
|
||||||
if (ReverseRumble2 == -1)
|
if (ReverseRumble2 == -1)
|
||||||
{
|
{
|
||||||
EnableRumble = 0;
|
EnableRumbleDevice2 = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -1630,7 +1727,7 @@ void TriggerRumbleEffectDevice2(double highfrequency, double lowfrequency, doubl
|
|||||||
int Rumble2 = SDL_JoystickRumble(GameController2, LowMotor, HighMotor, length);
|
int Rumble2 = SDL_JoystickRumble(GameController2, LowMotor, HighMotor, length);
|
||||||
if (Rumble2 == -1)
|
if (Rumble2 == -1)
|
||||||
{
|
{
|
||||||
EnableRumble = 0;
|
EnableRumbleDevice2 = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1691,6 +1788,7 @@ DWORD WINAPI FFBLoop(LPVOID lpParam)
|
|||||||
t.Spring = &TriggerSpringEffect;
|
t.Spring = &TriggerSpringEffect;
|
||||||
t.Friction = &TriggerFrictionEffect;
|
t.Friction = &TriggerFrictionEffect;
|
||||||
t.Sine = &TriggerSineEffect;
|
t.Sine = &TriggerSineEffect;
|
||||||
|
t.SineDevice2 = &TriggerSineEffectDevice2;
|
||||||
t.Rumble = &TriggerRumbleEffect;
|
t.Rumble = &TriggerRumbleEffect;
|
||||||
t.RumbleDevice2 = &TriggerRumbleEffectDevice2;
|
t.RumbleDevice2 = &TriggerRumbleEffectDevice2;
|
||||||
t.LeftRight = &TriggerLeftRightEffect;
|
t.LeftRight = &TriggerLeftRightEffect;
|
||||||
|
@ -28,6 +28,8 @@ static wchar_t* settingsFilename = TEXT(".\\FFBPlugin.ini");
|
|||||||
static int MinimumSpringStrength = GetPrivateProfileInt(TEXT("Settings"), TEXT("MinimumSpringStrength"), 0, settingsFilename);
|
static int MinimumSpringStrength = GetPrivateProfileInt(TEXT("Settings"), TEXT("MinimumSpringStrength"), 0, settingsFilename);
|
||||||
|
|
||||||
static bool init = false;
|
static bool init = false;
|
||||||
|
static bool MAEffect = false;
|
||||||
|
static bool MBEffect = false;
|
||||||
|
|
||||||
HINSTANCE hInstance;
|
HINSTANCE hInstance;
|
||||||
HINSTANCE hPrevInstance;
|
HINSTANCE hPrevInstance;
|
||||||
@ -1711,6 +1713,7 @@ void OutputReading::FFBLoop(EffectConstants* constants, Helpers* helpers, Effect
|
|||||||
SDL_HapticRumbleInit;
|
SDL_HapticRumbleInit;
|
||||||
SDL_HapticRumbleInit(ControllerHaptic2);
|
SDL_HapticRumbleInit(ControllerHaptic2);
|
||||||
}
|
}
|
||||||
|
SDL_HapticSetGain(haptic2, 100);
|
||||||
}
|
}
|
||||||
|
|
||||||
char* name = new char[256];
|
char* name = new char[256];
|
||||||
@ -2074,8 +2077,6 @@ void OutputReading::FFBLoop(EffectConstants* constants, Helpers* helpers, Effect
|
|||||||
|
|
||||||
if (hWnd45 > NULL) //OutRunners
|
if (hWnd45 > NULL) //OutRunners
|
||||||
{
|
{
|
||||||
static bool MAEffect = false;
|
|
||||||
static bool MBEffect = false;
|
|
||||||
|
|
||||||
if (name == MA_Steering_Wheel_motor)
|
if (name == MA_Steering_Wheel_motor)
|
||||||
{
|
{
|
||||||
@ -2109,21 +2110,25 @@ void OutputReading::FFBLoop(EffectConstants* constants, Helpers* helpers, Effect
|
|||||||
if (MAEffect)
|
if (MAEffect)
|
||||||
{
|
{
|
||||||
triggers->Sine(100, 0, 1.0);
|
triggers->Sine(100, 0, 1.0);
|
||||||
|
triggers->Rumble(1.0, 1.0, 100);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!MAEffect)
|
if (!MAEffect)
|
||||||
{
|
{
|
||||||
triggers->Sine(0, 0, 0);
|
triggers->Sine(0, 0, 0);
|
||||||
|
triggers->Rumble(0, 0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (MBEffect)
|
if (MBEffect)
|
||||||
{
|
{
|
||||||
// Need to add device 2
|
triggers->SineDevice2(100, 0, 1.0);
|
||||||
|
triggers->RumbleDevice2(1.0, 1.0, 100);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!MBEffect)
|
if (!MBEffect)
|
||||||
{
|
{
|
||||||
// Need to add device 2
|
triggers->SineDevice2(0, 0, 0);
|
||||||
|
triggers->RumbleDevice2(0, 0, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
Loading…
Reference in New Issue
Block a user