package openblocks.common.entity;
import cpw.mods.fml.relauncher.Side;
import cpw.mods.fml.relauncher.SideOnly;
import net.minecraft.entity.Entity;
import net.minecraft.util.Vec3;
import net.minecraft.world.World;
public abstract class EntitySmoothMove extends Entity {
public class MoveSmoother {
private final double damp;
private final double cutoff;
private final double panicLengthSq;
private final double minimalLengthSq;
private double targetX;
private double targetY;
private double targetZ;
public MoveSmoother(double damp, double cutoff, double panicLength, double minimalLength) {
this.damp = damp;
this.cutoff = cutoff;
this.panicLengthSq = panicLength * panicLength;
this.minimalLengthSq = minimalLength * minimalLength;
}
public void setTarget(Vec3 position) {
setTarget(position.xCoord, position.yCoord, position.zCoord);
}
public void setTarget(double targetX, double targetY, double targetZ) {
this.targetX = targetX;
this.targetY = targetY;
this.targetZ = targetZ;
}
public void update() {
double dx = targetX - posX;
double dy = targetY - posY;
double dz = targetZ - posZ;
double lenSq = dx * dx + dy * dy + dz * dz;
if (lenSq > panicLengthSq || lenSq < minimalLengthSq) {
setPosition(targetX, targetY, targetZ);
motionX = motionY = motionZ = 0;
} else {
if (lenSq > cutoff * cutoff) {
double scale = cutoff / Math.sqrt(lenSq);
dx *= scale;
dy *= scale;
dz *= scale;
}
moveEntity(motionX + dx * damp, motionY + dy * damp, motionZ + dz * damp);
}
}
}
protected final MoveSmoother smoother;
public EntitySmoothMove(World world) {
super(world);
smoother = createSmoother(world.isRemote);
}
protected MoveSmoother createSmoother(boolean isRemote) {
return isRemote? new MoveSmoother(0.25, 1.0, 8.0, 0.01) : new MoveSmoother(0.5, 5.0, 128.0, 0.01);
}
@Override
public void setPosition(double x, double y, double z) {
if (smoother != null) smoother.setTarget(x, y, z);
super.setPosition(x, y, z);
}
@Override
public void setPositionAndRotation(double x, double y, double z, float yaw, float pitch) {
smoother.setTarget(x, y, z);
super.setPositionAndRotation(x, y, z, yaw, pitch);
}
@Override
@SideOnly(Side.CLIENT)
public void setPositionAndRotation2(double x, double y, double z, float yaw, float pitch, int something) {
smoother.setTarget(x, y, z);
super.setRotation(yaw, pitch);
}
protected void updatePrevPosition() {
prevDistanceWalkedModified = distanceWalkedModified;
prevPosX = posX;
prevPosY = posY;
prevPosZ = posZ;
prevRotationPitch = this.rotationPitch;
prevRotationYaw = this.rotationYaw;
}
}