Improvements to the current Flick Stick implementation
Description
This Pull Request is made to attempt to fix some of the issues that the current implementation of the Flick Stick has.
I could try to add other additions, but I would probably need help implementing some. Comment if you have ideas for another feature for the Flick Stick.
Progress
- [x] Implement a way to configure (and disable) the Flick Stick animation
- [x] Make the Flick Stick work akin to Steam Input's Mouse simulation Flick Stick, ~~as per described in my comment in issue #506~~ This method didn't work, but I found another method.
Status
Currently everything is implemented, but needs testing.
I have tested the following versions, and they seem to work:
- 1.21.1 Fabric
- 1.21.3 Fabric
- 1.21.4 Fabric
- 1.21.5 Fabric
- 1.21.7 Fabric (This version is no longer available, but I did the first test on this one)
- 1.21.8 Fabric
I've also tested the following mods on 1.21.8 Fabric, and they seem to work:
- Better Third Person
- Shoulder Surfing Reloaded
I would prefer if when turning the Animation timer into 1 it displayed "None" or something akin to that, but I do not know how to implement that.
I can't seem to find a way to get the camera's yaw. I'm guessing it would be within the minecraft.player class, but I can't seem to find where.
Or it could be within minecraft.camera, but I'm unsure if importing it is a good idea.
yaw in yRot in mojmap
I would prefer if when turning the Animation timer into 1 it displayed "None" or something akin to that, but I do not know how to implement that.
.formatValue on the controller
I would prefer if when turning the Animation timer into 1 it displayed "None" or something akin to that, but I do not know how to implement that.
.formatValue on the controller
I'll try using ticksToMillis, but that requires me to implement a check that turns off the animation when it is 0, since 1 tick is 50ms.
Got the toggle working properly, now it's just getting the flick stick working as planned.
EDIT: And changing the strings, since they mention ticks.
yaw in yRot in mojmap
I'm guessing the camera's yRot? The player also has one, being inherited from entity, but I'm unsure as to which...
I have found Camera.getYRot() but I can't seem to be able to use it.
As for the variable yawOrigin, I'm not sure if the value would persist on each call, so it probably needs to be declared outside.
Also, does digitalNow() respect the deadzones? I plan to use it in order to detect when the stick first moved, in order to assign the value to yawOrigin.
I'm really not sure as to how to get the player's camera, since
import net.minecraft.client.Camera
// Other imports
public class InGameInputHandler {
private final Camera camera
...
Doesn't seem to work. I'm guessing I have to initialize the camera to something, like most of the things inside the function public InGameInputHandler, but I don't know to what.
As for the variable
yawOrigin, I'm not sure if the value would persist on each call, so it probably needs to be declared outside.
It indeed needed to be declared outside.
I am currently trying to test what happens if I use the player's yHeadRot instead... My guess is that it might work, but would break Free-Look like mods (Better Third Person, for instance).
I am currently trying to test what happens if I use the player's yHeadRot instead... My guess is that it might work, but would break Free-Look like mods (Better Third Person, for instance).
About that... It breaks the stick orientation fix (AKA the + 90f in flickAngle). Can't seem to find a way to fix that, since the current method is taking the flick stick's direction as an actual angle.
The current method described probably doesn't work for that reason, so I'll edit that out.
So, that means we would need a way to get the original yaw, and use it as an anchor in order to turn based on flickAngle, without messing up the orientation fix.
So, that means we would need a way to get the original yaw, and use it as an anchor in order to turn based on
flickAngle, without messing up the orientation fix.
Found the solution, turns out I was doing the calculations wrong... (oops)
The formula in order to calculate the angle where the camera should be would be:
(yawOrigin + flickAngle) - yawCurrent
Combined with a call to `Mth.wrapDegrees()`, it would end up looking like this:
This is in order to stop the camera from doing a 360 flick when switching from back-left to back-right and vice versafloat yawTurn = Mth.wrapDegrees((float) (yawOrigin + flickAngle) - yawCurrent);
As for implementing it, I still have a doubt:
I figured out that the camera divides the movement by 15º increments, hence having to divide by 0.15, in order to disable that.
TL;DR: I was right with it being a Vanilla animation.
1. What does the / 0.15 do within the player.turn() calls do?
I'm guessing it's done in an attempt to get the flick stick to snap into 90 degree angles, instead of having it flick you into the angle you held. It also disables an animation, which I am guessing is coming from Vanilla?/ 0.15 do within the player.turn() calls do?How could I get the camera's yRot?
I know that the Camera class has the `getYRot()` function for that, but I don't know how to import the camera object. See the previous comment for more context.Beyond that doubt, I'm pretty sure I can implement it to this PR.
I am currently trying to test what happens if I use the player's yHeadRot instead... My guess is that it might work, but would break Free-Look like mods (Better Third Person, for instance).
Sure enough, using the player's yHeadRot, obtained with player.getYHeadRot() breaks Better Third Person. 90º flicks work strange when combined with BTP, sometimes doing a full spin before settling on the angle.
Got it, figured out that you needed to import GameRenderer in order to be able to use getMainCamera().
Still needs testing, but it works on Fabric 1.21.7, and it works somewhat with Better Third Person (Sometimes the flick stick turns the player, but that isn't that bad). The animation also is somewhat glitchy, skipping every so often.
Should fix #506 and #484
Might be interesting to add the Steam Input-like Flick Stick as an option instead of replacing the old method.
I'm not sure as to how to proceed...
I've already stated that it might be interesting to add an option to re-enable the old method of Flick Stick.
As for the animation glitches, those are beyond my modding knowledge, and I would need help in order to fix them.
~~In the case of the testing, I would need to know how to compile for a single version that is older than what's within the versions/current file.~~
EDIT: Just noticed that the Stonecutter CI is now working, I'll close the issue I've made. That fixes this point.
What are your opinions in these matters, @isXander?
On 1.21.8 Fabric it seemingly acts jittery, though it might be caused by my controller, but it seemingly works beyond that.
Tested all Fabric versions, and besides the previously mentioned jitter, they are working properly.
EDIT: Besides 1.21.9, since I can't find which snapshot it would be.
In 1.21.8 Neoforge, it's crashing. But it seems like it's unrelated to this PR, as I tried installing the Modrinth published version, and it's still crashing.
EDIT: Seems like I'm the first one to have this issue, which is strange, to say the least. I'll create an issue.
Currently testing the newer versions, including NeoForge.
Controlify now reports that my controller doesn't have gyro, even though it does.
I'm using a Flydigi Vader 3 Pro, but Controlify used to detect the Gyro whenever it was on it's Switch Pro Controller mode.
I'll check if this isn't exclusive to this PR.
EDIT: It only occurs on this PR, I'll try to find the reason it's happening.
Controlify now reports that my controller doesn't have gyro, even though it does.
I'm using a Flydigi Vader 3 Pro, but Controlify used to detect the Gyro whenever it was on it's Switch Pro Controller mode.
I'll check if this isn't exclusive to this PR.
EDIT: It only occurs on this PR, I'll try to find the reason it's happening.
Worked after starting the game with the controller already connected.
That's all versions tested, although some (Mainly the fabric versions) on different versions of Controlify...
Which leads me: I should probably ask for the review.
The current state of this PR is that it's working, although with a few caveats:
- If the Flick Duration option is 50ms (1 tick), there's a leading 0, which makes it appear as 050ms.
- Without Flick Duration, the camera movement is jittery, but with too much Flick Duration, the camera overshoots and has to bounce back into place. I am not sure if this is my controller or not, but I've found that a Flick Duration of 3 ticks (150ms) works best.
Beyond those, I haven't noticed much issues yet.
EDIT: Just realized that most of the gyro options don't disable when Look Sensitivity is off.
Also, does the newly added Look Input Curve affect Flick Stick?