mirror of
https://github.com/Sollace/Unicopia.git
synced 2024-11-27 23:27:59 +01:00
Move various gravitation/force/physics stuff to a utility class
This commit is contained in:
parent
ca7ff47451
commit
ddbf75a44f
7 changed files with 89 additions and 58 deletions
|
@ -17,6 +17,13 @@ public interface SpellPredicate<T extends Spell> extends Predicate<Spell> {
|
|||
SpellPredicate<AbstractDisguiseSpell> IS_DISGUISE = s -> s instanceof AbstractDisguiseSpell;
|
||||
SpellPredicate<ShieldSpell> IS_SHIELD_LIKE = spell -> spell instanceof ShieldSpell;
|
||||
|
||||
default SpellPredicate<T> and(SpellPredicate<T> predicate) {
|
||||
SpellPredicate<T> self = this;
|
||||
return s -> {
|
||||
return self.test(s) && predicate.test(s);
|
||||
};
|
||||
}
|
||||
|
||||
default boolean isOn(Caster<?> caster) {
|
||||
return caster.getSpellSlot().contains(this);
|
||||
}
|
||||
|
|
|
@ -0,0 +1,62 @@
|
|||
package com.minelittlepony.unicopia.ability.magic.spell.effect;
|
||||
|
||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||
import com.minelittlepony.unicopia.item.enchantment.UEnchantments;
|
||||
|
||||
import net.minecraft.enchantment.EnchantmentHelper;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.entity.LivingEntity;
|
||||
import net.minecraft.util.math.MathHelper;
|
||||
import net.minecraft.util.math.Vec3d;
|
||||
|
||||
public interface AttractionUtils {
|
||||
|
||||
static double getAttractiveForce(double wellMass, Vec3d wellPosition, Entity target) {
|
||||
return (wellMass * AttractionUtils.getMass(target)) / MathHelper.square(wellPosition.distanceTo(target.getPos()));
|
||||
}
|
||||
|
||||
static double getMass(Entity entity) {
|
||||
return entity.getWidth() * entity.getHeight();
|
||||
}
|
||||
|
||||
/**
|
||||
* Applies a force to the given entity relative to a given center position
|
||||
*/
|
||||
static void applyForce(Vec3d center, Entity target, double force, double yChange, boolean clampVelocity) {
|
||||
if (clampVelocity) {
|
||||
target.setVelocity(target.getVelocity().multiply(Math.min(1, 1 - force)));
|
||||
}
|
||||
center = target.getPos().subtract(center).normalize().multiply(force);
|
||||
|
||||
if (target instanceof LivingEntity) {
|
||||
center = center.multiply(1 / (1 + EnchantmentHelper.getEquipmentLevel(UEnchantments.HEAVY, (LivingEntity)target)));
|
||||
}
|
||||
|
||||
target.addVelocity(
|
||||
center.x,
|
||||
center.y + yChange,
|
||||
center.z
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a force to apply based on the given player's given race.
|
||||
*/
|
||||
static double getForceAdjustment(Entity entity) {
|
||||
return Pony.of(entity).map(pony -> {
|
||||
double force = 0.75;
|
||||
|
||||
if (pony.getSpecies().canUseEarth()) {
|
||||
force /= 2;
|
||||
|
||||
if (pony.getMaster().isSneaking()) {
|
||||
force /= 6;
|
||||
}
|
||||
} else if (pony.getSpecies().canFly()) {
|
||||
force *= 2;
|
||||
}
|
||||
|
||||
return force;
|
||||
}).orElse(1D);
|
||||
}
|
||||
}
|
|
@ -4,7 +4,6 @@ import com.minelittlepony.unicopia.ability.magic.Caster;
|
|||
import com.minelittlepony.unicopia.ability.magic.spell.ProjectileSpell;
|
||||
import com.minelittlepony.unicopia.ability.magic.spell.trait.SpellTraits;
|
||||
import com.minelittlepony.unicopia.ability.magic.spell.trait.Trait;
|
||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||
import com.minelittlepony.unicopia.particle.FollowingParticleEffect;
|
||||
import com.minelittlepony.unicopia.particle.MagicParticleEffect;
|
||||
import com.minelittlepony.unicopia.particle.UParticles;
|
||||
|
@ -13,7 +12,6 @@ import com.minelittlepony.unicopia.util.shape.Sphere;
|
|||
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.entity.ItemEntity;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.util.math.MathHelper;
|
||||
import net.minecraft.util.math.Vec3d;
|
||||
|
||||
|
@ -53,15 +51,15 @@ public class AttractiveSpell extends ShieldSpell implements ProjectileSpell {
|
|||
|
||||
boolean isGood = isFriendlyTogether(source);
|
||||
|
||||
if (isGood && target instanceof PlayerEntity) {
|
||||
force *= calculateAdjustedForce(Pony.of((PlayerEntity)target));
|
||||
if (isGood) {
|
||||
force *= AttractionUtils.getForceAdjustment(target);
|
||||
}
|
||||
|
||||
if (!isGood && source.getWorld().random.nextInt(4500) == 0) {
|
||||
source.getEntity().damage(MagicalDamageSource.create("vortex"), 4);
|
||||
}
|
||||
|
||||
applyForce(getOrigin(source), target, -force, 0);
|
||||
AttractionUtils.applyForce(getOrigin(source), target, -force, 0, false);
|
||||
|
||||
float maxVel = !isFriendlyTogether(source) ? 1 : 1.6f;
|
||||
|
||||
|
|
|
@ -189,7 +189,7 @@ public class DarkVortexSpell extends AttractiveSpell implements ProjectileSpell
|
|||
}
|
||||
|
||||
private double getAttractiveForce(Caster<?> source, Entity target) {
|
||||
return (getMass() * getMass(target)) / Math.pow(getOrigin(source).distanceTo(target.getPos()), 2);
|
||||
return AttractionUtils.getAttractiveForce(getMass(), getOrigin(source), target);
|
||||
}
|
||||
|
||||
private double getMass() {
|
||||
|
@ -197,10 +197,6 @@ public class DarkVortexSpell extends AttractiveSpell implements ProjectileSpell
|
|||
return 10 + Math.min(15, Math.min(0.5F + pulse, (float)Math.exp(age) / 8F - 90) + accumulatedMass / 10F) + pulse;
|
||||
}
|
||||
|
||||
private double getMass(Entity entity) {
|
||||
return entity.getWidth() * entity.getHeight();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void applyRadialEffect(Caster<?> source, Entity target, double distance, double radius) {
|
||||
|
||||
|
@ -227,20 +223,21 @@ public class DarkVortexSpell extends AttractiveSpell implements ProjectileSpell
|
|||
return;
|
||||
}
|
||||
|
||||
accumulatedMass += getMass(target);
|
||||
double massOfTarget = AttractionUtils.getMass(target);
|
||||
|
||||
accumulatedMass += massOfTarget;
|
||||
setDirty();
|
||||
target.damage(MagicalDamageSource.create("black_hole"), Integer.MAX_VALUE);
|
||||
if (!(target instanceof PlayerEntity)) {
|
||||
target.discard();
|
||||
}
|
||||
|
||||
source.subtractEnergyCost(-getMass(target) * 10);
|
||||
source.subtractEnergyCost(-massOfTarget * 10);
|
||||
source.getWorld().playSound(null, source.getOrigin(), USounds.AMBIENT_DARK_VORTEX_MOOD, SoundCategory.AMBIENT, 2, 0.02F);
|
||||
} else {
|
||||
double force = getAttractiveForce(source, target);
|
||||
|
||||
target.setVelocity(target.getVelocity().multiply(Math.min(1, 1 - force)));
|
||||
applyForce(getOrigin(source), target, -force, 0);
|
||||
AttractionUtils.applyForce(getOrigin(source), target, -force, 0, true);
|
||||
|
||||
source.subtractEnergyCost(-2);
|
||||
}
|
||||
|
|
|
@ -7,8 +7,6 @@ import com.minelittlepony.unicopia.ability.magic.Caster;
|
|||
import com.minelittlepony.unicopia.ability.magic.spell.Situation;
|
||||
import com.minelittlepony.unicopia.ability.magic.spell.trait.SpellTraits;
|
||||
import com.minelittlepony.unicopia.ability.magic.spell.trait.Trait;
|
||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||
import com.minelittlepony.unicopia.item.enchantment.UEnchantments;
|
||||
import com.minelittlepony.unicopia.particle.MagicParticleEffect;
|
||||
import com.minelittlepony.unicopia.particle.ParticleHandle;
|
||||
import com.minelittlepony.unicopia.particle.SphereParticleEffect;
|
||||
|
@ -16,7 +14,6 @@ import com.minelittlepony.unicopia.particle.UParticles;
|
|||
import com.minelittlepony.unicopia.projectile.ProjectileUtil;
|
||||
import com.minelittlepony.unicopia.util.shape.Sphere;
|
||||
|
||||
import net.minecraft.enchantment.EnchantmentHelper;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.entity.EyeOfEnderEntity;
|
||||
import net.minecraft.entity.FallingBlockEntity;
|
||||
|
@ -24,7 +21,6 @@ import net.minecraft.entity.LivingEntity;
|
|||
import net.minecraft.entity.TntEntity;
|
||||
import net.minecraft.entity.Entity.RemovalReason;
|
||||
import net.minecraft.entity.decoration.ArmorStandEntity;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.entity.vehicle.AbstractMinecartEntity;
|
||||
import net.minecraft.entity.vehicle.BoatEntity;
|
||||
import net.minecraft.util.math.Vec3d;
|
||||
|
@ -160,50 +156,13 @@ public class ShieldSpell extends AbstractSpell {
|
|||
} else if (target instanceof LivingEntity) {
|
||||
double force = Math.max(0.1, radius / 4);
|
||||
|
||||
if (isFriendlyTogether(source) && target instanceof PlayerEntity) {
|
||||
force *= calculateAdjustedForce(Pony.of((PlayerEntity)target));
|
||||
if (isFriendlyTogether(source)) {
|
||||
force *= AttractionUtils.getForceAdjustment(target);
|
||||
} else {
|
||||
force *= 0.75;
|
||||
}
|
||||
|
||||
applyForce(pos, target, force, distance);
|
||||
AttractionUtils.applyForce(pos, target, force, (distance < 1 ? distance : 0), false);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Applies a force to the given entity based on distance from the source.
|
||||
*/
|
||||
protected void applyForce(Vec3d pos, Entity target, double force, double distance) {
|
||||
pos = target.getPos().subtract(pos).normalize().multiply(force);
|
||||
|
||||
if (target instanceof LivingEntity) {
|
||||
pos = pos.multiply(1 / (1 + EnchantmentHelper.getEquipmentLevel(UEnchantments.HEAVY, (LivingEntity)target)));
|
||||
}
|
||||
|
||||
target.addVelocity(
|
||||
pos.x,
|
||||
pos.y + (distance < 1 ? distance : 0),
|
||||
pos.z
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a force to apply based on the given player's given race.
|
||||
*/
|
||||
protected double calculateAdjustedForce(Pony player) {
|
||||
double force = 0.75;
|
||||
|
||||
if (player.getSpecies().canUseEarth()) {
|
||||
force /= 2;
|
||||
|
||||
if (player.getMaster().isSneaking()) {
|
||||
force /= 6;
|
||||
}
|
||||
} else if (player.getSpecies().canFly()) {
|
||||
force *= 2;
|
||||
}
|
||||
|
||||
return force;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -62,6 +62,10 @@ public class EntityReference<T extends Entity> implements NbtSerialisable {
|
|||
return pos;
|
||||
}
|
||||
|
||||
public boolean referenceEquals(Entity entity) {
|
||||
return entity != null && entity.getUuid().equals(uuid.orElse(null));
|
||||
}
|
||||
|
||||
public boolean isPresent(World world) {
|
||||
return getOrEmpty(world).isPresent();
|
||||
}
|
||||
|
|
|
@ -598,6 +598,10 @@ public class Pony extends Living<PlayerEntity> implements Transmittable, Copieab
|
|||
return player == null ? null : ((PonyContainer<Pony>)player).get();
|
||||
}
|
||||
|
||||
public static Optional<Pony> of(Entity entity) {
|
||||
return entity instanceof PlayerEntity ? PonyContainer.of(entity).map(a -> (Pony)a.get()) : Optional.empty();
|
||||
}
|
||||
|
||||
public static boolean equal(GameProfile one, GameProfile two) {
|
||||
return one == two || (one != null && two != null && one.getId().equals(two.getId()));
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue