Skip to content

Instantly share code, notes, and snippets.

@Ryochan7
Created June 10, 2018 22:15
Show Gist options
  • Save Ryochan7/6c2982a98580fa51a7cdc4e80691ca3e to your computer and use it in GitHub Desktop.
Save Ryochan7/6c2982a98580fa51a7cdc4e80691ca3e to your computer and use it in GitHub Desktop.
Messy experimental DS4Windows version of delta acceleration for stick mouse
diff --git a/DS4Windows/DS4Control/ControlService.cs b/DS4Windows/DS4Control/ControlService.cs
index 3c4ff38..70a81b4 100644
--- a/DS4Windows/DS4Control/ControlService.cs
+++ b/DS4Windows/DS4Control/ControlService.cs
@@ -828,7 +828,11 @@ namespace DS4Windows
if (getEnableTouchToggle(ind))
CheckForTouchToggle(ind, cState, pState);
- cState = Mapping.SetCurveAndDeadzone(ind, cState, TempState[ind]);
+ cState = Mapping.SetCurveAndDeadzone(ind, cState, pState, TempState[ind]);
+ pState.deltaAccelCurrent = cState.deltaAccelCurrent;
+ pState.deltaAccelMulti = cState.deltaAccelMulti;
+ pState.deltaAccelCurrentY = cState.deltaAccelCurrentY;
+ pState.deltaAccelMultiY = cState.deltaAccelMultiY;
if (!recordingMacro && (!string.IsNullOrEmpty(tempprofilename[ind]) ||
containsCustomAction(ind) || containsCustomExtras(ind) ||
diff --git a/DS4Windows/DS4Control/Mapping.cs b/DS4Windows/DS4Control/Mapping.cs
index bb452cc..8744f87 100644
--- a/DS4Windows/DS4Control/Mapping.cs
+++ b/DS4Windows/DS4Control/Mapping.cs
@@ -155,6 +155,26 @@ namespace DS4Windows
private static double[] tempDoubleArray = new double[4] { 0.0, 0.0, 0.0, 0.0 };
private static int[] tempIntArray = new int[4] { 0, 0, 0, 0 };
+ private static double testAccelEasingDuration = 0.3;
+ private static byte previousX = 127;
+ private static double previousXUnit = 0.0;
+ private static byte previousY = 127;
+ private static double previousYUnit = 0.0;
+ private static double testAccelMulti = 5.0;
+ private static double testAccelMinTravel = 0.01;
+ private static double testAccelMaxTravel = 0.24;
+ //private static double testAccelMinOffset = 0.25;
+ private static double testAccelMinFactor = 1.0;
+ private static double accelTravel = 0.0;
+ private static double accelTravelY;
+ private static bool testMultiActive = false;
+ private static bool testMultiActiveY = false;
+ private static byte testStartAccelX = 127;
+ private static byte testStartAccelY = 127;
+ private static Stopwatch testEasingDuration = new Stopwatch();
+ private static Stopwatch testEasingDurationY = new Stopwatch();
+ private static double previousHypo = 0.0;
+
// Special macros
static bool altTabDone = true;
static DateTime altTabNow = DateTime.UtcNow,
@@ -424,7 +444,7 @@ namespace DS4Windows
return (value < min) ? min : (value > max) ? max : value;
}
- public static DS4State SetCurveAndDeadzone(int device, DS4State cState, DS4State dState)
+ public static DS4State SetCurveAndDeadzone(int device, DS4State cState, DS4State pState, DS4State dState)
{
double rotation = tempDoubleArray[device] = getLSRotation(device);
if (rotation > 0.0 || rotation < 0.0)
@@ -434,6 +454,7 @@ namespace DS4Windows
if (rotationRS > 0.0 || rotationRS < 0.0)
cState.rotateRSCoordinates(rotationRS);
+ cState.calculateStickAngles();
cState.CopyTo(dState);
//DS4State dState = new DS4State(cState);
int x;
@@ -664,6 +685,181 @@ namespace DS4Windows
}
}
+ // Calculate delta acceleration slope and offset.
+ double accelSlope = (testAccelMulti - testAccelMinFactor) / (testAccelMaxTravel - testAccelMinTravel);
+ double accelOffset = testAccelMinFactor - (accelSlope * testAccelMinTravel);
+ double minstopDist = Math.Max(6, testAccelMinTravel * 127.0);
+ double minstop = minstopDist / 127.0;
+
+ if (Math.Abs(dState.RX) != 127 && Math.Abs(previousX - cState.RX) >= 2 &&
+ (cState.RX - previousX >= 0) == (cState.RX >= 127))
+ {
+ double tempTravel = Math.Min(Math.Abs(previousX - cState.RX) / 125.0, testAccelMaxTravel);
+ double tempDist = Math.Min(tempTravel, testAccelMaxTravel);
+
+ dState.deltaAccelMulti = dState.deltaAccelCurrent =
+ (accelSlope * tempDist + accelOffset);
+ double getMultiDiff2 = ((dState.deltaAccelMulti - testAccelMinFactor) / (testAccelMulti - testAccelMinFactor));
+ dState.deltaAccelMulti = dState.deltaAccelCurrent =
+ -(testAccelMulti - testAccelMinFactor) * (getMultiDiff2) * ((getMultiDiff2) - 2) + testAccelMinFactor;
+ //dState.deltaAccelMulti = dState.deltaAccelCurrent =
+ //-(testAccelMulti - testAccelMinFactor) * (dState.deltaAccelCurrent / testAccelMulti) * ((dState.deltaAccelCurrent / testAccelMulti) - 2) + 1.0;
+ previousX = testStartAccelX = cState.RX;
+ previousXUnit = cState.RXUnit;
+ accelTravel = tempTravel;
+ testEasingDuration.Restart();
+ testMultiActive = true;
+ }
+ else if (Math.Abs(dState.RX) != 127 && testMultiActive && pState.deltaAccelMulti > 1.0 &&
+ Math.Abs(cState.RX - testStartAccelX) < minstopDist &&
+ (cState.RX >= 127) == (previousX >= 127))
+ {
+ double timeElapsed = testEasingDuration.ElapsedMilliseconds;
+ double elapsedDiff = 1.0;
+ double tempAccel = pState.deltaAccelMulti;
+ double tempTravel = accelTravel;
+
+ if ((cState.RX - testStartAccelX >= 0.0) != (cState.RX > 127))
+ {
+ // Travelling towards dead zone. Decrease acceleration and duration.
+ double minstop2 = Math.Min(minstop, tempTravel);
+ double tempmix2 = Math.Abs(cState.RX - testStartAccelX) / 125.0;
+ tempmix2 = Math.Min(tempmix2, minstop2);
+
+ double tempmixslope = (testAccelMinTravel - tempTravel) / (minstop2);
+ double tempintercept = tempTravel;
+
+ double finalmanham = (tempmixslope * tempmix2 + tempintercept);
+ //tempAccel = finalmanham;
+ tempTravel = finalmanham;
+ tempAccel = (accelSlope * tempTravel + accelOffset);
+ }
+
+ double getMultiDiff2 = (tempAccel - testAccelMinFactor) / (testAccelMulti - testAccelMinFactor);
+ double temper = getMultiDiff2 * (getMultiDiff2 - 2);
+ //double elapsedDuration = testAccelEasingDuration * (tempAccel / testAccelMulti);
+ //double temper = (tempAccel / testAccelMulti) * ((tempAccel / testAccelMulti) - 2);
+ double elapsedDuration = -testAccelEasingDuration * temper;
+ tempAccel = -(testAccelMulti - testAccelMinFactor) * temper + testAccelMinFactor;
+ if (elapsedDuration > 0.0 && (timeElapsed * 0.001) < elapsedDuration)
+ {
+ elapsedDiff = ((timeElapsed * 0.001) / elapsedDuration);
+ elapsedDiff = (1.0 - tempAccel) * (elapsedDiff * elapsedDiff * elapsedDiff) + tempAccel;
+ dState.deltaAccelCurrent = elapsedDiff;
+ }
+ else
+ {
+ // Easing time has ended. Reset values.
+ previousXUnit = cState.RXUnit;
+ previousX = testStartAccelX = cState.RX;
+ dState.deltaAccelMulti = 1.0;
+ dState.deltaAccelCurrent = 1.0;
+ accelTravel = 0;
+ testMultiActive = false;
+ if (testEasingDuration.IsRunning)
+ {
+ testEasingDuration.Stop();
+ }
+ }
+ }
+ else
+ {
+ previousXUnit = cState.RXUnit;
+ previousX = testStartAccelX = cState.RX;
+ dState.deltaAccelMulti = 1.0;
+ dState.deltaAccelCurrent = 1.0;
+ accelTravel = 0;
+ testMultiActive = false;
+ if (testEasingDuration.IsRunning)
+ {
+ testEasingDuration.Stop();
+ }
+ }
+
+ if (Math.Abs(dState.RY) != 127 && Math.Abs(previousY - cState.RY) >= 2 &&
+ (cState.RY - previousY >= 0) == (cState.RY >= 127))
+ {
+ double tempTravel = Math.Min(Math.Abs(previousY - cState.RY) / 125.0, testAccelMaxTravel);
+ double tempDist = Math.Min(tempTravel, testAccelMaxTravel);
+
+ dState.deltaAccelMultiY = dState.deltaAccelCurrentY =
+ (accelSlope * tempDist + accelOffset);
+ double getMultiDiff2 = ((dState.deltaAccelMultiY - testAccelMinFactor) / (testAccelMulti - testAccelMinFactor));
+ dState.deltaAccelMultiY = dState.deltaAccelCurrentY =
+ -(testAccelMulti - testAccelMinFactor) * (getMultiDiff2) * ((getMultiDiff2) - 2) + testAccelMinFactor;
+ //dState.deltaAccelMultiY = dState.deltaAccelCurrentY =
+ //-(testAccelMulti - testAccelMinFactor) * (dState.deltaAccelCurrentY / testAccelMulti) * ((dState.deltaAccelCurrentY / testAccelMulti) - 2) + 1.0;
+ previousY = testStartAccelY = cState.RY;
+ previousYUnit = cState.RYUnit;
+ accelTravelY = tempTravel;
+ testEasingDurationY.Restart();
+ testMultiActiveY = true;
+ }
+ else if (Math.Abs(dState.RY) != 127 && testMultiActiveY && pState.deltaAccelMultiY > 1.0 &&
+ Math.Abs(cState.RY - testStartAccelY) < minstopDist &&
+ (cState.RY >= 127) == (previousY >= 127))
+ {
+ double timeElapsed = testEasingDurationY.ElapsedMilliseconds;
+ double elapsedDiff = 1.0;
+ double tempAccel = pState.deltaAccelMultiY;
+ double tempTravel = accelTravelY;
+
+ if ((cState.RY - testStartAccelY >= 0.0) != (cState.RY > 127))
+ {
+ // Travelling towards dead zone. Decrease acceleration and duration.
+ double minstop2 = Math.Min(minstop, tempTravel);
+ double tempmix2 = Math.Abs(cState.RY - testStartAccelY) / 125.0;
+ tempmix2 = Math.Min(tempmix2, minstop2);
+
+ double tempmixslope = (testAccelMinTravel - tempTravel) / (minstop2);
+ double tempintercept = tempTravel;
+
+ double finalmanham = (tempmixslope * tempmix2 + tempintercept);
+ //tempAccel = finalmanham;
+ tempTravel = finalmanham;
+ tempAccel = (accelSlope * tempTravel + accelOffset);
+ }
+
+ //double elapsedDuration = testAccelEasingDuration * (tempAccel / testAccelMulti);
+ double getMultiDiff2 = (tempAccel - testAccelMinFactor) / (testAccelMulti - testAccelMinFactor);
+ double temper = getMultiDiff2 * (getMultiDiff2 - 2);
+ double elapsedDuration = -testAccelEasingDuration * temper;
+ tempAccel = -(testAccelMulti - testAccelMinFactor) * temper + testAccelMinFactor;
+ if (elapsedDuration > 0.0 && (timeElapsed * 0.001) < elapsedDuration)
+ {
+ elapsedDiff = ((timeElapsed * 0.001) / elapsedDuration);
+ elapsedDiff = (1.0 - tempAccel) * (elapsedDiff * elapsedDiff * elapsedDiff) + tempAccel;
+ dState.deltaAccelCurrentY = elapsedDiff;
+ }
+ else
+ {
+ // Easing time has ended. Reset values.
+ previousYUnit = cState.RYUnit;
+ previousY = testStartAccelY = cState.RY;
+ dState.deltaAccelMultiY = 1.0;
+ dState.deltaAccelCurrentY = 1.0;
+ accelTravelY = 0;
+ testMultiActiveY = false;
+ if (testEasingDurationY.IsRunning)
+ {
+ testEasingDurationY.Stop();
+ }
+ }
+ }
+ else
+ {
+ previousYUnit = cState.RYUnit;
+ previousY = testStartAccelY = cState.RY;
+ dState.deltaAccelMultiY = 1.0;
+ dState.deltaAccelCurrentY = 1.0;
+ accelTravelY = 0;
+ testMultiActiveY = false;
+ if (testEasingDurationY.IsRunning)
+ {
+ testEasingDurationY.Stop();
+ }
+ }
+
byte l2Deadzone = getL2Deadzone(device);
int l2AntiDeadzone = getL2AntiDeadzone(device);
int l2Maxzone = getL2Maxzone(device);
@@ -2543,6 +2739,7 @@ namespace DS4Windows
//tempMouseOffsetX = MOUSESTICKOFFSET;
//tempMouseOffsetX = Math.Abs(Math.Cos(cState.RSAngleRad)) * MOUSESTICKOFFSET;
value = ((speed * MOUSESPEEDFACTOR * (timeElapsed * 0.001)) - tempMouseOffsetX) * diff + (tempMouseOffsetX * -1.0);
+ value = value * cState.deltaAccelCurrent;
//value = diff * MOUSESPEEDFACTOR * (timeElapsed * 0.001) * speed;
//value = -(cState.RX - 127 - deadzoneR) / 2550d * speed;
}
@@ -2558,6 +2755,7 @@ namespace DS4Windows
//tempMouseOffsetX = MOUSESTICKOFFSET;
//tempMouseOffsetX = Math.Abs(Math.Cos(cState.RSAngleRad)) * MOUSESTICKOFFSET;
value = ((speed * MOUSESPEEDFACTOR * (timeElapsed * 0.001)) - tempMouseOffsetX) * diff + tempMouseOffsetX;
+ value = value * cState.deltaAccelCurrent;
//value = diff * MOUSESPEEDFACTOR * (timeElapsed * 0.001) * speed;
//value = (cState.RX - 127 + deadzoneR) / 2550d * speed;
}
@@ -2603,6 +2801,7 @@ namespace DS4Windows
//tempMouseOffsetY = MOUSESTICKOFFSET;
//tempMouseOffsetY = Math.Abs(Math.Sin(cState.RSAngleRad)) * MOUSESTICKOFFSET;
value = ((speed * MOUSESPEEDFACTOR * (timeElapsed * 0.001)) - tempMouseOffsetY) * diff + (tempMouseOffsetY * -1.0);
+ value = value * cState.deltaAccelCurrentY;
//value = diff * MOUSESPEEDFACTOR * (timeElapsed * 0.001) * speed;
//value = -(cState.RY - 127 - deadzoneR) / 2550d * speed;
}
@@ -2618,6 +2817,7 @@ namespace DS4Windows
//tempMouseOffsetY = MOUSESTICKOFFSET;
//tempMouseOffsetY = Math.Abs(Math.Sin(cState.RSAngleRad)) * MOUSESTICKOFFSET;
value = ((speed * MOUSESPEEDFACTOR * (timeElapsed * 0.001)) - tempMouseOffsetY) * diff + tempMouseOffsetY;
+ value = value * cState.deltaAccelCurrentY;
//value = diff * MOUSESPEEDFACTOR * (timeElapsed * 0.001) * speed;
//value = (cState.RY - 127 + deadzoneR) / 2550d * speed;
}
diff --git a/DS4Windows/DS4Library/DS4State.cs b/DS4Windows/DS4Library/DS4State.cs
index c909780..8e05f4b 100644
--- a/DS4Windows/DS4Library/DS4State.cs
+++ b/DS4Windows/DS4Library/DS4State.cs
@@ -24,6 +24,10 @@ namespace DS4Windows
public double RXUnit;
public double RYUnit;
public double elapsedTime = 0.0;
+ public double deltaAccelMulti = 1.0;
+ public double deltaAccelCurrent = 1.0;
+ public double deltaAccelMultiY = 1.0;
+ public double deltaAccelCurrentY = 1.0;
public SixAxis Motion = null;
public static readonly int DEFAULT_AXISDIR_VALUE = 127;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment