From 2f1d473262fbb171dabbdaa96d1569f2d7755f17 Mon Sep 17 00:00:00 2001 From: Sollace Date: Sat, 13 Nov 2021 19:31:45 +0200 Subject: [PATCH] Implement traits to modify spell behaviours --- .../unicopia/ability/magic/Suppressable.java | 2 +- .../ability/magic/spell/DisguiseSpell.java | 6 ++++-- .../ability/magic/spell/effect/FireSpell.java | 11 ++++------- .../magic/spell/effect/NecromancySpell.java | 9 +++++++-- .../magic/spell/effect/RevealingSpell.java | 17 +++++++++++------ .../ability/magic/spell/effect/ScorchSpell.java | 3 ++- .../ability/magic/spell/effect/ShieldSpell.java | 10 +++++++++- .../ability/magic/spell/trait/SpellTraits.java | 16 +++++++++++++--- 8 files changed, 51 insertions(+), 23 deletions(-) diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/Suppressable.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/Suppressable.java index 1f4facb0..b38cb9ee 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/Suppressable.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/Suppressable.java @@ -20,5 +20,5 @@ public interface Suppressable extends Spell { /** * Event triggered when this effect is suppressed. */ - void onSuppressed(Caster otherSource); + void onSuppressed(Caster otherSource, float suppressTime); } diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/DisguiseSpell.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/DisguiseSpell.java index 284a10ad..e8271d09 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/DisguiseSpell.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/DisguiseSpell.java @@ -11,6 +11,7 @@ import com.minelittlepony.unicopia.ability.magic.Suppressable; import com.minelittlepony.unicopia.ability.magic.spell.effect.AbstractSpell; import com.minelittlepony.unicopia.ability.magic.spell.effect.SpellType; import com.minelittlepony.unicopia.ability.magic.spell.trait.SpellTraits; +import com.minelittlepony.unicopia.ability.magic.spell.trait.Trait; import com.minelittlepony.unicopia.entity.behaviour.EntityBehaviour; import com.minelittlepony.unicopia.entity.behaviour.Disguise; import com.minelittlepony.unicopia.entity.player.Pony; @@ -59,8 +60,9 @@ public class DisguiseSpell extends AbstractSpell implements Suppressable, Flight } @Override - public void onSuppressed(Caster otherSource) { - suppressionCounter = 100; + public void onSuppressed(Caster otherSource, float time) { + time /= getTraits().getOrDefault(Trait.STRENGTH, 1); + suppressionCounter = (int)(100 * time); setDirty(); } diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/FireSpell.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/FireSpell.java index 0924d90d..d80c58e8 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/FireSpell.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/FireSpell.java @@ -5,13 +5,13 @@ import com.minelittlepony.unicopia.ability.magic.Caster; import com.minelittlepony.unicopia.ability.magic.spell.Situation; 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.block.state.StateMaps; import com.minelittlepony.unicopia.particle.ParticleUtils; import com.minelittlepony.unicopia.projectile.MagicProjectileEntity; import com.minelittlepony.unicopia.util.MagicalDamageSource; import com.minelittlepony.unicopia.util.PosHelper; import com.minelittlepony.unicopia.util.VecHelper; -import com.minelittlepony.unicopia.util.shape.Shape; import com.minelittlepony.unicopia.util.shape.Sphere; import net.minecraft.block.Block; @@ -36,9 +36,6 @@ import net.minecraft.world.explosion.Explosion.DestructionType; * Simple fire spell that triggers an effect when used on a block. */ public class FireSpell extends AbstractSpell implements ProjectileSpell { - - private static final Shape EFFECT_RANGE = new Sphere(false, 4); - protected FireSpell(SpellType type, SpellTraits traits) { super(type, traits); } @@ -56,14 +53,14 @@ public class FireSpell extends AbstractSpell implements ProjectileSpell { generateParticles(source); } - return PosHelper.getAllInRegionMutable(source.getOrigin(), EFFECT_RANGE).reduce(false, + return PosHelper.getAllInRegionMutable(source.getOrigin(), new Sphere(false, Math.max(0, 4 + getTraits().get(Trait.POWER)))).reduce(false, (r, i) -> applyBlocks(source.getWorld(), i), (a, b) -> a || b) || applyEntities(null, source.getWorld(), source.getOriginVector()); } protected void generateParticles(Caster source) { - source.spawnParticles(EFFECT_RANGE, (1 + source.getLevel().get()) * 6, pos -> { + source.spawnParticles(new Sphere(false, Math.max(0, 4 + getTraits().get(Trait.POWER))), (1 + source.getLevel().get()) * 6, pos -> { source.addParticle(ParticleTypes.LARGE_SMOKE, pos, Vec3d.ZERO); }); } @@ -111,7 +108,7 @@ public class FireSpell extends AbstractSpell implements ProjectileSpell { } protected boolean applyEntities(Entity owner, World world, Vec3d pos) { - return !VecHelper.findInRange(owner, world, pos, 3, i -> applyEntitySingle(owner, world, i)).isEmpty(); + return !VecHelper.findInRange(owner, world, pos, Math.max(0, 3 + getTraits().get(Trait.POWER)), i -> applyEntitySingle(owner, world, i)).isEmpty(); } protected boolean applyEntitySingle(Entity owner, World world, Entity e) { diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/NecromancySpell.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/NecromancySpell.java index b40f56d3..3dfe0850 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/NecromancySpell.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/NecromancySpell.java @@ -6,6 +6,7 @@ import java.util.List; 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.EntityReference; import com.minelittlepony.unicopia.util.Weighted; import com.minelittlepony.unicopia.util.shape.Shape; @@ -39,7 +40,11 @@ public class NecromancySpell extends AbstractSpell { @Override public boolean tick(Caster source, Situation situation) { - int radius = (source.getLevel().get() + 1) * 4; + float radius = (source.getLevel().get() + 1) * 4 + getTraits().get(Trait.POWER); + + if (radius <= 0) { + return false; + } if (source.isClient()) { source.spawnParticles(new Sphere(false, radius), 5, pos -> { @@ -56,7 +61,7 @@ public class NecromancySpell extends AbstractSpell { summonedEntities.removeIf(ref -> !ref.isPresent(source.getWorld())); - float additional = source.getWorld().getLocalDifficulty(source.getOrigin()).getLocalDifficulty(); + float additional = source.getWorld().getLocalDifficulty(source.getOrigin()).getLocalDifficulty() + getTraits().get(Trait.CHAOS, 0, 10); Shape affectRegion = new Sphere(false, radius); diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/RevealingSpell.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/RevealingSpell.java index f3ab9634..fefac8fc 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/RevealingSpell.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/RevealingSpell.java @@ -4,8 +4,8 @@ import com.minelittlepony.unicopia.ability.magic.Caster; import com.minelittlepony.unicopia.ability.magic.SpellPredicate; 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.particle.MagicParticleEffect; -import com.minelittlepony.unicopia.util.shape.Shape; import com.minelittlepony.unicopia.util.shape.Sphere; import net.minecraft.sound.SoundCategory; @@ -16,28 +16,33 @@ import net.minecraft.util.math.Vec3d; * A spell for revealing changelings. */ public class RevealingSpell extends AbstractSpell { - private static final Shape AREA = new Sphere(false, 15); - protected RevealingSpell(SpellType type, SpellTraits traits) { super(type, traits); } @Override public boolean tick(Caster source, Situation situation) { + + float range = Math.max(0, 15 + getTraits().get(Trait.POWER)); + + if (range == 0) { + return false; + } + if (source.isClient()) { MagicParticleEffect effect = new MagicParticleEffect(getType().getColor()); - source.spawnParticles(AREA, 5, pos -> { + source.spawnParticles(new Sphere(false, range), 5, pos -> { source.addParticle(effect, pos, Vec3d.ZERO); }); source.spawnParticles(effect, 5); } - source.findAllSpellsInRange(15).forEach(e -> { + source.findAllSpellsInRange(range).forEach(e -> { e.getSpellSlot().get(SpellPredicate.CAN_SUPPRESS, false) .filter(spell -> spell.isVulnerable(source, this)) .ifPresent(spell -> { - spell.onSuppressed(source); + spell.onSuppressed(source, 1 + getTraits().get(Trait.STRENGTH)); source.getWorld().playSound(null, e.getOrigin(), SoundEvents.ENTITY_ZOMBIE_VILLAGER_CURE, SoundCategory.PLAYERS, 0.2F, 0.5F); }); }); diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ScorchSpell.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ScorchSpell.java index d1e8af14..b2f814ff 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ScorchSpell.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ScorchSpell.java @@ -3,6 +3,7 @@ package com.minelittlepony.unicopia.ability.magic.spell.effect; 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.block.state.StateMaps; import com.minelittlepony.unicopia.particle.MagicParticleEffect; import com.minelittlepony.unicopia.projectile.MagicProjectileEntity; @@ -24,7 +25,7 @@ public class ScorchSpell extends FireSpell { BlockPos pos = PosHelper.findSolidGroundAt(source.getWorld(), source.getOrigin(), source.getPhysics().getGravitySignum()); if (StateMaps.FIRE_AFFECTED.convert(source.getWorld(), pos)) { - source.spawnParticles(new Sphere(false, 1), 5, p -> { + source.spawnParticles(new Sphere(false, Math.max(1, getTraits().get(Trait.POWER))), 5, p -> { source.addParticle(ParticleTypes.SMOKE, PosHelper.offset(p, pos), Vec3d.ZERO); }); } diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ShieldSpell.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ShieldSpell.java index ea98cecd..b2fd267e 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ShieldSpell.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/effect/ShieldSpell.java @@ -12,6 +12,7 @@ import com.minelittlepony.unicopia.ability.magic.Caster; import com.minelittlepony.unicopia.ability.magic.spell.Situation; 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.item.FriendshipBraceletItem; import com.minelittlepony.unicopia.item.enchantment.UEnchantments; @@ -78,12 +79,18 @@ public class ShieldSpell extends AbstractSpell implements ProjectileSpell { return true; } + float knowledge = getTraits().get(Trait.KNOWLEDGE, -6, 6); + if (knowledge == 0) { + knowledge = 1; + } + long costMultiplier = applyEntities(source); if (costMultiplier > 0) { double cost = 2 + source.getLevel().get(); cost *= costMultiplier / ((1 + source.getLevel().get()) * 3F); cost /= 2.725D; + cost /= knowledge; if (!source.subtractEnergyCost(cost)) { setDead(); @@ -98,7 +105,8 @@ public class ShieldSpell extends AbstractSpell implements ProjectileSpell { */ public double getDrawDropOffRange(Caster source) { float multiplier = source.getMaster().isSneaking() ? 1 : 2; - return (4 + (source.getLevel().get() * 2)) / multiplier; + float min = 4 + getTraits().get(Trait.POWER); + return (min + (source.getLevel().get() * 2)) / multiplier; } protected List getTargets(Caster source, double radius) { diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/trait/SpellTraits.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/trait/SpellTraits.java index 16730fcb..13992080 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/trait/SpellTraits.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/trait/SpellTraits.java @@ -27,6 +27,7 @@ import net.minecraft.nbt.NbtElement; import net.minecraft.network.PacketByteBuf; import net.minecraft.text.LiteralText; import net.minecraft.text.Text; +import net.minecraft.util.math.MathHelper; import net.minecraft.util.registry.Registry; public final class SpellTraits implements Iterable> { @@ -62,7 +63,7 @@ public final class SpellTraits implements Iterable> { public boolean includes(SpellTraits other) { return other.stream().allMatch(pair -> { - return getAmount(pair.getKey()) >= pair.getValue(); + return get(pair.getKey()) >= pair.getValue(); }); } @@ -79,8 +80,17 @@ public final class SpellTraits implements Iterable> { return entries().stream(); } - public float getAmount(Trait trait) { - return traits.getOrDefault(trait, 0F); + public float getOrDefault(Trait trait, float def) { + float i = traits.getOrDefault(trait, def); + return i == 0 ? def : i; + } + + public float get(Trait trait) { + return getOrDefault(trait, 0F); + } + + public float get(Trait trait, float min, float max) { + return MathHelper.clamp(get(trait), min, max); } public void appendTooltip(List tooltip) {