Classify damage from fired fireworks as PvP damage

Closes #538
This commit is contained in:
coralpapa 2019-08-15 21:38:21 -07:00 committed by RoboMWM
parent 73325a3f8f
commit 08f8d81ca4

View File

@ -33,6 +33,7 @@ import org.bukkit.entity.Entity;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.Explosive;
import org.bukkit.entity.FallingBlock;
import org.bukkit.entity.Firework;
import org.bukkit.entity.Horse;
import org.bukkit.entity.Item;
import org.bukkit.entity.LightningStrike;
@ -68,6 +69,7 @@ import org.bukkit.event.entity.EntityExplodeEvent;
import org.bukkit.event.entity.EntityInteractEvent;
import org.bukkit.event.entity.EntityPortalEnterEvent;
import org.bukkit.event.entity.EntityPortalExitEvent;
import org.bukkit.event.entity.EntityShootBowEvent;
import org.bukkit.event.entity.ExpBottleEvent;
import org.bukkit.event.entity.ItemMergeEvent;
import org.bukkit.event.entity.ItemSpawnEvent;
@ -738,6 +740,7 @@ public class EntityEventHandler implements Listener
//determine which player is attacking, if any
Player attacker = null;
Projectile arrow = null;
Firework firework = null;
Entity damageSource = subEvent.getDamager();
if(damageSource != null)
@ -753,6 +756,16 @@ public class EntityEventHandler implements Listener
{
attacker = (Player)arrow.getShooter();
}
}else if(subEvent.getDamager() instanceof Firework) {
damageSource = subEvent.getDamager();
if(damageSource.hasMetadata("GP_FIREWORK")) {
List<MetadataValue> data = damageSource.getMetadata("GP_FIREWORK");
if(data != null && data.size() > 0)
{
firework = (Firework)damageSource;
attacker = (Player) data.get(0).value();
}
}
}
//protect players from lingering potion damage when protected from pvp
@ -790,6 +803,17 @@ public class EntityEventHandler implements Listener
}
}
//if the attacker is a firework from a crossbow by a player and defender is a player (nonpvp)
if(firework != null && event.getEntityType() == EntityType.PLAYER && !GriefPrevention.instance.pvpRulesApply(attacker.getWorld()))
{
Player defender = (Player)(event.getEntity());
if(attacker != defender) {
event.setCancelled(true);
return;
}
}
//if the attacker is a player and defender is a player (pvp combat)
if(attacker != null && event.getEntityType() == EntityType.PLAYER && GriefPrevention.instance.pvpRulesApply(attacker.getWorld()))
{
@ -1086,6 +1110,7 @@ public class EntityEventHandler implements Listener
//kill the arrow to avoid infinite bounce between crowded together animals //RoboMWM: except for tridents
if(arrow != null && arrow.getType() != EntityType.TRIDENT) arrow.remove();
if(damageSource != null && damageSource.getType() == EntityType.FIREWORK && event.getEntity().getType() != EntityType.PLAYER) return;
if(sendErrorMessagesToPlayers)
{
@ -1108,6 +1133,13 @@ public class EntityEventHandler implements Listener
}
}
@EventHandler(ignoreCancelled = true, priority = EventPriority.LOWEST)
public void onCrossbowFireWork(EntityShootBowEvent shootEvent) {
if(shootEvent.getEntity() instanceof Player && shootEvent.getProjectile() instanceof Firework) {
shootEvent.getProjectile().setMetadata("GP_FIREWORK", new FixedMetadataValue(GriefPrevention.instance, shootEvent.getEntity()));
}
}
//when an entity is damaged
@EventHandler(ignoreCancelled = true, priority = EventPriority.MONITOR)
public void onEntityDamageMonitor (EntityDamageEvent event)
@ -1149,6 +1181,15 @@ public class EntityEventHandler implements Listener
attacker = (Player)arrow.getShooter();
}
}
else if(damageSource instanceof Firework) {
if(damageSource.hasMetadata("GP_FIREWORK")) {
List<MetadataValue> data = damageSource.getMetadata("GP_FIREWORK");
if(data != null && data.size() > 0)
{
attacker = (Player) data.get(0).value();
}
}
}
}
//if attacker not a player, do nothing
@ -1202,6 +1243,15 @@ public class EntityEventHandler implements Listener
attacker = (Player)arrow.getShooter();
}
}
else if(damageSource instanceof Firework) {
if(damageSource.hasMetadata("GP_FIREWORK")) {
List<MetadataValue> data = damageSource.getMetadata("GP_FIREWORK");
if(data != null && data.size() > 0)
{
attacker = (Player) data.get(0).value();
}
}
}
}
//if not a player and not an explosion, always allow