diff --git a/pom.xml b/pom.xml index b98962c..a0b6f1e 100644 --- a/pom.xml +++ b/pom.xml @@ -58,14 +58,14 @@ 2.0.4 - 1.14.4-R0.1-SNAPSHOT - 1.9.0-SNAPSHOT + 1.15-R0.1-SNAPSHOT + 1.9.0 ${build.version}-SNAPSHOT -LOCAL - 1.9.0 + 1.9.2 diff --git a/src/main/java/world/bentobox/acidisland/AISettings.java b/src/main/java/world/bentobox/acidisland/AISettings.java index ec847cc..5f24b99 100644 --- a/src/main/java/world/bentobox/acidisland/AISettings.java +++ b/src/main/java/world/bentobox/acidisland/AISettings.java @@ -69,7 +69,7 @@ public class AISettings implements WorldSettings { @ConfigEntry(path = "acid.damage.acid.item") private long acidDestroyItemTime = 0; - @ConfigComment("Damage from acid rain") + @ConfigComment("Damage from acid rain (and snow, if toggled on).") @ConfigEntry(path = "acid.damage.rain") private int acidRainDamage = 1; @@ -82,12 +82,34 @@ public class AISettings implements WorldSettings { @ConfigEntry(path = "acid.damage.delay") private long acidDamageDelay = 2; - @ConfigComment("Portion effects from going into acid water") - @ConfigComment("You can list multiple effects") + @ConfigComment("Potion effects from going into acid water.") + @ConfigComment("You can list multiple effects.") + @ConfigComment("Available effects are:") + @ConfigComment(" BLINDNESS") + @ConfigComment(" CONFUSION") + @ConfigComment(" HUNGER") + @ConfigComment(" POISON") + @ConfigComment(" SLOW") + @ConfigComment(" SLOW_DIGGING") + @ConfigComment(" WEAKNESS") @ConfigEntry(path = "acid.damage.effects") @Adapter(PotionEffectListAdapter.class) private List acidEffects = new ArrayList<>(); + @ConfigComment("Potion effects from going into acid rain and snow.") + @ConfigComment("You can list multiple effects.") + @ConfigComment("Available effects are:") + @ConfigComment(" BLINDNESS") + @ConfigComment(" CONFUSION") + @ConfigComment(" HUNGER") + @ConfigComment(" POISON") + @ConfigComment(" SLOW") + @ConfigComment(" SLOW_DIGGING") + @ConfigComment(" WEAKNESS") + @ConfigEntry(path = "acid.damage.rain-effects", since = "1.9.1") + @Adapter(PotionEffectListAdapter.class) + private List acidRainEffects = new ArrayList<>(); + @ConfigComment("If player wears a helmet then they will not suffer from acid rain") @ConfigEntry(path = "acid.damage.protection.helmet") private boolean helmetProtection; @@ -1507,4 +1529,22 @@ public class AISettings implements WorldSettings { { this.createIslandOnFirstLoginAbortOnLogout = createIslandOnFirstLoginAbortOnLogout; } + + /** + * + * @return + * @since 1.9.1 + */ + public List getAcidRainEffects() { + return acidRainEffects; + } + + /** + * + * @param acidRainEffects + * @since 1.9.1 + */ + public void setAcidRainEffects(List acidRainEffects) { + this.acidRainEffects = acidRainEffects; + } } diff --git a/src/main/java/world/bentobox/acidisland/events/AcidEvent.java b/src/main/java/world/bentobox/acidisland/events/AcidEvent.java index 80d9ff0..667f6ce 100644 --- a/src/main/java/world/bentobox/acidisland/events/AcidEvent.java +++ b/src/main/java/world/bentobox/acidisland/events/AcidEvent.java @@ -21,7 +21,7 @@ public class AcidEvent extends Event implements Cancellable { private Player player; private double totalDamage; private final double protection; - private List potionEffects = new ArrayList<>(); + private List potionEffects; /** * @param player - player diff --git a/src/main/java/world/bentobox/acidisland/events/AcidRainEvent.java b/src/main/java/world/bentobox/acidisland/events/AcidRainEvent.java index c6f6962..60e8e20 100644 --- a/src/main/java/world/bentobox/acidisland/events/AcidRainEvent.java +++ b/src/main/java/world/bentobox/acidisland/events/AcidRainEvent.java @@ -4,6 +4,9 @@ import org.bukkit.entity.Player; import org.bukkit.event.Cancellable; import org.bukkit.event.Event; import org.bukkit.event.HandlerList; +import org.bukkit.potion.PotionEffectType; + +import java.util.List; /** * This event is fired when a player is going to be burned by acid rain @@ -17,6 +20,10 @@ public class AcidRainEvent extends Event implements Cancellable { private Player player; private double rainDamage; private final double protection; + /** + * @since 1.9.1 + */ + private List potionEffects; private boolean cancelled; @@ -26,10 +33,11 @@ public class AcidRainEvent extends Event implements Cancellable { * @param rainDamage * @param protection */ - public AcidRainEvent(Player player, double rainDamage, double protection) { + public AcidRainEvent(Player player, double rainDamage, double protection, List potionEffects) { this.player = player; this.rainDamage = rainDamage; this.protection = protection; + this.potionEffects = potionEffects; } /** @@ -69,6 +77,25 @@ public class AcidRainEvent extends Event implements Cancellable { this.rainDamage = rainDamage; } + /** + * Returns the potion effects that will be applied to the player. + * @return + * @since 1.9.1 + */ + public List getPotionEffects() { + return potionEffects; + } + + /** + * + * @param potionEffects the potionEffects to set + * @return + * @since 1.9.1 + */ + public void setPotionEffects(List potionEffects) { + this.potionEffects = potionEffects; + } + @Override public HandlerList getHandlers() { return handlers; diff --git a/src/main/java/world/bentobox/acidisland/listeners/AcidEffect.java b/src/main/java/world/bentobox/acidisland/listeners/AcidEffect.java index 0f30431..21228ba 100644 --- a/src/main/java/world/bentobox/acidisland/listeners/AcidEffect.java +++ b/src/main/java/world/bentobox/acidisland/listeners/AcidEffect.java @@ -9,6 +9,7 @@ import org.bukkit.GameMode; import org.bukkit.Location; import org.bukkit.Material; import org.bukkit.Sound; +import org.bukkit.World.Environment; import org.bukkit.attribute.Attribute; import org.bukkit.block.BlockFace; import org.bukkit.entity.EntityType; @@ -116,11 +117,16 @@ public class AcidEffect implements Listener { } else if (wetPlayers.containsKey(player) && wetPlayers.get(player) < System.currentTimeMillis()) { double protection = addon.getSettings().getAcidRainDamage() * getDamageReduced(player); double totalDamage = Math.max(0, addon.getSettings().getAcidRainDamage() - protection); - AcidRainEvent e = new AcidRainEvent(player, totalDamage, protection); - addon.getServer().getPluginManager().callEvent(e); - if (!e.isCancelled()) { - player.damage(e.getRainDamage()); - player.getWorld().playSound(playerLoc, Sound.ENTITY_CREEPER_PRIMED, 3F, 3F); + AcidRainEvent event = new AcidRainEvent(player, totalDamage, protection, addon.getSettings().getAcidRainEffects()); + addon.getServer().getPluginManager().callEvent(event); + if (!event.isCancelled()) { + event.getPotionEffects().stream().filter(EFFECTS::contains).forEach(t -> player.addPotionEffect(new PotionEffect(t, 600, 1))); + event.getPotionEffects().stream().filter(e -> e.equals(PotionEffectType.POISON)).forEach(t -> player.addPotionEffect(new PotionEffect(t, 200, 1))); + // Apply damage if there is any + if (event.getRainDamage() > 0D) { + player.damage(event.getRainDamage()); + player.getWorld().playSound(playerLoc, Sound.ENTITY_CREEPER_PRIMED, 3F, 3F); + } } } } @@ -172,11 +178,13 @@ public class AcidEffect implements Listener { * @return true if they are safe */ private boolean isSafeFromRain(Player player) { - if (addon.getSettings().isHelmetProtection() && (player.getInventory().getHelmet() != null - && player.getInventory().getHelmet().getType().name().contains("HELMET")) + if (player.getWorld().getEnvironment().equals(Environment.NETHER) + || player.getWorld().getEnvironment().equals(Environment.THE_END) + || (addon.getSettings().isHelmetProtection() && (player.getInventory().getHelmet() != null && player.getInventory().getHelmet().getType().name().contains("HELMET"))) || (!addon.getSettings().isAcidDamageSnow() && player.getLocation().getBlock().getTemperature() < 0.1) // snow falls || player.getLocation().getBlock().getHumidity() == 0 // dry - || (player.getActivePotionEffects().stream().map(PotionEffect::getType).anyMatch(IMMUNE_EFFECTS::contains))) { + || (player.getActivePotionEffects().stream().map(PotionEffect::getType).anyMatch(IMMUNE_EFFECTS::contains)) + ) { return true; } // Check if all air above player diff --git a/src/test/java/world/bentobox/acidisland/events/AcidRainEventTest.java b/src/test/java/world/bentobox/acidisland/events/AcidRainEventTest.java index 7aac502..c8899a6 100644 --- a/src/test/java/world/bentobox/acidisland/events/AcidRainEventTest.java +++ b/src/test/java/world/bentobox/acidisland/events/AcidRainEventTest.java @@ -7,19 +7,27 @@ import static org.junit.Assert.assertTrue; import static org.mockito.Mockito.mock; import org.bukkit.entity.Player; +import org.bukkit.potion.PotionEffectType; +import org.junit.Assert; import org.junit.Before; import org.junit.Test; import org.mockito.Mock; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + public class AcidRainEventTest { @Mock private Player player; + private List effects; private AcidRainEvent e; @Before public void setUp() throws Exception { - e = new AcidRainEvent(player, 10, 5); + effects = Arrays.asList(PotionEffectType.values()); + e = new AcidRainEvent(player, 10, 5, effects); } @Test @@ -55,6 +63,17 @@ public class AcidRainEventTest { assertTrue(e.getRainDamage() == 50D); } + @Test + public void testGetPotionEffects() { + Assert.assertArrayEquals(PotionEffectType.values(), e.getPotionEffects().toArray()); + } + + @Test + public void testSetPotionEffects() { + e.setPotionEffects(new ArrayList<>()); + assertTrue(e.getPotionEffects().isEmpty()); + } + @Test public void testIsCancelled() { assertFalse(e.isCancelled()); diff --git a/src/test/java/world/bentobox/acidisland/listeners/AcidEffectTest.java b/src/test/java/world/bentobox/acidisland/listeners/AcidEffectTest.java index 43bc5a3..ab7e93c 100644 --- a/src/test/java/world/bentobox/acidisland/listeners/AcidEffectTest.java +++ b/src/test/java/world/bentobox/acidisland/listeners/AcidEffectTest.java @@ -18,6 +18,7 @@ import org.bukkit.GameMode; import org.bukkit.Location; import org.bukkit.Material; import org.bukkit.World; +import org.bukkit.World.Environment; import org.bukkit.attribute.Attribute; import org.bukkit.attribute.AttributeInstance; import org.bukkit.block.Block; @@ -146,6 +147,7 @@ public class AcidEffectTest { when(world.hasStorm()).thenReturn(true); when(world.getBlockAt(anyInt(), anyInt(), anyInt())).thenReturn(airBlock); when(world.getMaxHeight()).thenReturn(5); + when(world.getEnvironment()).thenReturn(Environment.NORMAL); ae = new AcidEffect(addon); } @@ -305,6 +307,38 @@ public class AcidEffectTest { verify(settings).getAcidDamageDelay(); } + /** + * Test method for {@link world.bentobox.acidisland.listeners.AcidEffect#onPlayerMove(org.bukkit.event.player.PlayerMoveEvent)}. + */ + @Test + public void testOnPlayerMoveAcidRainWrongWorld() { + World nether = mock(World.class); + when(nether.getName()).thenReturn("world_nether"); + when(nether.getEnvironment()).thenReturn(Environment.NETHER); + when(player.getWorld()).thenReturn(nether); + + PlayerMoveEvent e = new PlayerMoveEvent(player, from, to); + ae.onPlayerMove(e); + // 2 times only + verify(addon, times(2)).getPlugin(); + } + + /** + * Test method for {@link world.bentobox.acidisland.listeners.AcidEffect#onPlayerMove(org.bukkit.event.player.PlayerMoveEvent)}. + */ + @Test + public void testOnPlayerMoveAcidRainWrongWorldEnd() { + World end = mock(World.class); + when(end.getName()).thenReturn("world_end"); + when(end.getEnvironment()).thenReturn(Environment.THE_END); + when(player.getWorld()).thenReturn(end); + + PlayerMoveEvent e = new PlayerMoveEvent(player, from, to); + ae.onPlayerMove(e); + // 2 times only + verify(addon, times(2)).getPlugin(); + } + /** * Test method for {@link world.bentobox.acidisland.listeners.AcidEffect#onPlayerMove(org.bukkit.event.player.PlayerMoveEvent)}. */