WhiteMagic / JoystickGremlin

A tool for configuring and managing joystick devices.
http://whitemagic.github.io/JoystickGremlin/
GNU General Public License v3.0
313 stars 46 forks source link

Feature Request: Response Curve Multiplier #410

Closed TheGoodIdeaFairy closed 2 years ago

TheGoodIdeaFairy commented 2 years ago

This is an admittedly niche request, but I would like to be able to modify the curve assigned to one axis by a ratio of the current value of another axis.

Specifically, I'd like to use the Slider on my Virpil Alpha (pinky lever) to vertically "squash" the X, Y, and Z axes for precise and/or slow speed flight control. Essentially the Y axis of the target's response curve would be multiplied by a variable defined by the modifier axis' current value, where at 100% this variable would be 1 and at -100% the variable would be 0. Applying a response curve to the modifier axis would then affect the way this variable changes as the modifier axis is moved.

WhiteMagic commented 2 years ago

Actions in Gremlin do not interact with multiple inputs, a single physical input triggers its associated actions and that is it. Additionally, the response curve classes do not support dynamic scaling and thus a new response curve needs to be created every time an axis value changes or some other mechanism to scale things needs to be used.

While this is all rather easy to implement this is not something action will support and should be implemented with a simple plugin.

TheGoodIdeaFairy commented 2 years ago

I suppose I could probably borrow the logic from merge axis and just change the math that's performed between them to suit. Thanks for pointing out the dynamic scaling issue, that changes the way I view the problem.

WhiteMagic commented 2 years ago

If it's a simple "squishing" then you might be able to get away with just multiplying a constant scalar but that might not be enough. Another odd option could be to have both a response curve on the physical axis and one on the vJoy axis as they will combine. However, that is likely to end up being a headache to work out what happens.

TheGoodIdeaFairy commented 2 years ago

Quick question: is self.axis_values[] in class MergeAxis normalized to say -100..100 or -1..1, or are these raw values? Edit: also, is there a global value somewhere that defines the allowable range of axis values or do you just hardcode these?

WhiteMagic commented 2 years ago

They should be in [-1, 1] as all axis values in Gremlin ought to be in that range. The only place that ever sees raw values is the event handler that receives the DirectInput data which is in [0, 65536] but then normalized and calibrated (if setup) into the [-1, 1] range.

TheGoodIdeaFairy commented 2 years ago

Ok great. Then it looks like I just have to add the function to class MergeAxis in code_runner, add the entry into class MergeAxisOperation in common, and I think there were a couple things I need to add in the UI modules. Should look something like - value = (self.axis_values[0] * ( (self.axis_values[1] + 1) / 2 ) ) )

TheGoodIdeaFairy commented 2 years ago

Hmm, small problem. Looks like Merge Axis doesn't accept vJoy devices... I'll keep digging. Thanks.

WhiteMagic commented 2 years ago

I suspect the easiest way to achieve this is with a plugin, as everything else will require a good amount of mangling of UI and logic inside of Gremlin.

Some starting points might be

The last one is there merely for the response curve parts, as the way in which the device decorator is generated in that example is no longer valid.