Skip to content

Commit

Permalink
Take roll into account for movement, bypass pitch ascent
Browse files Browse the repository at this point in the history
  • Loading branch information
gdavid04 committed Feb 19, 2024
1 parent 3127e7e commit 9aaa49d
Show file tree
Hide file tree
Showing 4 changed files with 60 additions and 10 deletions.
5 changes: 4 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,10 @@ A WIP space mod for Fabric 1.20.1 with 6DOF movement.
## Zero gravity space
- [x] no gravity
- [x] swim movement
- [ ] no swim up/down based on pitch
- [x] no swim up/down based on pitch
- [ ] swim up/down based on jump/sneak
- [ ] correct on ground to use all surface orientations
- [ ] disable jumping or make it work in all directions
- [x] no fall damage
- [ ] bump into wall damage regardless of direction
- [ ] make mob AI less helpless
Expand All @@ -22,6 +24,7 @@ A WIP space mod for Fabric 1.20.1 with 6DOF movement.
- [x] camera
- [ ] fix glitch when looking upside down (gimbal lock?)
- [ ] fix frustum culling
- [ ] fix debug cursor orientation
- [x] model pose
- [x] look around
- [ ] fix first person model acting weird on some rotations
Expand Down
2 changes: 2 additions & 0 deletions src/main/java/gdavid/sixdoftest/IRoll.java
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@ public interface IRoll {
*/
void rotate(float dr, float dx, float dy);

float getRollf();

/**
* Get the interpolated roll.
*/
Expand Down
16 changes: 16 additions & 0 deletions src/main/java/gdavid/sixdoftest/mixin/EntityMixin.java
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
import net.minecraft.client.util.GlfwUtil;
import net.minecraft.entity.Entity;
import net.minecraft.entity.data.TrackedData;
import net.minecraft.util.math.Vec3d;
import org.spongepowered.asm.mixin.Final;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;
Expand Down Expand Up @@ -76,5 +77,20 @@ private void rollLook(double dx, double dy, CallbackInfo callback) {
if (self().getVehicle() != null) self().getVehicle().onPassengerLookAround(self()); // Stay consistent with vanilla behavior
callback.cancel(); // We already handled mouse look
}

@Inject(method = "updateVelocity", at = @At("HEAD"), cancellable = true)
private void movementIn6DOFSpace(float speed, Vec3d movementInput, CallbackInfo callback) {
if (!SpaceManager.isIn6dof(self()) || !(self() instanceof IRoll roll)) return;
callback.cancel();
double sqMag = movementInput.lengthSquared();
if (sqMag < 1e-7) return;
// Perform voodoo magic on coordinates
Vec3d vel = (sqMag > 1 ? movementInput.normalize() : movementInput).multiply(speed)
.rotateZ((float) Math.toRadians(roll.getRollf()))
.rotateX((float) Math.toRadians(self().getPitch()))
.rotateY(-(float) Math.toRadians(self().getYaw()))
.multiply(1, -1, 1); // Up is down
self().setVelocity(self().getVelocity().add(vel));
}

}
47 changes: 38 additions & 9 deletions src/main/java/gdavid/sixdoftest/mixin/PlayerEntityMixin.java
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,16 @@

import gdavid.sixdoftest.IRoll;
import gdavid.sixdoftest.SpaceManager;
import net.minecraft.entity.EntityType;
import net.minecraft.entity.LivingEntity;
import net.minecraft.entity.player.PlayerAbilities;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraft.util.math.MathHelper;
import net.minecraft.util.math.Vec3d;
import net.minecraft.world.World;
import org.joml.*;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;
import org.spongepowered.asm.mixin.Unique;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
Expand All @@ -14,8 +20,14 @@
import java.lang.Math;

@Mixin(PlayerEntity.class)
public class PlayerEntityMixin implements IRoll {

public abstract class PlayerEntityMixin extends LivingEntity implements IRoll {

@Shadow public abstract PlayerAbilities getAbilities();

private PlayerEntityMixin(EntityType<? extends LivingEntity> entityType, World world) {
super(entityType, world);
}

@Unique
private PlayerEntity self() {
return (PlayerEntity) (Object) this;
Expand All @@ -36,13 +48,13 @@ public void rotate(float dr, float dx, float dy) {
.rotateZ(Math.toRadians(dr))
.rotateX(Math.toRadians(dy))
.rotateY(Math.toRadians(dx));
Vector3d cur = rotate(new Vector3d(self().getPitch(), self().getYaw(), roll), rot);
Vector3d prev = rotate(new Vector3d(self().prevPitch, self().prevYaw, prevRoll), rot);
self().setPitch((float) cur.x);
self().setYaw((float) cur.y);
Vector3d cur = rotate(new Vector3d(getPitch(), getYaw(), roll), rot);
Vector3d prev = rotate(new Vector3d(prevPitch, prevYaw, prevRoll), rot);
setPitch((float) cur.x);
setYaw((float) cur.y);
roll = (float) cur.z;
self().prevPitch = (float) prev.x;
self().prevYaw = (float) prev.y;
prevPitch = (float) prev.x;
prevYaw = (float) prev.y;
prevRoll = (float) prev.z;
}

Expand All @@ -56,6 +68,11 @@ private Vector3d rotate(Vector3d base, Quaterniond rot) {
.getEulerAnglesZXY(new Vector3d())
.mul(180 / Math.PI);
}

@Override
public float getRollf() {
return roll;
}

@Override
public float getRollf(float partialTicks) {
Expand All @@ -66,11 +83,23 @@ public float getRollf(float partialTicks) {
private void updateRoll(CallbackInfo callback) {
prevRoll = roll;
// Transition back to upright when not in 6dof
if (!SpaceManager.isIn6dof(self())) {
if (!SpaceManager.isIn6dof(this)) {
// TODO: better transition
if (Math.abs(roll) < 0.01f) roll = 0;
else roll *= 0.9f;
}
}

@Inject(method = "travel", at = @At("HEAD"), cancellable = true)
private void travelIn6DOFSpace(Vec3d movementInput, CallbackInfo callback) {
if (!SpaceManager.isIn6dof(this) || !isSwimming() || hasVehicle() || getAbilities().flying) return;
callback.cancel();
// Bypass pitch based ascent/descent
double x = getX();
double y = getY();
double z = getZ();
super.travel(movementInput);
self().increaseTravelMotionStats(getX() - x, getY() - y, getZ() - z);
}

}

0 comments on commit 9aaa49d

Please sign in to comment.