bag o' patches
This commit is contained in:
parent
feca8d248c
commit
89c3c31af9
39 changed files with 226 additions and 214 deletions
|
@ -1,24 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Shane Freeder <theboyetronic@gmail.com>
|
||||
Date: Sun, 27 Dec 2020 11:31:06 +0000
|
||||
Subject: [PATCH] Do not crash from invalid ingredient lists in
|
||||
VillagerAcquireTradeEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java b/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
|
||||
index 68bd3bb6fde77a65b5271631f6ef726dc613019b..742ffe531bb8f3a9ca34dea99b044123d90cfff9 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
|
||||
@@ -275,7 +275,11 @@ public abstract class AbstractVillager extends AgeableMob implements InventoryCa
|
||||
Bukkit.getPluginManager().callEvent(event);
|
||||
}
|
||||
if (!event.isCancelled()) {
|
||||
- recipeList.add(CraftMerchantRecipe.fromBukkit(event.getRecipe()).toMinecraft());
|
||||
+ // Paper start
|
||||
+ final CraftMerchantRecipe craftMerchantRecipe = CraftMerchantRecipe.fromBukkit(event.getRecipe());
|
||||
+ if (craftMerchantRecipe.getIngredients().isEmpty()) return;
|
||||
+ recipeList.add(craftMerchantRecipe.toMinecraft());
|
||||
+ // Paper end
|
||||
}
|
||||
// CraftBukkit end
|
||||
}
|
|
@ -1,251 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Thu, 2 Jul 2020 16:12:10 -0700
|
||||
Subject: [PATCH] Add PlayerTradeEvent and PlayerPurchaseEvent
|
||||
|
||||
Co-authored-by: Alexander <protonull@protonmail.com>
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java b/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
|
||||
index 742ffe531bb8f3a9ca34dea99b044123d90cfff9..bd283f71cb05ffbe1fed39afb41ae54dc52ec297 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/npc/AbstractVillager.java
|
||||
@@ -138,11 +138,24 @@ public abstract class AbstractVillager extends AgeableMob implements InventoryCa
|
||||
@Override
|
||||
public void overrideXp(int experience) {}
|
||||
|
||||
+ // Paper start
|
||||
+ @Override
|
||||
+ public void processTrade(MerchantOffer recipe, @Nullable io.papermc.paper.event.player.PlayerPurchaseEvent event) { // The MerchantRecipe passed in here is the one set by the PlayerPurchaseEvent
|
||||
+ if (event == null || event.willIncreaseTradeUses()) {
|
||||
+ recipe.increaseUses();
|
||||
+ }
|
||||
+ if (event == null || event.isRewardingExp()) {
|
||||
+ this.rewardTradeXp(recipe);
|
||||
+ }
|
||||
+ this.notifyTrade(recipe);
|
||||
+ }
|
||||
+ // Paper end
|
||||
+
|
||||
@Override
|
||||
public void notifyTrade(MerchantOffer offer) {
|
||||
- offer.increaseUses();
|
||||
+ // offer.increaseUses(); // Paper - handled in processTrade
|
||||
this.ambientSoundTime = -this.getAmbientSoundInterval();
|
||||
- this.rewardTradeXp(offer);
|
||||
+ // this.rewardTradeXp(offer); // Paper - handled in processTrade
|
||||
if (this.tradingPlayer instanceof ServerPlayer) {
|
||||
CriteriaTriggers.TRADE.trigger((ServerPlayer) this.tradingPlayer, this, offer.getResult());
|
||||
}
|
||||
diff --git a/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java b/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java
|
||||
index eecb852e4946c774ad295c53dbd904571262055a..3dc87e86dcd4c87e8e87e1dcd2765acb3b258bdf 100644
|
||||
--- a/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java
|
||||
+++ b/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java
|
||||
@@ -753,6 +753,14 @@ public abstract class AbstractContainerMenu {
|
||||
public abstract boolean stillValid(Player player);
|
||||
|
||||
protected boolean moveItemStackTo(ItemStack stack, int startIndex, int endIndex, boolean fromLast) {
|
||||
+ // Paper start
|
||||
+ return this.moveItemStackTo(stack, startIndex, endIndex, fromLast, false);
|
||||
+ }
|
||||
+ protected boolean moveItemStackTo(ItemStack stack, int startIndex, int endIndex, boolean fromLast, boolean isCheck) {
|
||||
+ if (isCheck) {
|
||||
+ stack = stack.copy();
|
||||
+ }
|
||||
+ // Paper end
|
||||
boolean flag1 = false;
|
||||
int k = startIndex;
|
||||
|
||||
@@ -775,18 +783,27 @@ public abstract class AbstractContainerMenu {
|
||||
|
||||
slot = (Slot) this.slots.get(k);
|
||||
itemstack1 = slot.getItem();
|
||||
+ // Paper start - clone if only a check
|
||||
+ if (isCheck) {
|
||||
+ itemstack1 = itemstack1.copy();
|
||||
+ }
|
||||
+ // Paper end
|
||||
if (!itemstack1.isEmpty() && ItemStack.isSameItemSameTags(stack, itemstack1)) {
|
||||
int l = itemstack1.getCount() + stack.getCount();
|
||||
|
||||
if (l <= stack.getMaxStackSize()) {
|
||||
stack.setCount(0);
|
||||
itemstack1.setCount(l);
|
||||
+ if (!isCheck) { // Paper - dont update if only a check
|
||||
slot.setChanged();
|
||||
+ } // Paper
|
||||
flag1 = true;
|
||||
} else if (itemstack1.getCount() < stack.getMaxStackSize()) {
|
||||
stack.shrink(stack.getMaxStackSize() - itemstack1.getCount());
|
||||
itemstack1.setCount(stack.getMaxStackSize());
|
||||
+ if (!isCheck) { // Paper - dont update if only a check
|
||||
slot.setChanged();
|
||||
+ } // Paper
|
||||
flag1 = true;
|
||||
}
|
||||
}
|
||||
@@ -817,14 +834,33 @@ public abstract class AbstractContainerMenu {
|
||||
|
||||
slot = (Slot) this.slots.get(k);
|
||||
itemstack1 = slot.getItem();
|
||||
+ // Paper start - clone if only a check
|
||||
+ if (isCheck) {
|
||||
+ itemstack1 = itemstack1.copy();
|
||||
+ }
|
||||
+ // Paper end
|
||||
if (itemstack1.isEmpty() && slot.mayPlace(stack)) {
|
||||
if (stack.getCount() > slot.getMaxStackSize()) {
|
||||
+ // Paper start - dont set slot if only check
|
||||
+ if (isCheck) {
|
||||
+ stack.shrink(slot.getMaxStackSize());
|
||||
+ } else {
|
||||
+ // Paper end
|
||||
slot.set(stack.split(slot.getMaxStackSize()));
|
||||
+ } // Paper
|
||||
} else {
|
||||
+ // Paper start - dont set slot if only check
|
||||
+ if (isCheck) {
|
||||
+ stack.shrink(stack.getCount());
|
||||
+ } else {
|
||||
+ // Paper end
|
||||
slot.set(stack.split(stack.getCount()));
|
||||
+ } // Paper
|
||||
}
|
||||
|
||||
+ if (!isCheck) { // Paper - dont update if only check
|
||||
slot.setChanged();
|
||||
+ } // Paper
|
||||
flag1 = true;
|
||||
break;
|
||||
}
|
||||
diff --git a/src/main/java/net/minecraft/world/inventory/MerchantMenu.java b/src/main/java/net/minecraft/world/inventory/MerchantMenu.java
|
||||
index 0d3002c5b13cbac0e021e8cdcf7d0685b256268a..3e3dfbe30fc5357e144aa176bc5df1b8a7ae6d64 100644
|
||||
--- a/src/main/java/net/minecraft/world/inventory/MerchantMenu.java
|
||||
+++ b/src/main/java/net/minecraft/world/inventory/MerchantMenu.java
|
||||
@@ -134,12 +134,12 @@ public class MerchantMenu extends AbstractContainerMenu {
|
||||
|
||||
itemstack = itemstack1.copy();
|
||||
if (index == 2) {
|
||||
- if (!this.moveItemStackTo(itemstack1, 3, 39, true)) {
|
||||
+ if (!this.moveItemStackTo(itemstack1, 3, 39, true, true)) { // Paper
|
||||
return ItemStack.EMPTY;
|
||||
}
|
||||
|
||||
- slot.onQuickCraft(itemstack1, itemstack);
|
||||
- this.playTradeSound();
|
||||
+ // slot.onQuickCraft(itemstack1, itemstack); // Paper - moved to after the non-check moveItemStackTo call
|
||||
+ // this.playTradeSound();
|
||||
} else if (index != 0 && index != 1) {
|
||||
if (index >= 3 && index < 30) {
|
||||
if (!this.moveItemStackTo(itemstack1, 30, 39, false)) {
|
||||
@@ -152,6 +152,7 @@ public class MerchantMenu extends AbstractContainerMenu {
|
||||
return ItemStack.EMPTY;
|
||||
}
|
||||
|
||||
+ if (index != 2) { // Paper - moved down for slot 2
|
||||
if (itemstack1.isEmpty()) {
|
||||
slot.set(ItemStack.EMPTY);
|
||||
} else {
|
||||
@@ -163,6 +164,21 @@ public class MerchantMenu extends AbstractContainerMenu {
|
||||
}
|
||||
|
||||
slot.onTake(player, itemstack1);
|
||||
+ } // Paper start - handle slot 2
|
||||
+ if (index == 2) { // is merchant result slot
|
||||
+ slot.onTake(player, itemstack1);
|
||||
+ if (itemstack1.isEmpty()) {
|
||||
+ slot.set(ItemStack.EMPTY);
|
||||
+ return ItemStack.EMPTY;
|
||||
+ }
|
||||
+
|
||||
+ this.moveItemStackTo(itemstack1, 3, 39, true, false); // This should always succeed because it's checked above
|
||||
+
|
||||
+ slot.onQuickCraft(itemstack1, itemstack);
|
||||
+ this.playTradeSound();
|
||||
+ slot.set(ItemStack.EMPTY); // itemstack1 should ALWAYS be empty
|
||||
+ }
|
||||
+ // Paper end
|
||||
}
|
||||
|
||||
return itemstack;
|
||||
diff --git a/src/main/java/net/minecraft/world/inventory/MerchantResultSlot.java b/src/main/java/net/minecraft/world/inventory/MerchantResultSlot.java
|
||||
index 74b28315197b81f80334ae6023113904e4fac4c3..7acf5ab9339e0134819aab5f270e99e927cc7a62 100644
|
||||
--- a/src/main/java/net/minecraft/world/inventory/MerchantResultSlot.java
|
||||
+++ b/src/main/java/net/minecraft/world/inventory/MerchantResultSlot.java
|
||||
@@ -47,13 +47,32 @@ public class MerchantResultSlot extends Slot {
|
||||
|
||||
@Override
|
||||
public void onTake(Player player, ItemStack stack) {
|
||||
- this.checkTakeAchievements(stack);
|
||||
+ // this.checkTakeAchievements(stack); // Paper - move to after event is called and not cancelled
|
||||
MerchantOffer merchantOffer = this.slots.getActiveOffer();
|
||||
+ // Paper start
|
||||
+ io.papermc.paper.event.player.PlayerPurchaseEvent event = null;
|
||||
+ if (merchantOffer != null && player instanceof net.minecraft.server.level.ServerPlayer serverPlayer) {
|
||||
+ if (this.merchant instanceof net.minecraft.world.entity.npc.AbstractVillager abstractVillager) {
|
||||
+ event = new io.papermc.paper.event.player.PlayerTradeEvent(serverPlayer.getBukkitEntity(), (org.bukkit.entity.AbstractVillager) abstractVillager.getBukkitEntity(), merchantOffer.asBukkit(), true, true);
|
||||
+ } else if (this.merchant instanceof org.bukkit.craftbukkit.inventory.CraftMerchantCustom.MinecraftMerchant) {
|
||||
+ event = new io.papermc.paper.event.player.PlayerPurchaseEvent(serverPlayer.getBukkitEntity(), merchantOffer.asBukkit(), false, true);
|
||||
+ }
|
||||
+ if (event != null) {
|
||||
+ if (!event.callEvent()) {
|
||||
+ stack.setCount(0);
|
||||
+ event.getPlayer().updateInventory();
|
||||
+ return;
|
||||
+ }
|
||||
+ merchantOffer = org.bukkit.craftbukkit.inventory.CraftMerchantRecipe.fromBukkit(event.getTrade()).toMinecraft();
|
||||
+ }
|
||||
+ }
|
||||
+ this.checkTakeAchievements(stack);
|
||||
+ // Paper end
|
||||
if (merchantOffer != null) {
|
||||
ItemStack itemStack = this.slots.getItem(0);
|
||||
ItemStack itemStack2 = this.slots.getItem(1);
|
||||
if (merchantOffer.take(itemStack, itemStack2) || merchantOffer.take(itemStack2, itemStack)) {
|
||||
- this.merchant.notifyTrade(merchantOffer);
|
||||
+ this.merchant.processTrade(merchantOffer, event); // Paper
|
||||
player.awardStat(Stats.TRADED_WITH_VILLAGER);
|
||||
this.slots.setItem(0, itemStack);
|
||||
this.slots.setItem(1, itemStack2);
|
||||
diff --git a/src/main/java/net/minecraft/world/item/trading/Merchant.java b/src/main/java/net/minecraft/world/item/trading/Merchant.java
|
||||
index d41f44ed2e497ba3373d170c08488b49e88334c4..d3a99ba6f3085ad12b67ddc94cc4ab393ec7ecbe 100644
|
||||
--- a/src/main/java/net/minecraft/world/item/trading/Merchant.java
|
||||
+++ b/src/main/java/net/minecraft/world/item/trading/Merchant.java
|
||||
@@ -20,6 +20,7 @@ public interface Merchant {
|
||||
|
||||
void overrideOffers(MerchantOffers offers);
|
||||
|
||||
+ default void processTrade(MerchantOffer merchantRecipe, @Nullable io.papermc.paper.event.player.PlayerPurchaseEvent event) { this.notifyTrade(merchantRecipe); } // Paper
|
||||
void notifyTrade(MerchantOffer offer);
|
||||
|
||||
void notifyTradeUpdated(ItemStack stack);
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/inventory/CraftMerchantCustom.java b/src/main/java/org/bukkit/craftbukkit/inventory/CraftMerchantCustom.java
|
||||
index 552851cff3678d605428866999951fefd4375d7a..9f6ce6c4cba1e6fe83fbac129da990748681ce94 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/inventory/CraftMerchantCustom.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/inventory/CraftMerchantCustom.java
|
||||
@@ -79,10 +79,25 @@ public class CraftMerchantCustom extends CraftMerchant {
|
||||
return this.trades;
|
||||
}
|
||||
|
||||
+ // Paper start
|
||||
+ @Override
|
||||
+ public void processTrade(MerchantOffer merchantRecipe, @javax.annotation.Nullable io.papermc.paper.event.player.PlayerPurchaseEvent event) { // The MerchantRecipe passed in here is the one set by the PlayerPurchaseEvent
|
||||
+ /** Based on {@link net.minecraft.world.entity.npc.AbstractVillager#processTrade(MerchantOffer, io.papermc.paper.event.player.PlayerPurchaseEvent)} */
|
||||
+ if (getTradingPlayer() instanceof net.minecraft.server.level.ServerPlayer) {
|
||||
+ if (event == null || event.willIncreaseTradeUses()) {
|
||||
+ merchantRecipe.increaseUses();
|
||||
+ }
|
||||
+ if (event == null || event.isRewardingExp()) {
|
||||
+ this.tradingWorld.addFreshEntity(new net.minecraft.world.entity.ExperienceOrb(tradingWorld, tradingPlayer.getX(), tradingPlayer.getY(), tradingPlayer.getZ(), merchantRecipe.getXp(), org.bukkit.entity.ExperienceOrb.SpawnReason.VILLAGER_TRADE, this.tradingPlayer, null));
|
||||
+ }
|
||||
+ }
|
||||
+ this.notifyTrade(merchantRecipe);
|
||||
+ }
|
||||
+ // Paper end
|
||||
@Override
|
||||
public void notifyTrade(MerchantOffer offer) {
|
||||
// increase recipe's uses
|
||||
- offer.increaseUses();
|
||||
+ // offer.increaseUses(); // Paper - handled above in processTrade
|
||||
}
|
||||
|
||||
@Override
|
|
@ -1,42 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jason Penilla <11360596+jpenilla@users.noreply.github.com>
|
||||
Date: Wed, 25 Nov 2020 23:20:44 -0800
|
||||
Subject: [PATCH] Implement TargetHitEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/level/block/TargetBlock.java b/src/main/java/net/minecraft/world/level/block/TargetBlock.java
|
||||
index f71649338588c576cffc7fecc1e83217c529c335..20955a3944a2fcb66ad98267ef3570ddfc32980e 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/block/TargetBlock.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/block/TargetBlock.java
|
||||
@@ -35,6 +35,10 @@ public class TargetBlock extends Block {
|
||||
@Override
|
||||
public void onProjectileHit(Level world, BlockState state, BlockHitResult hit, Projectile projectile) {
|
||||
int i = updateRedstoneOutput(world, state, hit, projectile);
|
||||
+ // Paper start
|
||||
+ }
|
||||
+ private static void awardTargetHitCriteria(Projectile projectile, BlockHitResult hit, int i) {
|
||||
+ // Paper end
|
||||
Entity entity = projectile.getOwner();
|
||||
if (entity instanceof ServerPlayer serverPlayer) {
|
||||
serverPlayer.awardStat(Stats.TARGET_HIT);
|
||||
@@ -46,6 +50,20 @@ public class TargetBlock extends Block {
|
||||
private static int updateRedstoneOutput(LevelAccessor world, BlockState state, BlockHitResult hitResult, Entity entity) {
|
||||
int i = getRedstoneStrength(hitResult, hitResult.getLocation());
|
||||
int j = entity instanceof AbstractArrow ? 20 : 8;
|
||||
+ // Paper start
|
||||
+ if (entity instanceof Projectile) {
|
||||
+ final Projectile projectile = (Projectile) entity;
|
||||
+ final org.bukkit.craftbukkit.block.CraftBlock craftBlock = org.bukkit.craftbukkit.block.CraftBlock.at(world, hitResult.getBlockPos());
|
||||
+ final org.bukkit.block.BlockFace blockFace = org.bukkit.craftbukkit.block.CraftBlock.notchToBlockFace(hitResult.getDirection());
|
||||
+ final io.papermc.paper.event.block.TargetHitEvent targetHitEvent = new io.papermc.paper.event.block.TargetHitEvent((org.bukkit.entity.Projectile) projectile.getBukkitEntity(), craftBlock, blockFace, i);
|
||||
+ if (targetHitEvent.callEvent()) {
|
||||
+ i = targetHitEvent.getSignalStrength();
|
||||
+ awardTargetHitCriteria(projectile, hitResult, i);
|
||||
+ } else {
|
||||
+ return i;
|
||||
+ }
|
||||
+ }
|
||||
+ // Paper end
|
||||
if (!world.getBlockTicks().hasScheduledTick(hitResult.getBlockPos(), state.getBlock())) {
|
||||
setOutputPower(world, state, i, hitResult.getBlockPos(), j);
|
||||
}
|
|
@ -1,40 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Aikar <aikar@aikar.co>
|
||||
Date: Wed, 30 Dec 2020 19:43:01 -0500
|
||||
Subject: [PATCH] Additional Block Material API's
|
||||
|
||||
Faster version for isSolid() that utilizes NMS's state for isSolid instead of the slower
|
||||
process to do this in the Bukkit API
|
||||
|
||||
Adds API for buildable, replaceable, burnable too.
|
||||
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
|
||||
index 653dcec33f83ab490af424faa6ede7df07d41742..817d7143fb60916a6747ee4b9f7c77becd9071c1 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/block/CraftBlock.java
|
||||
@@ -463,6 +463,25 @@ public class CraftBlock implements Block {
|
||||
return this.getNMS().getMaterial().isLiquid();
|
||||
}
|
||||
|
||||
+ // Paper start
|
||||
+ @Override
|
||||
+ public boolean isBuildable() {
|
||||
+ return getNMS().getMaterial().isSolid(); // This is in fact isSolid, despite the fact that isSolid below returns blocksMotion
|
||||
+ }
|
||||
+ @Override
|
||||
+ public boolean isBurnable() {
|
||||
+ return getNMS().getMaterial().isFlammable();
|
||||
+ }
|
||||
+ @Override
|
||||
+ public boolean isReplaceable() {
|
||||
+ return getNMS().getMaterial().isReplaceable();
|
||||
+ }
|
||||
+ @Override
|
||||
+ public boolean isSolid() {
|
||||
+ return getNMS().getMaterial().blocksMotion();
|
||||
+ }
|
||||
+ // Paper end
|
||||
+
|
||||
@Override
|
||||
public PistonMoveReaction getPistonMoveReaction() {
|
||||
return PistonMoveReaction.getById(this.getNMS().getPistonPushReaction().ordinal());
|
|
@ -1,49 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: PepperCode1 <44146161+PepperCode1@users.noreply.github.com>
|
||||
Date: Thu, 23 Jul 2020 14:25:07 -0700
|
||||
Subject: [PATCH] Fix harming potion dupe
|
||||
|
||||
EntityLiving#applyInstantEffect() immediately kills the player and drops their inventory.
|
||||
Before this patch, instant effects would be applied before the potion ItemStack is removed and replaced with a glass bottle. This caused the potion ItemStack to be dropped before it was supposed to be removed from the inventory. It also caused the glass bottle to be put into a dead player's inventory.
|
||||
This patch makes it so that instant effects are applied after the potion ItemStack is removed, and the glass bottle is only put into the player's inventory if the player is not dead. Otherwise, the glass bottle is dropped on the ground.
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/item/PotionItem.java b/src/main/java/net/minecraft/world/item/PotionItem.java
|
||||
index 166f7483163a0cf62b000764d635ec2ee36a5036..4b5c9da0e858016c1a3afcb6eaa1ff4cbf47739e 100644
|
||||
--- a/src/main/java/net/minecraft/world/item/PotionItem.java
|
||||
+++ b/src/main/java/net/minecraft/world/item/PotionItem.java
|
||||
@@ -41,6 +41,7 @@ public class PotionItem extends Item {
|
||||
CriteriaTriggers.CONSUME_ITEM.trigger((ServerPlayer) entityhuman, stack);
|
||||
}
|
||||
|
||||
+ List<MobEffectInstance> instantLater = new java.util.ArrayList<>(); // Paper - Fix harming potion dupe
|
||||
if (!world.isClientSide) {
|
||||
List<MobEffectInstance> list = PotionUtils.getMobEffects(stack);
|
||||
Iterator iterator = list.iterator();
|
||||
@@ -49,7 +50,7 @@ public class PotionItem extends Item {
|
||||
MobEffectInstance mobeffect = (MobEffectInstance) iterator.next();
|
||||
|
||||
if (mobeffect.getEffect().isInstantenous()) {
|
||||
- mobeffect.getEffect().applyInstantenousEffect(entityhuman, entityhuman, user, mobeffect.getAmplifier(), 1.0D);
|
||||
+ instantLater.add(mobeffect); // Paper - Fix harming potion dupe
|
||||
} else {
|
||||
user.addEffect(new MobEffectInstance(mobeffect), org.bukkit.event.entity.EntityPotionEffectEvent.Cause.POTION_DRINK); // CraftBukkit
|
||||
}
|
||||
@@ -63,7 +64,18 @@ public class PotionItem extends Item {
|
||||
}
|
||||
}
|
||||
|
||||
+ // Paper start - Fix harming potion dupe
|
||||
+ for (MobEffectInstance mobeffect : instantLater) {
|
||||
+ mobeffect.getEffect().applyInstantenousEffect(entityhuman, entityhuman, user, mobeffect.getAmplifier(), 1.0D);
|
||||
+ }
|
||||
+ // Paper end
|
||||
if (entityhuman == null || !entityhuman.getAbilities().instabuild) {
|
||||
+ // Paper start - Fix harming potion dupe
|
||||
+ if (user.getHealth() <= 0 && !user.level.getGameRules().getBoolean(net.minecraft.world.level.GameRules.RULE_KEEPINVENTORY)) {
|
||||
+ user.spawnAtLocation(new ItemStack(Items.GLASS_BOTTLE), 0);
|
||||
+ return ItemStack.EMPTY;
|
||||
+ }
|
||||
+ // Paper end
|
||||
if (stack.isEmpty()) {
|
||||
return new ItemStack(Items.GLASS_BOTTLE);
|
||||
}
|
|
@ -1,62 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Madeline Miller <mnmiller1@me.com>
|
||||
Date: Thu, 31 Dec 2020 12:48:19 +1000
|
||||
Subject: [PATCH] Implement API to get Material from Boats and Minecarts
|
||||
|
||||
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftBoat.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftBoat.java
|
||||
index 47f95fb26793fbf6c5c37187d4958ee5ba93f060..39e7aeb409a39bd8cd8200b18dd3da1e427519ab 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/entity/CraftBoat.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftBoat.java
|
||||
@@ -65,6 +65,13 @@ public class CraftBoat extends CraftVehicle implements Boat {
|
||||
this.getHandle().landBoats = workOnLand;
|
||||
}
|
||||
|
||||
+ // Paper start
|
||||
+ @Override
|
||||
+ public org.bukkit.Material getBoatMaterial() {
|
||||
+ return org.bukkit.craftbukkit.util.CraftMagicNumbers.getMaterial(getHandle().getDropItem());
|
||||
+ }
|
||||
+ // Paper end
|
||||
+
|
||||
@Override
|
||||
public net.minecraft.world.entity.vehicle.Boat getHandle() {
|
||||
return (net.minecraft.world.entity.vehicle.Boat) entity;
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftMinecart.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftMinecart.java
|
||||
index 053112d7411caa6f439bd344e74aff8c844d93ac..067fcc1f44d59dd675a9cc5485234c87366ffe10 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/entity/CraftMinecart.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftMinecart.java
|
||||
@@ -1,8 +1,10 @@
|
||||
package org.bukkit.craftbukkit.entity;
|
||||
|
||||
import net.minecraft.world.entity.vehicle.AbstractMinecart;
|
||||
+import net.minecraft.world.item.Items; // Paper
|
||||
import net.minecraft.world.level.block.Blocks;
|
||||
import net.minecraft.world.level.block.state.BlockState;
|
||||
+import org.bukkit.Material; // Paper
|
||||
import org.bukkit.block.data.BlockData;
|
||||
import org.bukkit.craftbukkit.CraftServer;
|
||||
import org.bukkit.craftbukkit.block.data.CraftBlockData;
|
||||
@@ -68,6 +70,22 @@ public abstract class CraftMinecart extends CraftVehicle implements Minecart {
|
||||
this.getHandle().setDerailedVelocityMod(derailed);
|
||||
}
|
||||
|
||||
+ // Paper start
|
||||
+ @Override
|
||||
+ public Material getMinecartMaterial() {
|
||||
+ net.minecraft.world.item.Item minecartItem = switch (getHandle().getMinecartType()) {
|
||||
+ case CHEST -> Items.CHEST_MINECART;
|
||||
+ case FURNACE -> Items.FURNACE_MINECART;
|
||||
+ case TNT -> Items.TNT_MINECART;
|
||||
+ case HOPPER -> Items.HOPPER_MINECART;
|
||||
+ case COMMAND_BLOCK -> Items.COMMAND_BLOCK_MINECART;
|
||||
+ case RIDEABLE, SPAWNER -> Items.MINECART;
|
||||
+ };
|
||||
+
|
||||
+ return CraftMagicNumbers.getMaterial(minecartItem);
|
||||
+ }
|
||||
+ // Paper end
|
||||
+
|
||||
@Override
|
||||
public AbstractMinecart getHandle() {
|
||||
return (AbstractMinecart) entity;
|
|
@ -1,36 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: lukas <lukasalt98@gmail.com>
|
||||
Date: Sun, 27 Dec 2020 16:47:00 +0100
|
||||
Subject: [PATCH] Cache burn durations
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/level/block/entity/AbstractFurnaceBlockEntity.java b/src/main/java/net/minecraft/world/level/block/entity/AbstractFurnaceBlockEntity.java
|
||||
index 635d47d4bea679e96736ef891c40f57488cbc6a1..e62fa09ca481183be2ee158b0717172c90de1b92 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/block/entity/AbstractFurnaceBlockEntity.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/block/entity/AbstractFurnaceBlockEntity.java
|
||||
@@ -129,7 +129,13 @@ public abstract class AbstractFurnaceBlockEntity extends BaseContainerBlockEntit
|
||||
this.recipeType = recipeType;
|
||||
}
|
||||
|
||||
+ private static Map<Item, Integer> cachedBurnDurations = null; // Paper - cache burn durations
|
||||
public static Map<Item, Integer> getFuel() {
|
||||
+ // Paper start - cache burn durations
|
||||
+ if(cachedBurnDurations != null) {
|
||||
+ return cachedBurnDurations;
|
||||
+ }
|
||||
+ // Paper end
|
||||
Map<Item, Integer> map = Maps.newLinkedHashMap();
|
||||
|
||||
AbstractFurnaceBlockEntity.add(map, (ItemLike) Items.LAVA_BUCKET, 20000);
|
||||
@@ -194,7 +200,10 @@ public abstract class AbstractFurnaceBlockEntity extends BaseContainerBlockEntit
|
||||
AbstractFurnaceBlockEntity.add(map, (ItemLike) Blocks.COMPOSTER, 300);
|
||||
AbstractFurnaceBlockEntity.add(map, (ItemLike) Blocks.AZALEA, 100);
|
||||
AbstractFurnaceBlockEntity.add(map, (ItemLike) Blocks.FLOWERING_AZALEA, 100);
|
||||
- return map;
|
||||
+ // Paper start - cache burn durations
|
||||
+ cachedBurnDurations = com.google.common.collect.ImmutableMap.copyOf(map);
|
||||
+ return cachedBurnDurations;
|
||||
+ // Paper end
|
||||
}
|
||||
|
||||
// CraftBukkit start - add fields and methods
|
|
@ -1,35 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: BrodyBeckwith <brody@beckwith.dev>
|
||||
Date: Fri, 9 Oct 2020 20:30:12 -0400
|
||||
Subject: [PATCH] Allow disabling mob spawner spawn egg transformation
|
||||
|
||||
|
||||
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
index d6cbd9ea2eb70e25a5e37e0bdda2396a99b3342e..5fe4d2005e87a7b69e98dcd68e0fff3cc26a8c96 100644
|
||||
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
@@ -138,6 +138,11 @@ public class PaperWorldConfig {
|
||||
fixCuringZombieVillagerDiscountExploit = getBoolean("game-mechanics.fix-curing-zombie-villager-discount-exploit", fixCuringZombieVillagerDiscountExploit);
|
||||
}
|
||||
|
||||
+ public boolean disableMobSpawnerSpawnEggTransformation = false;
|
||||
+ private void disableMobSpawnerSpawnEggTransformation() {
|
||||
+ disableMobSpawnerSpawnEggTransformation = getBoolean("game-mechanics.disable-mob-spawner-spawn-egg-transformation", disableMobSpawnerSpawnEggTransformation);
|
||||
+ }
|
||||
+
|
||||
public short keepLoadedRange;
|
||||
private void keepLoadedRange() {
|
||||
keepLoadedRange = (short) (getInt("keep-spawn-loaded-range", Math.min(spigotConfig.viewDistance, 10)) * 16);
|
||||
diff --git a/src/main/java/net/minecraft/world/item/SpawnEggItem.java b/src/main/java/net/minecraft/world/item/SpawnEggItem.java
|
||||
index 901df339e40738413ce1cce87e72be82cc893087..3d9daa9e2c35d7fd277bde37cd5d1bfc9362d2ee 100644
|
||||
--- a/src/main/java/net/minecraft/world/item/SpawnEggItem.java
|
||||
+++ b/src/main/java/net/minecraft/world/item/SpawnEggItem.java
|
||||
@@ -61,7 +61,7 @@ public class SpawnEggItem extends Item {
|
||||
Direction enumdirection = context.getClickedFace();
|
||||
BlockState iblockdata = world.getBlockState(blockposition);
|
||||
|
||||
- if (iblockdata.is(Blocks.SPAWNER)) {
|
||||
+ if (!world.paperConfig.disableMobSpawnerSpawnEggTransformation && iblockdata.is(Blocks.SPAWNER)) { // Paper
|
||||
BlockEntity tileentity = world.getBlockEntity(blockposition);
|
||||
|
||||
if (tileentity instanceof SpawnerBlockEntity) {
|
|
@ -1,54 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Aikar <aikar@aikar.co>
|
||||
Date: Thu, 8 Oct 2020 00:00:25 -0400
|
||||
Subject: [PATCH] Fix "Not a string" Map Conversion spam
|
||||
|
||||
The maps did convert successfully, but had noisy logs due to Spigot
|
||||
implementing this logic incorrectly.
|
||||
|
||||
This stops the spam by converting the old format to new before
|
||||
requesting the world.
|
||||
|
||||
Track spigot issue to see when fixed: https://hub.spigotmc.org/jira/browse/SPIGOT-6181
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/level/saveddata/maps/MapItemSavedData.java b/src/main/java/net/minecraft/world/level/saveddata/maps/MapItemSavedData.java
|
||||
index 913fabc7f42c05ccec6501247a5e8d1d481756ee..4acbcafc158cf11af51d9518ba5b83aaa75f52a1 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/saveddata/maps/MapItemSavedData.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/saveddata/maps/MapItemSavedData.java
|
||||
@@ -15,6 +15,8 @@ import net.minecraft.core.BlockPos;
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.nbt.ListTag;
|
||||
import net.minecraft.nbt.NbtOps;
|
||||
+import net.minecraft.nbt.NumericTag;
|
||||
+import net.minecraft.nbt.StringTag;
|
||||
import net.minecraft.nbt.Tag;
|
||||
import net.minecraft.network.chat.Component;
|
||||
import net.minecraft.network.protocol.Packet;
|
||||
@@ -103,7 +105,26 @@ public class MapItemSavedData extends SavedData {
|
||||
}
|
||||
|
||||
public static MapItemSavedData load(CompoundTag nbt) {
|
||||
- DataResult<ResourceKey<Level>> dataresult = DimensionType.parseLegacy(new Dynamic(NbtOps.INSTANCE, nbt.get("dimension"))); // CraftBukkit - decompile error
|
||||
+ // Paper start - fix "Not a string" spam
|
||||
+ Tag dimension = nbt.get("dimension");
|
||||
+ if (dimension instanceof NumericTag && ((NumericTag) dimension).getAsInt() >= CraftWorld.CUSTOM_DIMENSION_OFFSET) {
|
||||
+ long least = nbt.getLong("UUIDLeast");
|
||||
+ long most = nbt.getLong("UUIDMost");
|
||||
+
|
||||
+ if (least != 0L && most != 0L) {
|
||||
+ UUID uuid = new UUID(most, least);
|
||||
+ CraftWorld world = (CraftWorld) Bukkit.getWorld(uuid);
|
||||
+ if (world != null) {
|
||||
+ dimension = StringTag.valueOf("minecraft:" + world.getName().toLowerCase(java.util.Locale.ENGLISH));
|
||||
+ } else {
|
||||
+ dimension = StringTag.valueOf("bukkit:_invalidworld_");
|
||||
+ }
|
||||
+ } else {
|
||||
+ dimension = StringTag.valueOf("bukkit:_invalidworld_");
|
||||
+ }
|
||||
+ }
|
||||
+ DataResult<ResourceKey<Level>> dataresult = DimensionType.parseLegacy(new Dynamic(NbtOps.INSTANCE, dimension)); // CraftBukkit - decompile error
|
||||
+ // Paper end - fix "Not a string" spam
|
||||
Logger logger = MapItemSavedData.LOGGER;
|
||||
|
||||
Objects.requireNonNull(logger);
|
|
@ -1,37 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: MisterVector <whizkid3000@hotmail.com>
|
||||
Date: Tue, 13 Aug 2019 19:45:06 -0700
|
||||
Subject: [PATCH] Implement PlayerFlowerPotManipulateEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/level/block/FlowerPotBlock.java b/src/main/java/net/minecraft/world/level/block/FlowerPotBlock.java
|
||||
index 9a8fc69de43fcfeebcb31c895fa4b5868952fa0a..db05c1ea847d60ad45d33cd798cb34ad3f5cfd75 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/block/FlowerPotBlock.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/block/FlowerPotBlock.java
|
||||
@@ -52,6 +52,26 @@ public class FlowerPotBlock extends Block {
|
||||
boolean bl = blockState.is(Blocks.AIR);
|
||||
boolean bl2 = this.isEmpty();
|
||||
if (bl != bl2) {
|
||||
+ // Paper start
|
||||
+ org.bukkit.entity.Player player1 = (org.bukkit.entity.Player) player.getBukkitEntity();
|
||||
+ boolean placing = bl2;
|
||||
+ org.bukkit.block.Block bukkitblock = org.bukkit.craftbukkit.block.CraftBlock.at(world, pos);
|
||||
+ org.bukkit.inventory.ItemStack bukkititemstack = org.bukkit.craftbukkit.inventory.CraftItemStack.asBukkitCopy(itemStack);
|
||||
+ org.bukkit.Material mat = org.bukkit.craftbukkit.util.CraftMagicNumbers.getMaterial(content);
|
||||
+ org.bukkit.inventory.ItemStack bukkititemstack1 = new org.bukkit.inventory.ItemStack(mat, 1);
|
||||
+ org.bukkit.inventory.ItemStack whichitem = placing ? bukkititemstack : bukkititemstack1;
|
||||
+
|
||||
+ io.papermc.paper.event.player.PlayerFlowerPotManipulateEvent event = new io.papermc.paper.event.player.PlayerFlowerPotManipulateEvent(player1, bukkitblock, whichitem, placing);
|
||||
+ player1.getServer().getPluginManager().callEvent(event);
|
||||
+
|
||||
+ if (event.isCancelled()) {
|
||||
+ // Update client
|
||||
+ player1.sendBlockChange(bukkitblock.getLocation(), bukkitblock.getBlockData());
|
||||
+ player1.updateInventory();
|
||||
+
|
||||
+ return InteractionResult.PASS;
|
||||
+ }
|
||||
+ // Paper end
|
||||
if (bl2) {
|
||||
world.setBlock(pos, blockState, 3);
|
||||
player.awardStat(Stats.POT_FLOWER);
|
|
@ -1,29 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: TheMolkaPL <themolkapl@gmail.com>
|
||||
Date: Sun, 21 Jun 2020 17:21:46 +0200
|
||||
Subject: [PATCH] Fix interact event not being called in adventure
|
||||
|
||||
Call PlayerInteractEvent when left-clicking on a block in adventure mode
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
|
||||
index 2a5eb98c6e0f54f098c24ec09c68c3a4dda21aa8..8b2c246f60886053beb9c4baf18c867910b9a8fd 100644
|
||||
--- a/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
|
||||
+++ b/src/main/java/net/minecraft/server/network/ServerGamePacketListenerImpl.java
|
||||
@@ -1764,7 +1764,7 @@ public class ServerGamePacketListenerImpl implements ServerPlayerConnection, Ser
|
||||
MutableComponent ichatmutablecomponent = (new TranslatableComponent("build.tooHigh", new Object[]{i - 1})).withStyle(ChatFormatting.RED);
|
||||
|
||||
this.player.sendMessage(ichatmutablecomponent, ChatType.GAME_INFO, Util.NIL_UUID);
|
||||
- } else if (enuminteractionresult.shouldSwing()) {
|
||||
+ } else if (enuminteractionresult.shouldSwing() && !this.player.gameMode.interactResult) {
|
||||
this.player.swing(enumhand, true);
|
||||
}
|
||||
}
|
||||
@@ -2242,7 +2242,7 @@ public class ServerGamePacketListenerImpl implements ServerPlayerConnection, Ser
|
||||
Vec3 vec3d1 = vec3d.add((double) f7 * d3, (double) f6 * d3, (double) f8 * d3);
|
||||
HitResult movingobjectposition = this.player.level.clip(new ClipContext(vec3d, vec3d1, ClipContext.Block.OUTLINE, ClipContext.Fluid.NONE, this.player));
|
||||
|
||||
- if (movingobjectposition == null || movingobjectposition.getType() != HitResult.Type.BLOCK) {
|
||||
+ if (movingobjectposition == null || movingobjectposition.getType() != HitResult.Type.BLOCK || this.player.gameMode.getGameModeForPlayer() == GameType.ADVENTURE) { // Paper - call PlayerInteractEvent when left-clicking on a block in adventure mode
|
||||
CraftEventFactory.callPlayerInteractEvent(this.player, Action.LEFT_CLICK_AIR, this.player.getInventory().getSelected(), InteractionHand.MAIN_HAND);
|
||||
}
|
||||
|
|
@ -1,32 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Wed, 18 Nov 2020 11:32:46 -0800
|
||||
Subject: [PATCH] Zombie API - breaking doors
|
||||
|
||||
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftZombie.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftZombie.java
|
||||
index 77e4875484bdaedfba576a6b008245c488b2a112..bcd765abe0317fe5c1fa2efcbc43d7b8503f80a6 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/entity/CraftZombie.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftZombie.java
|
||||
@@ -128,6 +128,21 @@ public class CraftZombie extends CraftMonster implements Zombie {
|
||||
public void setShouldBurnInDay(boolean shouldBurnInDay) {
|
||||
getHandle().setShouldBurnInDay(shouldBurnInDay);
|
||||
}
|
||||
+
|
||||
+ @Override
|
||||
+ public boolean canBreakDoors() {
|
||||
+ return getHandle().canBreakDoors();
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public void setCanBreakDoors(boolean canBreakDoors) {
|
||||
+ getHandle().setCanBreakDoors(canBreakDoors);
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public boolean supportsBreakingDoors() {
|
||||
+ return getHandle().supportsBreakDoorGoal();
|
||||
+ }
|
||||
// Paper end
|
||||
|
||||
@Override
|
|
@ -1,18 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Mon, 24 Aug 2020 08:39:06 -0700
|
||||
Subject: [PATCH] Fix nerfed slime when splitting
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/monster/Slime.java b/src/main/java/net/minecraft/world/entity/monster/Slime.java
|
||||
index 8d03466e2f546aae705c1d4dd2d562d3db2f2671..85edba5de3ce6c1fce8872855544863de84e7759 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/monster/Slime.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/monster/Slime.java
|
||||
@@ -239,6 +239,7 @@ public class Slime extends Mob implements Enemy {
|
||||
entityslime.setPersistenceRequired();
|
||||
}
|
||||
|
||||
+ entityslime.aware = this.aware; // Paper
|
||||
entityslime.setCustomName(ichatbasecomponent);
|
||||
entityslime.setNoAi(flag);
|
||||
entityslime.setInvulnerable(this.isInvulnerable());
|
|
@ -1,42 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: JRoy <joshroy126@gmail.com>
|
||||
Date: Wed, 7 Oct 2020 12:04:01 -0400
|
||||
Subject: [PATCH] Add EntityLoadCrossbowEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/item/CrossbowItem.java b/src/main/java/net/minecraft/world/item/CrossbowItem.java
|
||||
index 1ec3fd560a2b6528040bca68be4a05c9a8435ae9..c0c211c7227f4ce5d1e0e433419425e6bb13046f 100644
|
||||
--- a/src/main/java/net/minecraft/world/item/CrossbowItem.java
|
||||
+++ b/src/main/java/net/minecraft/world/item/CrossbowItem.java
|
||||
@@ -90,7 +90,14 @@ public class CrossbowItem extends ProjectileWeaponItem implements Vanishable {
|
||||
int j = this.getUseDuration(stack) - remainingUseTicks;
|
||||
float f = CrossbowItem.getPowerForTime(j, stack);
|
||||
|
||||
- if (f >= 1.0F && !CrossbowItem.isCharged(stack) && CrossbowItem.tryLoadProjectiles(user, stack)) {
|
||||
+ // Paper start - EntityLoadCrossbowEvent
|
||||
+ if (f >= 1.0F && !CrossbowItem.isCharged(stack) /*&& CrossbowItem.tryLoadProjectiles(entityliving, itemstack)*/) {
|
||||
+ final io.papermc.paper.event.entity.EntityLoadCrossbowEvent event = new io.papermc.paper.event.entity.EntityLoadCrossbowEvent(user.getBukkitLivingEntity(), stack.asBukkitMirror(), user.getUsedItemHand() == InteractionHand.MAIN_HAND ? org.bukkit.inventory.EquipmentSlot.HAND : org.bukkit.inventory.EquipmentSlot.OFF_HAND);
|
||||
+ if (!event.callEvent() || !tryLoadProjectiles(user, stack, event.shouldConsumeItem())) {
|
||||
+ if (user instanceof ServerPlayer player) player.containerMenu.sendAllDataToRemote();
|
||||
+ return;
|
||||
+ }
|
||||
+ // Paper end
|
||||
CrossbowItem.setCharged(stack, true);
|
||||
SoundSource soundcategory = user instanceof Player ? SoundSource.PLAYERS : SoundSource.HOSTILE;
|
||||
|
||||
@@ -100,9 +107,14 @@ public class CrossbowItem extends ProjectileWeaponItem implements Vanishable {
|
||||
}
|
||||
|
||||
private static boolean tryLoadProjectiles(LivingEntity shooter, ItemStack projectile) {
|
||||
+ // Paper start
|
||||
+ return CrossbowItem.tryLoadProjectiles(shooter, projectile, true);
|
||||
+ }
|
||||
+ private static boolean tryLoadProjectiles(LivingEntity shooter, ItemStack projectile, boolean consume) {
|
||||
+ // Paper end
|
||||
int i = EnchantmentHelper.getItemEnchantmentLevel(Enchantments.MULTISHOT, projectile);
|
||||
int j = i == 0 ? 1 : 3;
|
||||
- boolean flag = shooter instanceof Player && ((Player) shooter).getAbilities().instabuild;
|
||||
+ boolean flag = !consume || shooter instanceof Player && ((Player) shooter).getAbilities().instabuild; // Paper - add consume
|
||||
ItemStack itemstack1 = shooter.getProjectile(projectile);
|
||||
ItemStack itemstack2 = itemstack1.copy();
|
||||
|
|
@ -1,20 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Gabscap <git@gabscap.de>
|
||||
Date: Sat, 19 Mar 2016 22:25:11 +0100
|
||||
Subject: [PATCH] Guardian beam workaround
|
||||
|
||||
This patch is a workaround for MC-165595
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/network/protocol/game/ClientboundSetTimePacket.java b/src/main/java/net/minecraft/network/protocol/game/ClientboundSetTimePacket.java
|
||||
index 9ec6145fe04ec64bbee8ec6a837719caebdbc6f5..689ad22925b2561f7c8db961743eb1f821dbb25f 100644
|
||||
--- a/src/main/java/net/minecraft/network/protocol/game/ClientboundSetTimePacket.java
|
||||
+++ b/src/main/java/net/minecraft/network/protocol/game/ClientboundSetTimePacket.java
|
||||
@@ -8,7 +8,7 @@ public class ClientboundSetTimePacket implements Packet<ClientGamePacketListener
|
||||
private final long dayTime;
|
||||
|
||||
public ClientboundSetTimePacket(long time, long timeOfDay, boolean doDaylightCycle) {
|
||||
- this.gameTime = time;
|
||||
+ this.gameTime = time % 192000; // Paper - fix guardian beam
|
||||
long l = timeOfDay;
|
||||
if (!doDaylightCycle) {
|
||||
l = -timeOfDay;
|
|
@ -1,98 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Sun, 20 Dec 2020 16:41:44 -0800
|
||||
Subject: [PATCH] Added WorldGameRuleChangeEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/commands/GameRuleCommand.java b/src/main/java/net/minecraft/server/commands/GameRuleCommand.java
|
||||
index f2e53fbb067a3909f386386eb3b89dfe090ee096..6f6292e7945cec1bdc69632dbfb950d6af53df42 100644
|
||||
--- a/src/main/java/net/minecraft/server/commands/GameRuleCommand.java
|
||||
+++ b/src/main/java/net/minecraft/server/commands/GameRuleCommand.java
|
||||
@@ -33,7 +33,7 @@ public class GameRuleCommand {
|
||||
CommandSourceStack commandlistenerwrapper = (CommandSourceStack) context.getSource();
|
||||
T t0 = commandlistenerwrapper.getLevel().getGameRules().getRule(key); // CraftBukkit
|
||||
|
||||
- t0.setFromArgument(context, "value");
|
||||
+ t0.setFromArgument(context, "value", key); // Paper
|
||||
commandlistenerwrapper.sendSuccess(new TranslatableComponent("commands.gamerule.set", new Object[]{key.getId(), t0.toString()}), true);
|
||||
return t0.getCommandResult();
|
||||
}
|
||||
diff --git a/src/main/java/net/minecraft/world/level/GameRules.java b/src/main/java/net/minecraft/world/level/GameRules.java
|
||||
index 74e10d581f8c1b0b026d8f940194971efbdef434..798afc145c54306fcf0838d8daef2bdf17763da9 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/GameRules.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/GameRules.java
|
||||
@@ -261,10 +261,10 @@ public class GameRules {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
- protected abstract void updateFromArgument(CommandContext<CommandSourceStack> context, String name);
|
||||
+ protected abstract void updateFromArgument(CommandContext<CommandSourceStack> context, String name, GameRules.Key<T> gameRuleKey); // Paper
|
||||
|
||||
- public void setFromArgument(CommandContext<CommandSourceStack> context, String name) {
|
||||
- this.updateFromArgument(context, name);
|
||||
+ public void setFromArgument(CommandContext<CommandSourceStack> context, String name, GameRules.Key<T> gameRuleKey) { // Paper
|
||||
+ this.updateFromArgument(context, name, gameRuleKey); // Paper
|
||||
this.onChanged(((CommandSourceStack) context.getSource()).getServer());
|
||||
}
|
||||
|
||||
@@ -322,8 +322,11 @@ public class GameRules {
|
||||
}
|
||||
|
||||
@Override
|
||||
- protected void updateFromArgument(CommandContext<CommandSourceStack> context, String name) {
|
||||
- this.value = BoolArgumentType.getBool(context, name);
|
||||
+ protected void updateFromArgument(CommandContext<CommandSourceStack> context, String name, GameRules.Key<BooleanValue> gameRuleKey) { // Paper start
|
||||
+ io.papermc.paper.event.world.WorldGameRuleChangeEvent event = new io.papermc.paper.event.world.WorldGameRuleChangeEvent(context.getSource().getBukkitWorld(), context.getSource().getBukkitSender(), (org.bukkit.GameRule<Boolean>) org.bukkit.GameRule.getByName(gameRuleKey.toString()), String.valueOf(BoolArgumentType.getBool(context, name)));
|
||||
+ if (!event.callEvent()) return;
|
||||
+ this.value = Boolean.parseBoolean(event.getValue());
|
||||
+ // Paper end
|
||||
}
|
||||
|
||||
public boolean get() {
|
||||
@@ -387,8 +390,11 @@ public class GameRules {
|
||||
}
|
||||
|
||||
@Override
|
||||
- protected void updateFromArgument(CommandContext<CommandSourceStack> context, String name) {
|
||||
- this.value = IntegerArgumentType.getInteger(context, name);
|
||||
+ protected void updateFromArgument(CommandContext<CommandSourceStack> context, String name, GameRules.Key<IntegerValue> gameRuleKey) { // Paper start
|
||||
+ io.papermc.paper.event.world.WorldGameRuleChangeEvent event = new io.papermc.paper.event.world.WorldGameRuleChangeEvent(context.getSource().getBukkitWorld(), context.getSource().getBukkitSender(), (org.bukkit.GameRule<Integer>) org.bukkit.GameRule.getByName(gameRuleKey.toString()), String.valueOf(IntegerArgumentType.getInteger(context, name)));
|
||||
+ if (!event.callEvent()) return;
|
||||
+ this.value = Integer.parseInt(event.getValue());
|
||||
+ // Paper end
|
||||
}
|
||||
|
||||
public int get() {
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
|
||||
index f7d5c6aa18ee44e0a6651ed73c922a973bb809b3..6777b678efebc5eee72b2aa368309aea3191157f 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/CraftWorld.java
|
||||
@@ -1798,8 +1798,13 @@ public class CraftWorld extends CraftRegionAccessor implements World {
|
||||
|
||||
if (!this.isGameRule(rule)) return false;
|
||||
|
||||
+ // Paper start
|
||||
+ GameRule<?> gameRule = GameRule.getByName(rule);
|
||||
+ io.papermc.paper.event.world.WorldGameRuleChangeEvent event = new io.papermc.paper.event.world.WorldGameRuleChangeEvent(this, null, gameRule, value);
|
||||
+ if (!event.callEvent()) return false;
|
||||
+ // Paper end
|
||||
GameRules.Value<?> handle = this.getHandle().getGameRules().getRule(CraftWorld.getGameRulesNMS().get(rule));
|
||||
- handle.deserialize(value);
|
||||
+ handle.deserialize(event.getValue()); // Paper
|
||||
handle.onChanged(this.getHandle().getServer());
|
||||
return true;
|
||||
}
|
||||
@@ -1834,8 +1839,12 @@ public class CraftWorld extends CraftRegionAccessor implements World {
|
||||
|
||||
if (!this.isGameRule(rule.getName())) return false;
|
||||
|
||||
+ // Paper start
|
||||
+ io.papermc.paper.event.world.WorldGameRuleChangeEvent event = new io.papermc.paper.event.world.WorldGameRuleChangeEvent(this, null, rule, String.valueOf(newValue));
|
||||
+ if (!event.callEvent()) return false;
|
||||
+ // Paper end
|
||||
GameRules.Value<?> handle = this.getHandle().getGameRules().getRule(CraftWorld.getGameRulesNMS().get(rule.getName()));
|
||||
- handle.deserialize(newValue.toString());
|
||||
+ handle.deserialize(event.getValue()); // Paper
|
||||
handle.onChanged(this.getHandle().getServer());
|
||||
return true;
|
||||
}
|
|
@ -1,54 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Wed, 2 Dec 2020 20:04:01 -0800
|
||||
Subject: [PATCH] Added ServerResourcesReloadedEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
index 8ebd25e66301c62ae30d53f2104f732a32939029..3eda7f5469803af5fae138b81976ecae2b7c6c2e 100644
|
||||
--- a/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
+++ b/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
@@ -2000,7 +2000,13 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
|
||||
return this.functionManager;
|
||||
}
|
||||
|
||||
+ // Paper start - add cause
|
||||
+ @Deprecated
|
||||
public CompletableFuture<Void> reloadResources(Collection<String> dataPacks) {
|
||||
+ return this.reloadResources(dataPacks, io.papermc.paper.event.server.ServerResourcesReloadedEvent.Cause.PLUGIN);
|
||||
+ }
|
||||
+ public CompletableFuture<Void> reloadResources(Collection<String> dataPacks, io.papermc.paper.event.server.ServerResourcesReloadedEvent.Cause cause) {
|
||||
+ // Paper end
|
||||
RegistryAccess.Frozen iregistrycustom_dimension = this.registryAccess();
|
||||
CompletableFuture<Void> completablefuture = CompletableFuture.supplyAsync(() -> {
|
||||
Stream<String> stream = dataPacks.stream(); // CraftBukkit - decompile error
|
||||
@@ -2026,6 +2032,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
|
||||
this.packRepository.setSelected(dataPacks);
|
||||
this.worldData.setDataPackConfig(MinecraftServer.getSelectedPacks(this.packRepository));
|
||||
this.resources.managers.updateRegistryTags(this.registryAccess());
|
||||
+ new io.papermc.paper.event.server.ServerResourcesReloadedEvent(cause).callEvent(); // Paper
|
||||
if (Thread.currentThread() != this.serverThread) return; // Paper
|
||||
//this.getPlayerList().saveAll(); // Paper - we don't need to do this
|
||||
this.getPlayerList().reloadResources();
|
||||
diff --git a/src/main/java/net/minecraft/server/commands/ReloadCommand.java b/src/main/java/net/minecraft/server/commands/ReloadCommand.java
|
||||
index c94252ba962262ed9546d48fe05fd5995b8c73b6..4517e59584213db1f355fd993b75b4b016e02634 100644
|
||||
--- a/src/main/java/net/minecraft/server/commands/ReloadCommand.java
|
||||
+++ b/src/main/java/net/minecraft/server/commands/ReloadCommand.java
|
||||
@@ -20,7 +20,7 @@ public class ReloadCommand {
|
||||
public ReloadCommand() {}
|
||||
|
||||
public static void reloadPacks(Collection<String> dataPacks, CommandSourceStack source) {
|
||||
- source.getServer().reloadResources(dataPacks).exceptionally((throwable) -> {
|
||||
+ source.getServer().reloadResources(dataPacks, io.papermc.paper.event.server.ServerResourcesReloadedEvent.Cause.COMMAND).exceptionally((throwable) -> {
|
||||
ReloadCommand.LOGGER.warn("Failed to execute reload", throwable);
|
||||
source.sendFailure(new TranslatableComponent("commands.reload.failure"));
|
||||
return null;
|
||||
@@ -50,7 +50,7 @@ public class ReloadCommand {
|
||||
WorldData savedata = minecraftserver.getWorldData();
|
||||
Collection<String> collection = resourcepackrepository.getSelectedIds();
|
||||
Collection<String> collection1 = ReloadCommand.discoverNewPacks(resourcepackrepository, savedata, collection);
|
||||
- minecraftserver.reloadResources(collection1);
|
||||
+ minecraftserver.reloadResources(collection1, io.papermc.paper.event.server.ServerResourcesReloadedEvent.Cause.PLUGIN); // Paper
|
||||
}
|
||||
// CraftBukkit end
|
||||
|
|
@ -1,51 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Sat, 28 Nov 2020 18:43:52 -0800
|
||||
Subject: [PATCH] Added world settings for mobs picking up loot
|
||||
|
||||
|
||||
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
index 5fe4d2005e87a7b69e98dcd68e0fff3cc26a8c96..f4559f3bc7751da48a84d75a949c9df298ee48b4 100644
|
||||
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
@@ -787,6 +787,14 @@ public class PaperWorldConfig {
|
||||
phantomOnlyAttackInsomniacs = getBoolean("phantoms-only-attack-insomniacs", phantomOnlyAttackInsomniacs);
|
||||
}
|
||||
|
||||
+ public boolean zombiesAlwaysCanPickUpLoot;
|
||||
+ public boolean skeletonsAlwaysCanPickUpLoot;
|
||||
+ private void setMobsAlwaysCanPickUpLoot() {
|
||||
+ zombiesAlwaysCanPickUpLoot = getBoolean("mobs-can-always-pick-up-loot.zombies", false);
|
||||
+ skeletonsAlwaysCanPickUpLoot = getBoolean("mobs-can-always-pick-up-loot.skeletons", false);
|
||||
+ log("Zombies can always pick up loot: " + zombiesAlwaysCanPickUpLoot + ". Skeletons can always pick up loot: " + skeletonsAlwaysCanPickUpLoot + ".");
|
||||
+ }
|
||||
+
|
||||
public int expMergeMaxValue;
|
||||
private void expMergeMaxValue() {
|
||||
expMergeMaxValue = getInt("experience-merge-max-value", -1);
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/monster/AbstractSkeleton.java b/src/main/java/net/minecraft/world/entity/monster/AbstractSkeleton.java
|
||||
index 609380af4de4118a543b6ec94feb176e6f6870ed..ecf12ed5014202181e78af051e4a9ca88a275794 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/monster/AbstractSkeleton.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/monster/AbstractSkeleton.java
|
||||
@@ -147,7 +147,7 @@ public abstract class AbstractSkeleton extends Monster implements RangedAttackMo
|
||||
this.populateDefaultEquipmentSlots(difficulty);
|
||||
this.populateDefaultEquipmentEnchantments(difficulty);
|
||||
this.reassessWeaponGoal();
|
||||
- this.setCanPickUpLoot(this.random.nextFloat() < 0.55F * difficulty.getSpecialMultiplier());
|
||||
+ this.setCanPickUpLoot(this.level.paperConfig.skeletonsAlwaysCanPickUpLoot || this.random.nextFloat() < 0.55F * difficulty.getSpecialMultiplier()); // Paper
|
||||
if (this.getItemBySlot(EquipmentSlot.HEAD).isEmpty()) {
|
||||
LocalDate localdate = LocalDate.now();
|
||||
int i = localdate.get(ChronoField.DAY_OF_MONTH);
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/monster/Zombie.java b/src/main/java/net/minecraft/world/entity/monster/Zombie.java
|
||||
index 5341f65436bb147c8aed5206c5e4515c7517bc2e..92145b35cf9f04afd388dfea8215097a9da7c5a7 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/monster/Zombie.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/monster/Zombie.java
|
||||
@@ -503,7 +503,7 @@ public class Zombie extends Monster {
|
||||
Object object = super.finalizeSpawn(world, difficulty, spawnReason, entityData, entityNbt);
|
||||
float f = difficulty.getSpecialMultiplier();
|
||||
|
||||
- this.setCanPickUpLoot(this.random.nextFloat() < 0.55F * f);
|
||||
+ this.setCanPickUpLoot(this.level.paperConfig.zombiesAlwaysCanPickUpLoot || this.random.nextFloat() < 0.55F * f); // Paper
|
||||
if (object == null) {
|
||||
object = new Zombie.ZombieGroupData(Zombie.getSpawnAsBabyOdds(world.getRandom()), true);
|
||||
}
|
|
@ -1,50 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: TheViperShow <29604693+TheViperShow@users.noreply.github.com>
|
||||
Date: Wed, 22 Apr 2020 09:40:38 +0200
|
||||
Subject: [PATCH] Implemented BlockFailedDispenseEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/level/block/DispenserBlock.java b/src/main/java/net/minecraft/world/level/block/DispenserBlock.java
|
||||
index 7ffbdfb1d192e70ab2259391210d73b8821e4989..07d357b5fcb30ed9ff074a196a19de1481fe3738 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/block/DispenserBlock.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/block/DispenserBlock.java
|
||||
@@ -83,8 +83,10 @@ public class DispenserBlock extends BaseEntityBlock {
|
||||
int i = tileentitydispenser.getRandomSlot();
|
||||
|
||||
if (i < 0) {
|
||||
+ if (org.bukkit.craftbukkit.event.CraftEventFactory.handleBlockFailedDispenseEvent(world, pos)) {// Paper - BlockFailedDispenseEvent is called here
|
||||
world.levelEvent(1001, pos, 0);
|
||||
world.gameEvent(GameEvent.DISPENSE_FAIL, pos);
|
||||
+ } // Paper
|
||||
} else {
|
||||
ItemStack itemstack = tileentitydispenser.getItem(i);
|
||||
DispenseItemBehavior idispensebehavior = this.getDispenseMethod(itemstack);
|
||||
diff --git a/src/main/java/net/minecraft/world/level/block/DropperBlock.java b/src/main/java/net/minecraft/world/level/block/DropperBlock.java
|
||||
index 47258da56363037fba17d92e1518955a5fd4ef3b..234dc491ca30853eefdf86229296cc89fc8d46c2 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/block/DropperBlock.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/block/DropperBlock.java
|
||||
@@ -44,6 +44,7 @@ public class DropperBlock extends DispenserBlock {
|
||||
int i = tileentitydispenser.getRandomSlot();
|
||||
|
||||
if (i < 0) {
|
||||
+ if (org.bukkit.craftbukkit.event.CraftEventFactory.handleBlockFailedDispenseEvent(world, pos)) // Paper - BlockFailedDispenseEvent is called here
|
||||
world.levelEvent(1001, pos, 0);
|
||||
} else {
|
||||
ItemStack itemstack = tileentitydispenser.getItem(i);
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
index c5fd069085efa57f99698930640198c6fcaa4bfb..ed5c598a803748bc001f8ee5ca40b8aa6fe72a3a 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
@@ -1865,4 +1865,12 @@ public class CraftEventFactory {
|
||||
EntitiesUnloadEvent event = new EntitiesUnloadEvent(new CraftChunk((ServerLevel) world, coords.x, coords.z), bukkitEntities);
|
||||
Bukkit.getPluginManager().callEvent(event);
|
||||
}
|
||||
+
|
||||
+ // Paper start
|
||||
+ public static boolean handleBlockFailedDispenseEvent(ServerLevel serverLevel, BlockPos blockposition) {
|
||||
+ org.bukkit.block.Block block = serverLevel.getWorld().getBlockAt(blockposition.getX(), blockposition.getY(), blockposition.getZ());
|
||||
+ io.papermc.paper.event.block.BlockFailedDispenseEvent event = new io.papermc.paper.event.block.BlockFailedDispenseEvent(block);
|
||||
+ return event.callEvent();
|
||||
+ }
|
||||
+ // Paper end
|
||||
}
|
|
@ -1,46 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Mon, 23 Nov 2020 12:58:51 -0800
|
||||
Subject: [PATCH] Added PlayerLecternPageChangeEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/inventory/LecternMenu.java b/src/main/java/net/minecraft/world/inventory/LecternMenu.java
|
||||
index 0149b958a3bdeb529a8b7e64f4ca458d0be88998..ff79925bc6437222f9ceb133e21bbc0600cc74ed 100644
|
||||
--- a/src/main/java/net/minecraft/world/inventory/LecternMenu.java
|
||||
+++ b/src/main/java/net/minecraft/world/inventory/LecternMenu.java
|
||||
@@ -64,6 +64,7 @@ public class LecternMenu extends AbstractContainerMenu {
|
||||
@Override
|
||||
public boolean clickMenuButton(net.minecraft.world.entity.player.Player player, int id) {
|
||||
int j;
|
||||
+ io.papermc.paper.event.player.PlayerLecternPageChangeEvent playerLecternPageChangeEvent; CraftInventoryLectern bukkitView; // Paper
|
||||
|
||||
if (id >= 100) {
|
||||
j = id - 100;
|
||||
@@ -73,11 +74,25 @@ public class LecternMenu extends AbstractContainerMenu {
|
||||
switch (id) {
|
||||
case 1:
|
||||
j = this.lecternData.get(0);
|
||||
- this.setData(0, j - 1);
|
||||
+ // Paper start
|
||||
+ bukkitView = (CraftInventoryLectern) getBukkitView().getTopInventory();
|
||||
+ playerLecternPageChangeEvent = new io.papermc.paper.event.player.PlayerLecternPageChangeEvent((org.bukkit.entity.Player) player.getBukkitEntity(), bukkitView.getHolder(), bukkitView.getBook(), io.papermc.paper.event.player.PlayerLecternPageChangeEvent.PageChangeDirection.LEFT, j, j - 1);
|
||||
+ if (!playerLecternPageChangeEvent.callEvent()) {
|
||||
+ return false;
|
||||
+ }
|
||||
+ this.setData(0, playerLecternPageChangeEvent.getNewPage());
|
||||
+ // Paper end
|
||||
return true;
|
||||
case 2:
|
||||
j = this.lecternData.get(0);
|
||||
- this.setData(0, j + 1);
|
||||
+ // Paper start
|
||||
+ bukkitView = (CraftInventoryLectern) getBukkitView().getTopInventory();
|
||||
+ playerLecternPageChangeEvent = new io.papermc.paper.event.player.PlayerLecternPageChangeEvent((org.bukkit.entity.Player) player.getBukkitEntity(), bukkitView.getHolder(), bukkitView.getBook(), io.papermc.paper.event.player.PlayerLecternPageChangeEvent.PageChangeDirection.RIGHT, j, j + 1);
|
||||
+ if (!playerLecternPageChangeEvent.callEvent()) {
|
||||
+ return false;
|
||||
+ }
|
||||
+ this.setData(0, playerLecternPageChangeEvent.getNewPage());
|
||||
+ // Paper end
|
||||
return true;
|
||||
case 3:
|
||||
if (!player.mayBuild()) {
|
|
@ -1,34 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Wed, 25 Nov 2020 16:33:27 -0800
|
||||
Subject: [PATCH] Added PlayerLoomPatternSelectEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/inventory/LoomMenu.java b/src/main/java/net/minecraft/world/inventory/LoomMenu.java
|
||||
index fba8c59071847d9669943534ff8a0898b5787c28..1fefb682d34ab165444c45439dbc1ea28dc9079f 100644
|
||||
--- a/src/main/java/net/minecraft/world/inventory/LoomMenu.java
|
||||
+++ b/src/main/java/net/minecraft/world/inventory/LoomMenu.java
|
||||
@@ -168,7 +168,22 @@ public class LoomMenu extends AbstractContainerMenu {
|
||||
@Override
|
||||
public boolean clickMenuButton(net.minecraft.world.entity.player.Player player, int id) {
|
||||
if (id > 0 && id <= BannerPattern.AVAILABLE_PATTERNS) {
|
||||
- this.selectedBannerPatternIndex.set(id);
|
||||
+ // Paper start
|
||||
+ int enumBannerPatternTypeOrdinal = id;
|
||||
+ io.papermc.paper.event.player.PlayerLoomPatternSelectEvent event = new io.papermc.paper.event.player.PlayerLoomPatternSelectEvent((Player) player.getBukkitEntity(), ((CraftInventoryLoom) getBukkitView().getTopInventory()), org.bukkit.block.banner.PatternType.getByIdentifier(BannerPattern.values()[id].getHashname()));
|
||||
+ if (!event.callEvent()) {
|
||||
+ ((Player) player.getBukkitEntity()).updateInventory();
|
||||
+ return false;
|
||||
+ }
|
||||
+ for (BannerPattern nms : BannerPattern.values()) {
|
||||
+ if (event.getPatternType().getIdentifier().equals(nms.getHashname())) {
|
||||
+ enumBannerPatternTypeOrdinal = nms.ordinal();
|
||||
+ break;
|
||||
+ }
|
||||
+ }
|
||||
+ ((Player) player.getBukkitEntity()).updateInventory();
|
||||
+ this.selectedBannerPatternIndex.set(enumBannerPatternTypeOrdinal);
|
||||
+ // Paper end
|
||||
this.setupResultSlot();
|
||||
return true;
|
||||
} else {
|
|
@ -1,65 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Sun, 3 Jan 2021 22:27:43 -0800
|
||||
Subject: [PATCH] Configurable door breaking difficulty
|
||||
|
||||
Co-authored-by: Doc <nachito94@msn.com>
|
||||
|
||||
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
index f4559f3bc7751da48a84d75a949c9df298ee48b4..96fd9803810db0f8a4b25e070a56da05862e1e4e 100644
|
||||
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
@@ -142,6 +142,27 @@ public class PaperWorldConfig {
|
||||
private void disableMobSpawnerSpawnEggTransformation() {
|
||||
disableMobSpawnerSpawnEggTransformation = getBoolean("game-mechanics.disable-mob-spawner-spawn-egg-transformation", disableMobSpawnerSpawnEggTransformation);
|
||||
}
|
||||
+
|
||||
+ private final List<net.minecraft.world.entity.EntityType<?>> entitiesValidForBreakDoors = Arrays.asList(net.minecraft.world.entity.EntityType.ZOMBIE, net.minecraft.world.entity.EntityType.ZOMBIE_VILLAGER, net.minecraft.world.entity.EntityType.HUSK, net.minecraft.world.entity.EntityType.ZOMBIFIED_PIGLIN, net.minecraft.world.entity.EntityType.VINDICATOR);
|
||||
+ public java.util.Map<net.minecraft.world.entity.EntityType<?>, java.util.List<net.minecraft.world.Difficulty>> entitiesDifficultyBreakDoors = new it.unimi.dsi.fastutil.objects.Reference2ObjectOpenHashMap<>();
|
||||
+ private void setupEntityBreakingDoors() {
|
||||
+ for (net.minecraft.world.entity.EntityType<?> entityType : entitiesValidForBreakDoors) {
|
||||
+ java.util.function.Predicate<net.minecraft.world.Difficulty> difficultyPredicate = net.minecraft.world.entity.monster.Zombie.DOOR_BREAKING_PREDICATE;
|
||||
+ if (entityType == net.minecraft.world.entity.EntityType.VINDICATOR) {
|
||||
+ difficultyPredicate = net.minecraft.world.entity.monster.Vindicator.DOOR_BREAKING_PREDICATE;
|
||||
+ }
|
||||
+ entitiesDifficultyBreakDoors.put(
|
||||
+ entityType,
|
||||
+ getEnumList(
|
||||
+ "door-breaking-difficulty." + entityType.id,
|
||||
+ java.util.Arrays.stream(net.minecraft.world.Difficulty.values())
|
||||
+ .filter(difficultyPredicate)
|
||||
+ .collect(Collectors.toList()),
|
||||
+ net.minecraft.world.Difficulty.class
|
||||
+ )
|
||||
+ );
|
||||
+ }
|
||||
+ }
|
||||
|
||||
public short keepLoadedRange;
|
||||
private void keepLoadedRange() {
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/monster/Vindicator.java b/src/main/java/net/minecraft/world/entity/monster/Vindicator.java
|
||||
index 920c2101ebbdc07c7fd15903a3d641aa55f8336d..430492facbaa80471875da07bf4b9b601777d1fd 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/monster/Vindicator.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/monster/Vindicator.java
|
||||
@@ -192,7 +192,7 @@ public class Vindicator extends AbstractIllager {
|
||||
private static class VindicatorBreakDoorGoal extends BreakDoorGoal {
|
||||
|
||||
public VindicatorBreakDoorGoal(Mob mob) {
|
||||
- super(mob, 6, Vindicator.DOOR_BREAKING_PREDICATE);
|
||||
+ super(mob, 6, com.google.common.base.Predicates.in(mob.level.paperConfig.entitiesDifficultyBreakDoors.getOrDefault(mob.getType(), mob.level.paperConfig.entitiesDifficultyBreakDoors.get(EntityType.VINDICATOR)))); // Paper
|
||||
this.setFlags(EnumSet.of(Goal.Flag.MOVE));
|
||||
}
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/monster/Zombie.java b/src/main/java/net/minecraft/world/entity/monster/Zombie.java
|
||||
index 92145b35cf9f04afd388dfea8215097a9da7c5a7..f9b7877ce5f66cc58ff1111d0fa72081a03c4f4e 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/monster/Zombie.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/monster/Zombie.java
|
||||
@@ -97,7 +97,7 @@ public class Zombie extends Monster {
|
||||
|
||||
public Zombie(EntityType<? extends Zombie> type, Level world) {
|
||||
super(type, world);
|
||||
- this.breakDoorGoal = new BreakDoorGoal(this, Zombie.DOOR_BREAKING_PREDICATE);
|
||||
+ this.breakDoorGoal = new BreakDoorGoal(this, com.google.common.base.Predicates.in(world.paperConfig.entitiesDifficultyBreakDoors.getOrDefault(type, world.paperConfig.entitiesDifficultyBreakDoors.get(EntityType.ZOMBIE)))); // Paper
|
||||
}
|
||||
|
||||
public Zombie(Level world) {
|
|
@ -1,18 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Mariell Hoversholm <proximyst@proximyst.com>
|
||||
Date: Wed, 6 Jan 2021 23:38:43 +0100
|
||||
Subject: [PATCH] Empty commands shall not be dispatched
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/commands/Commands.java b/src/main/java/net/minecraft/commands/Commands.java
|
||||
index 4bc28b66788d06d1446284f5adef6a44be736f92..e195ef979984ea7ffe4558c42ebabadf2a00950a 100644
|
||||
--- a/src/main/java/net/minecraft/commands/Commands.java
|
||||
+++ b/src/main/java/net/minecraft/commands/Commands.java
|
||||
@@ -241,6 +241,7 @@ public class Commands {
|
||||
command = event.getCommand();
|
||||
|
||||
String[] args = command.split(" ");
|
||||
+ if (args.length == 0) return 0; // Paper - empty commands shall not be dispatched
|
||||
|
||||
String cmd = args[0];
|
||||
if (cmd.startsWith("minecraft:")) cmd = cmd.substring("minecraft:".length());
|
|
@ -1,59 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Madeline Miller <mnmiller1@me.com>
|
||||
Date: Mon, 4 Jan 2021 16:40:27 +1000
|
||||
Subject: [PATCH] Implement API to expose exact interaction point
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/level/ServerPlayerGameMode.java b/src/main/java/net/minecraft/server/level/ServerPlayerGameMode.java
|
||||
index d006964cb6c4c3cd843064ab685700c67df8c238..f97d97426144527cff9ebb91b26fe8541a9c6d9b 100644
|
||||
--- a/src/main/java/net/minecraft/server/level/ServerPlayerGameMode.java
|
||||
+++ b/src/main/java/net/minecraft/server/level/ServerPlayerGameMode.java
|
||||
@@ -511,7 +511,7 @@ public class ServerPlayerGameMode {
|
||||
cancelledBlock = true;
|
||||
}
|
||||
|
||||
- PlayerInteractEvent event = CraftEventFactory.callPlayerInteractEvent(player, Action.RIGHT_CLICK_BLOCK, blockposition, hitResult.getDirection(), stack, cancelledBlock, hand);
|
||||
+ PlayerInteractEvent event = CraftEventFactory.callPlayerInteractEvent(player, Action.RIGHT_CLICK_BLOCK, blockposition, hitResult.getDirection(), stack, cancelledBlock, hand, hitResult.getLocation()); // Paper
|
||||
this.firedInteract = true;
|
||||
this.interactResult = event.useItemInHand() == Event.Result.DENY;
|
||||
this.interactPosition = blockposition.immutable();
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
index ed5c598a803748bc001f8ee5ca40b8aa6fe72a3a..dbc777a7d872116da0f60953fc6a650df17d9f5c 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
@@ -56,7 +56,9 @@ import net.minecraft.world.level.storage.loot.parameters.LootContextParams;
|
||||
import net.minecraft.world.phys.BlockHitResult;
|
||||
import net.minecraft.world.phys.EntityHitResult;
|
||||
import net.minecraft.world.phys.HitResult;
|
||||
+import net.minecraft.world.phys.Vec3;
|
||||
import org.bukkit.Bukkit;
|
||||
+import org.bukkit.Location; // Paper
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.NamespacedKey;
|
||||
import org.bukkit.Server;
|
||||
@@ -483,7 +485,13 @@ public class CraftEventFactory {
|
||||
return CraftEventFactory.callPlayerInteractEvent(who, action, position, direction, itemstack, false, hand);
|
||||
}
|
||||
|
||||
+ // Paper start - Add interactionPoint
|
||||
public static PlayerInteractEvent callPlayerInteractEvent(net.minecraft.world.entity.player.Player who, Action action, BlockPos position, Direction direction, ItemStack itemstack, boolean cancelledBlock, InteractionHand hand) {
|
||||
+ return callPlayerInteractEvent(who, action, position, direction, itemstack, cancelledBlock, hand, null);
|
||||
+ }
|
||||
+
|
||||
+ public static PlayerInteractEvent callPlayerInteractEvent(net.minecraft.world.entity.player.Player who, Action action, BlockPos position, Direction direction, ItemStack itemstack, boolean cancelledBlock, InteractionHand hand, Vec3 hitVec) {
|
||||
+ // Paper end
|
||||
Player player = (who == null) ? null : (Player) who.getBukkitEntity();
|
||||
CraftItemStack itemInHand = CraftItemStack.asCraftMirror(itemstack);
|
||||
|
||||
@@ -509,7 +517,10 @@ public class CraftEventFactory {
|
||||
itemInHand = null;
|
||||
}
|
||||
|
||||
- PlayerInteractEvent event = new PlayerInteractEvent(player, action, itemInHand, blockClicked, blockFace, (hand == null) ? null : ((hand == InteractionHand.OFF_HAND) ? EquipmentSlot.OFF_HAND : EquipmentSlot.HAND));
|
||||
+ // Paper start
|
||||
+ Location interactionPoint = hitVec == null ? null : new Location(craftWorld, hitVec.x, hitVec.y, hitVec.z);
|
||||
+ PlayerInteractEvent event = new PlayerInteractEvent(player, action, itemInHand, blockClicked, blockFace, (hand == null) ? null : ((hand == InteractionHand.OFF_HAND) ? EquipmentSlot.OFF_HAND : EquipmentSlot.HAND), interactionPoint);
|
||||
+ // Paper end
|
||||
if (cancelledBlock) {
|
||||
event.setUseInteractedBlock(Event.Result.DENY);
|
||||
}
|
|
@ -1,22 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Shane Freeder <theboyetronic@gmail.com>
|
||||
Date: Sat, 9 Jan 2021 14:17:07 +0100
|
||||
Subject: [PATCH] Remove stale POIs
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/level/ServerLevel.java b/src/main/java/net/minecraft/server/level/ServerLevel.java
|
||||
index 053ca558c7db0b0a7c2b768e3827e0b90094fc5b..5f9376afffa369ea2480fafdda5e9fadf46f236e 100644
|
||||
--- a/src/main/java/net/minecraft/server/level/ServerLevel.java
|
||||
+++ b/src/main/java/net/minecraft/server/level/ServerLevel.java
|
||||
@@ -1834,6 +1834,11 @@ public class ServerLevel extends Level implements WorldGenLevel {
|
||||
});
|
||||
optional1.ifPresent((villageplacetype) -> {
|
||||
this.getServer().execute(() -> {
|
||||
+ // Paper start
|
||||
+ if (optional.isEmpty() && this.getPoiManager().exists(blockposition1, poiType -> true)) {
|
||||
+ this.getPoiManager().remove(blockposition1);
|
||||
+ }
|
||||
+ // Paper end
|
||||
this.getPoiManager().add(blockposition1, villageplacetype);
|
||||
DebugPackets.sendPoiAddedPacket(this, blockposition1);
|
||||
});
|
|
@ -1,25 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jason Penilla <11360596+jpenilla@users.noreply.github.com>
|
||||
Date: Mon, 11 Jan 2021 12:43:51 -0800
|
||||
Subject: [PATCH] Fix villager boat exploit
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/players/PlayerList.java b/src/main/java/net/minecraft/server/players/PlayerList.java
|
||||
index 8d5154cad319d7762db696cd9cd2bf8ab69f632e..65335a8dc42366c5318d583097b24443dc3c9616 100644
|
||||
--- a/src/main/java/net/minecraft/server/players/PlayerList.java
|
||||
+++ b/src/main/java/net/minecraft/server/players/PlayerList.java
|
||||
@@ -625,6 +625,14 @@ public abstract class PlayerList {
|
||||
PlayerList.LOGGER.debug("Removing player mount");
|
||||
entityplayer.stopRiding();
|
||||
entity.getPassengersAndSelf().forEach((entity1) -> {
|
||||
+ // Paper start
|
||||
+ if (entity1 instanceof net.minecraft.world.entity.npc.AbstractVillager villager) {
|
||||
+ final net.minecraft.world.entity.player.Player human = villager.getTradingPlayer();
|
||||
+ if (human != null) {
|
||||
+ villager.setTradingPlayer(null);
|
||||
+ }
|
||||
+ }
|
||||
+ // Paper end
|
||||
entity1.setRemoved(Entity.RemovalReason.UNLOADED_WITH_PLAYER);
|
||||
});
|
||||
}
|
|
@ -1,51 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Mariell Hoversholm <proximyst@proximyst.com>
|
||||
Date: Tue, 29 Dec 2020 15:03:03 +0100
|
||||
Subject: [PATCH] Add sendOpLevel API
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/players/PlayerList.java b/src/main/java/net/minecraft/server/players/PlayerList.java
|
||||
index 65335a8dc42366c5318d583097b24443dc3c9616..71b6f3990ace47ac752ec825c78d7fa964011898 100644
|
||||
--- a/src/main/java/net/minecraft/server/players/PlayerList.java
|
||||
+++ b/src/main/java/net/minecraft/server/players/PlayerList.java
|
||||
@@ -1123,6 +1123,11 @@ public abstract class PlayerList {
|
||||
}
|
||||
|
||||
private void sendPlayerPermissionLevel(ServerPlayer player, int permissionLevel) {
|
||||
+ // Paper start - add recalculatePermissions parameter
|
||||
+ this.sendPlayerPermissionLevel(player, permissionLevel, true);
|
||||
+ }
|
||||
+ public void sendPlayerPermissionLevel(ServerPlayer player, int permissionLevel, boolean recalculatePermissions) {
|
||||
+ // Paper end
|
||||
if (player.connection != null) {
|
||||
byte b0;
|
||||
|
||||
@@ -1137,8 +1142,10 @@ public abstract class PlayerList {
|
||||
player.connection.send(new ClientboundEntityEventPacket(player, b0));
|
||||
}
|
||||
|
||||
+ if (recalculatePermissions) { // Paper
|
||||
player.getBukkitEntity().recalculatePermissions(); // CraftBukkit
|
||||
this.server.getCommands().sendCommands(player);
|
||||
+ } // Paper
|
||||
}
|
||||
|
||||
// Paper start
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java
|
||||
index a55dc36244c7a60300c988504d214eef546dfa36..047411e24a53c2e625c05b7079406060024e5dc9 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftPlayer.java
|
||||
@@ -609,6 +609,13 @@ public class CraftPlayer extends CraftHumanEntity implements Player {
|
||||
? (org.bukkit.entity.Firework) entity.getBukkitEntity()
|
||||
: null;
|
||||
}
|
||||
+
|
||||
+ @Override
|
||||
+ public void sendOpLevel(byte level) {
|
||||
+ Preconditions.checkArgument(level >= 0 && level <= 4, "Level must be within [0, 4]");
|
||||
+
|
||||
+ this.getHandle().getServer().getPlayerList().sendPlayerPermissionLevel(this.getHandle(), level, false);
|
||||
+ }
|
||||
// Paper end
|
||||
|
||||
@Override
|
|
@ -1,222 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Wed, 2 Mar 2022 13:33:08 -0800
|
||||
Subject: [PATCH] Add PaperRegistry
|
||||
|
||||
PaperRegistry is a server-backed impl of bukkit's Registry interface
|
||||
|
||||
diff --git a/src/main/java/io/papermc/paper/registry/PaperRegistry.java b/src/main/java/io/papermc/paper/registry/PaperRegistry.java
|
||||
new file mode 100644
|
||||
index 0000000000000000000000000000000000000000..8d1f3c4891870b4239df678dd1e52e9f4ef74b2c
|
||||
--- /dev/null
|
||||
+++ b/src/main/java/io/papermc/paper/registry/PaperRegistry.java
|
||||
@@ -0,0 +1,147 @@
|
||||
+package io.papermc.paper.registry;
|
||||
+
|
||||
+import com.google.common.base.Preconditions;
|
||||
+import com.google.common.base.Suppliers;
|
||||
+import net.minecraft.core.Holder;
|
||||
+import net.minecraft.core.Registry;
|
||||
+import net.minecraft.core.RegistryAccess;
|
||||
+import net.minecraft.resources.ResourceKey;
|
||||
+import net.minecraft.resources.ResourceLocation;
|
||||
+import net.minecraft.server.MinecraftServer;
|
||||
+import org.bukkit.Keyed;
|
||||
+import org.bukkit.NamespacedKey;
|
||||
+import org.bukkit.craftbukkit.util.CraftNamespacedKey;
|
||||
+import org.checkerframework.checker.nullness.qual.NonNull;
|
||||
+import org.checkerframework.checker.nullness.qual.Nullable;
|
||||
+import org.checkerframework.framework.qual.DefaultQualifier;
|
||||
+
|
||||
+import java.util.Collections;
|
||||
+import java.util.HashMap;
|
||||
+import java.util.Iterator;
|
||||
+import java.util.Map;
|
||||
+import java.util.Objects;
|
||||
+import java.util.Optional;
|
||||
+import java.util.concurrent.ConcurrentHashMap;
|
||||
+import java.util.function.Supplier;
|
||||
+
|
||||
+@DefaultQualifier(NonNull.class)
|
||||
+public abstract class PaperRegistry<API extends Keyed, MINECRAFT> implements org.bukkit.Registry<API> {
|
||||
+
|
||||
+ @SuppressWarnings("FieldMayBeFinal") // non-final for testing
|
||||
+ private static Supplier<RegistryAccess> REGISTRY_ACCESS = Suppliers.memoize(() -> MinecraftServer.getServer().registryAccess());
|
||||
+ private static final Map<RegistryKey<?, ?>, PaperRegistry<?, ?>> INTERNAL_REGISTRIES = new HashMap<>();
|
||||
+ public static final Map<RegistryKey<?, ?>, PaperRegistry<?, ?>> REGISTRIES = Collections.unmodifiableMap(INTERNAL_REGISTRIES);
|
||||
+ private static final Map<Class<?>, PaperRegistry<?, ?>> REGISTRY_BY_API_CLASS = new HashMap<>();
|
||||
+ private static final Map<ResourceKey<? extends Registry<?>>, PaperRegistry<?, ?>> REGISTRY_BY_RES_KEY = new HashMap<>();
|
||||
+
|
||||
+ private boolean registered;
|
||||
+ private final RegistryKey<API, MINECRAFT> registryKey;
|
||||
+ private final Supplier<Registry<MINECRAFT>> registry;
|
||||
+ private final Map<NamespacedKey, API> cache = new ConcurrentHashMap<>();
|
||||
+ private final Map<NamespacedKey, ResourceKey<MINECRAFT>> resourceKeyCache = new ConcurrentHashMap<>();
|
||||
+
|
||||
+ public PaperRegistry(RegistryKey<API, MINECRAFT> registryKey) {
|
||||
+ this.registryKey = registryKey;
|
||||
+ this.registry = Suppliers.memoize(() -> REGISTRY_ACCESS.get().registryOrThrow(this.registryKey.resourceKey()));
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public @Nullable API get(NamespacedKey key) {
|
||||
+ return this.cache.computeIfAbsent(key, k -> {
|
||||
+ final @Nullable MINECRAFT nms = this.registry.get().get(CraftNamespacedKey.toMinecraft(k));
|
||||
+ if (nms != null) {
|
||||
+ return this.convertToApi(k, nms);
|
||||
+ }
|
||||
+ return null;
|
||||
+ });
|
||||
+ }
|
||||
+
|
||||
+ public abstract API convertToApi(NamespacedKey key, MINECRAFT nms);
|
||||
+
|
||||
+ public API convertToApi(ResourceLocation resourceLocation, MINECRAFT nms) {
|
||||
+ return this.convertToApi(CraftNamespacedKey.fromMinecraft(resourceLocation), nms);
|
||||
+ }
|
||||
+
|
||||
+ public API convertToApi(Holder<MINECRAFT> nmsHolder) {
|
||||
+ final Optional<ResourceKey<MINECRAFT>> key = nmsHolder.unwrapKey();
|
||||
+ if (nmsHolder.isBound() && key.isPresent()) {
|
||||
+ return this.convertToApi(key.get().location(), nmsHolder.value());
|
||||
+ } else if (!nmsHolder.isBound() && key.isPresent()) {
|
||||
+ return this.convertToApi(key.get().location(), this.registry.get().getOrThrow(key.get()));
|
||||
+ } else if (nmsHolder.isBound() && key.isEmpty()) {
|
||||
+ final @Nullable ResourceLocation loc = this.registry.get().getKey(nmsHolder.value());
|
||||
+ if (loc != null) {
|
||||
+ return this.convertToApi(loc, nmsHolder.value());
|
||||
+ }
|
||||
+ }
|
||||
+ throw new IllegalStateException("Cannot convert " + nmsHolder + " to an API type in: " + this.registryKey);
|
||||
+ }
|
||||
+
|
||||
+ public MINECRAFT getMinecraftValue(API apiValue) {
|
||||
+ return this.registry.get().getOptional(CraftNamespacedKey.toMinecraft(apiValue.getKey())).orElseThrow();
|
||||
+ }
|
||||
+
|
||||
+ public Holder<MINECRAFT> getMinecraftHolder(API apiValue) {
|
||||
+ return this.registry.get().getHolderOrThrow(this.resourceKeyCache.computeIfAbsent(apiValue.getKey(), key -> ResourceKey.create(this.registryKey.resourceKey(), CraftNamespacedKey.toMinecraft(key))));
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public Iterator<API> iterator() {
|
||||
+ return this.registry.get().keySet().stream().map(key -> this.get(CraftNamespacedKey.fromMinecraft(key))).iterator();
|
||||
+ }
|
||||
+
|
||||
+ public void clearCache() {
|
||||
+ this.cache.clear();
|
||||
+ }
|
||||
+
|
||||
+ public void register() {
|
||||
+ if (this.registered) {
|
||||
+ throw new IllegalStateException("Already registered: " + this.registryKey.apiClass());
|
||||
+ }
|
||||
+ INTERNAL_REGISTRIES.put(this.registryKey, this);
|
||||
+ REGISTRY_BY_API_CLASS.put(this.registryKey.apiClass(), this);
|
||||
+ REGISTRY_BY_RES_KEY.put(this.registryKey.resourceKey(), this);
|
||||
+ this.registered = true;
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public boolean equals(@Nullable Object o) {
|
||||
+ if (this == o) return true;
|
||||
+ if (o == null || !PaperRegistry.class.isAssignableFrom(o.getClass())) return false;
|
||||
+ PaperRegistry<?, ?> that = (PaperRegistry<?, ?>) o;
|
||||
+ return this.registryKey.equals(that.registryKey);
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public int hashCode() {
|
||||
+ return Objects.hash(this.registryKey);
|
||||
+ }
|
||||
+
|
||||
+ protected static <T> Supplier<Registry<T>> registryFor(ResourceKey<? extends Registry<T>> registryKey) {
|
||||
+ return Suppliers.memoize(() -> REGISTRY_ACCESS.get().registryOrThrow(registryKey));
|
||||
+ }
|
||||
+
|
||||
+ public static void clearCaches() {
|
||||
+ for (PaperRegistry<?, ?> registry : INTERNAL_REGISTRIES.values()) {
|
||||
+ registry.clearCache();
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ @SuppressWarnings("unchecked")
|
||||
+ public static <T extends Keyed> PaperRegistry<T, ?> getRegistry(Class<T> classOfT) {
|
||||
+ Preconditions.checkArgument(REGISTRY_BY_API_CLASS.containsKey(classOfT), "No registry for that type");
|
||||
+ return (PaperRegistry<T, ?>) REGISTRY_BY_API_CLASS.get(classOfT);
|
||||
+ }
|
||||
+
|
||||
+ @SuppressWarnings("unchecked")
|
||||
+ public static <T> PaperRegistry<?, T> getRegistry(ResourceKey<? extends Registry<T>> resourceKey) {
|
||||
+ Preconditions.checkArgument(REGISTRY_BY_RES_KEY.containsKey(resourceKey));
|
||||
+ return (PaperRegistry<?, T>) REGISTRY_BY_RES_KEY.get(resourceKey);
|
||||
+ }
|
||||
+
|
||||
+ @SuppressWarnings("unchecked")
|
||||
+ public static <A extends Keyed, M> PaperRegistry<A, M> getRegistry(RegistryKey<A, M> registryKey) {
|
||||
+ Preconditions.checkArgument(INTERNAL_REGISTRIES.containsKey(registryKey));
|
||||
+ return (PaperRegistry<A, M>) INTERNAL_REGISTRIES.get(registryKey);
|
||||
+ }
|
||||
+}
|
||||
diff --git a/src/main/java/io/papermc/paper/registry/RegistryKey.java b/src/main/java/io/papermc/paper/registry/RegistryKey.java
|
||||
new file mode 100644
|
||||
index 0000000000000000000000000000000000000000..6f39e343147803e15e7681c993b8797a629702e7
|
||||
--- /dev/null
|
||||
+++ b/src/main/java/io/papermc/paper/registry/RegistryKey.java
|
||||
@@ -0,0 +1,8 @@
|
||||
+package io.papermc.paper.registry;
|
||||
+
|
||||
+import net.minecraft.core.Registry;
|
||||
+import net.minecraft.resources.ResourceKey;
|
||||
+import org.bukkit.Keyed;
|
||||
+
|
||||
+public record RegistryKey<API extends Keyed, MINECRAFT>(Class<API> apiClass, ResourceKey<? extends Registry<MINECRAFT>> resourceKey) {
|
||||
+}
|
||||
diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
index 3eda7f5469803af5fae138b81976ecae2b7c6c2e..9941456a019a34384f892c44df3c73f9416bd560 100644
|
||||
--- a/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
+++ b/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
@@ -2032,6 +2032,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
|
||||
this.packRepository.setSelected(dataPacks);
|
||||
this.worldData.setDataPackConfig(MinecraftServer.getSelectedPacks(this.packRepository));
|
||||
this.resources.managers.updateRegistryTags(this.registryAccess());
|
||||
+ io.papermc.paper.PaperRegistry.clearCaches(); // Paper
|
||||
new io.papermc.paper.event.server.ServerResourcesReloadedEvent(cause).callEvent(); // Paper
|
||||
if (Thread.currentThread() != this.serverThread) return; // Paper
|
||||
//this.getPlayerList().saveAll(); // Paper - we don't need to do this
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/util/CraftMagicNumbers.java b/src/main/java/org/bukkit/craftbukkit/util/CraftMagicNumbers.java
|
||||
index 5540c5a881a9d34a8c50d6b6f0694303c76aa610..9af0bd83c03a7e9fba04f7b9f0c66029a7f4b65a 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/util/CraftMagicNumbers.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/util/CraftMagicNumbers.java
|
||||
@@ -512,6 +512,11 @@ public final class CraftMagicNumbers implements UnsafeValues {
|
||||
public int nextEntityId() {
|
||||
return net.minecraft.world.entity.Entity.nextEntityId();
|
||||
}
|
||||
+
|
||||
+ @Override
|
||||
+ public <T extends org.bukkit.Keyed> Registry<T> registryFor(Class<T> classOfT) {
|
||||
+ return io.papermc.paper.registry.PaperRegistry.getRegistry(classOfT);
|
||||
+ }
|
||||
// Paper end
|
||||
|
||||
/**
|
||||
diff --git a/src/test/java/org/bukkit/support/AbstractTestingBase.java b/src/test/java/org/bukkit/support/AbstractTestingBase.java
|
||||
index d6b6b7a3d2949126520e8256563afeb2b43bf12c..37934f0da922d696373e7a3a8cf976fcb9015271 100644
|
||||
--- a/src/test/java/org/bukkit/support/AbstractTestingBase.java
|
||||
+++ b/src/test/java/org/bukkit/support/AbstractTestingBase.java
|
||||
@@ -38,6 +38,15 @@ public abstract class AbstractTestingBase {
|
||||
MultiPackResourceManager resourceManager = new MultiPackResourceManager(PackType.SERVER_DATA, Collections.singletonList(new VanillaPackResources(ServerPacksSource.BUILT_IN_METADATA, "minecraft")));
|
||||
// add tags and loot tables for unit tests
|
||||
RegistryAccess.Frozen registry = RegistryAccess.builtinCopy().freeze();
|
||||
+ // Paper start
|
||||
+ try {
|
||||
+ java.lang.reflect.Field field = io.papermc.paper.registry.PaperRegistry.class.getDeclaredField("REGISTRY_ACCESS");
|
||||
+ field.trySetAccessible();
|
||||
+ field.set(null, com.google.common.base.Suppliers.ofInstance(registry));
|
||||
+ } catch (ReflectiveOperationException ex) {
|
||||
+ throw new IllegalStateException("Could not reflectively set RegistryAccess in PaperRegistry", ex);
|
||||
+ }
|
||||
+ // Paper end
|
||||
// Register vanilla pack
|
||||
DATA_PACK = ReloadableServerResources.loadResources(resourceManager, registry, Commands.CommandSelection.DEDICATED, 0, MoreExecutors.directExecutor(), MoreExecutors.directExecutor()).join();
|
||||
// Bind tags
|
|
@ -1,224 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: dfsek <dfsek@protonmail.com>
|
||||
Date: Wed, 16 Sep 2020 01:12:29 -0700
|
||||
Subject: [PATCH] Add StructuresLocateEvent
|
||||
|
||||
Co-authored-by: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
|
||||
diff --git a/src/main/java/io/papermc/paper/registry/RegistryKey.java b/src/main/java/io/papermc/paper/registry/RegistryKey.java
|
||||
index 6f39e343147803e15e7681c993b8797a629702e7..cbff75f19e54b37c762b209b04f6d4799152cf5b 100644
|
||||
--- a/src/main/java/io/papermc/paper/registry/RegistryKey.java
|
||||
+++ b/src/main/java/io/papermc/paper/registry/RegistryKey.java
|
||||
@@ -1,8 +1,13 @@
|
||||
package io.papermc.paper.registry;
|
||||
|
||||
+import io.papermc.paper.world.structure.ConfiguredStructure;
|
||||
import net.minecraft.core.Registry;
|
||||
import net.minecraft.resources.ResourceKey;
|
||||
+import net.minecraft.world.level.levelgen.feature.ConfiguredStructureFeature;
|
||||
import org.bukkit.Keyed;
|
||||
|
||||
public record RegistryKey<API extends Keyed, MINECRAFT>(Class<API> apiClass, ResourceKey<? extends Registry<MINECRAFT>> resourceKey) {
|
||||
+
|
||||
+ public static final RegistryKey<ConfiguredStructure, ConfiguredStructureFeature<?, ?>> CONFIGURED_STRUCTURE_REGISTRY = new RegistryKey<>(ConfiguredStructure.class, Registry.CONFIGURED_STRUCTURE_FEATURE_REGISTRY);
|
||||
+
|
||||
}
|
||||
diff --git a/src/main/java/io/papermc/paper/world/structure/PaperConfiguredStructure.java b/src/main/java/io/papermc/paper/world/structure/PaperConfiguredStructure.java
|
||||
new file mode 100644
|
||||
index 0000000000000000000000000000000000000000..41f6c2e1e60fc32e6393097711412ca2ad643e57
|
||||
--- /dev/null
|
||||
+++ b/src/main/java/io/papermc/paper/world/structure/PaperConfiguredStructure.java
|
||||
@@ -0,0 +1,42 @@
|
||||
+package io.papermc.paper.world.structure;
|
||||
+
|
||||
+import io.papermc.paper.registry.PaperRegistry;
|
||||
+import io.papermc.paper.registry.RegistryKey;
|
||||
+import net.minecraft.core.Registry;
|
||||
+import net.minecraft.resources.ResourceLocation;
|
||||
+import net.minecraft.world.level.levelgen.feature.ConfiguredStructureFeature;
|
||||
+import net.minecraft.world.level.levelgen.feature.StructureFeature;
|
||||
+import org.bukkit.NamespacedKey;
|
||||
+import org.bukkit.StructureType;
|
||||
+import org.checkerframework.checker.nullness.qual.NonNull;
|
||||
+import org.checkerframework.framework.qual.DefaultQualifier;
|
||||
+
|
||||
+import java.util.Objects;
|
||||
+import java.util.function.Supplier;
|
||||
+
|
||||
+@DefaultQualifier(NonNull.class)
|
||||
+public final class PaperConfiguredStructure {
|
||||
+
|
||||
+ private PaperConfiguredStructure() {
|
||||
+ }
|
||||
+
|
||||
+ public static void init() {
|
||||
+ new ConfiguredStructureRegistry().register();
|
||||
+ }
|
||||
+
|
||||
+ static final class ConfiguredStructureRegistry extends PaperRegistry<ConfiguredStructure, ConfiguredStructureFeature<?, ?>> {
|
||||
+
|
||||
+ private static final Supplier<Registry<StructureFeature<?>>> STRUCTURE_FEATURE_REGISTRY = registryFor(Registry.STRUCTURE_FEATURE_REGISTRY);
|
||||
+
|
||||
+ public ConfiguredStructureRegistry() {
|
||||
+ super(RegistryKey.CONFIGURED_STRUCTURE_REGISTRY);
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public ConfiguredStructure convertToApi(NamespacedKey key, ConfiguredStructureFeature<?, ?> nms) {
|
||||
+ final ResourceLocation structureFeatureLoc = Objects.requireNonNull(STRUCTURE_FEATURE_REGISTRY.get().getKey(nms.feature));
|
||||
+ final StructureType structureType = Objects.requireNonNull(StructureType.getStructureTypes().get(structureFeatureLoc.getPath()), structureFeatureLoc + " could not be converted to an API type");
|
||||
+ return new ConfiguredStructure(key, structureType);
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
diff --git a/src/main/java/net/minecraft/server/MinecraftServer.java b/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
index 9941456a019a34384f892c44df3c73f9416bd560..d109ef77109fbeb710eafb55a38c803b9bb37d73 100644
|
||||
--- a/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
+++ b/src/main/java/net/minecraft/server/MinecraftServer.java
|
||||
@@ -2032,7 +2032,7 @@ public abstract class MinecraftServer extends ReentrantBlockableEventLoop<TickTa
|
||||
this.packRepository.setSelected(dataPacks);
|
||||
this.worldData.setDataPackConfig(MinecraftServer.getSelectedPacks(this.packRepository));
|
||||
this.resources.managers.updateRegistryTags(this.registryAccess());
|
||||
- io.papermc.paper.PaperRegistry.clearCaches(); // Paper
|
||||
+ io.papermc.paper.registry.PaperRegistry.clearCaches(); // Paper
|
||||
new io.papermc.paper.event.server.ServerResourcesReloadedEvent(cause).callEvent(); // Paper
|
||||
if (Thread.currentThread() != this.serverThread) return; // Paper
|
||||
//this.getPlayerList().saveAll(); // Paper - we don't need to do this
|
||||
diff --git a/src/main/java/net/minecraft/world/level/chunk/ChunkGenerator.java b/src/main/java/net/minecraft/world/level/chunk/ChunkGenerator.java
|
||||
index fff5c9d40a0bab8642376db3ec25cc1e8d666fa6..a3af8b892a01756addc8c24e0726b5a8a700cbba 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/chunk/ChunkGenerator.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/chunk/ChunkGenerator.java
|
||||
@@ -302,6 +302,26 @@ public abstract class ChunkGenerator implements BiomeManager.NoiseBiomeSource {
|
||||
|
||||
@Nullable
|
||||
public Pair<BlockPos, Holder<ConfiguredStructureFeature<?, ?>>> findNearestMapFeature(ServerLevel worldserver, HolderSet<ConfiguredStructureFeature<?, ?>> holderset, BlockPos center, int radius, boolean skipExistingChunks) {
|
||||
+ // Paper start - StructureLocateEvent
|
||||
+ final org.bukkit.World world = worldserver.getWorld();
|
||||
+ final org.bukkit.Location origin = net.minecraft.server.MCUtil.toLocation(worldserver, center);
|
||||
+ final var paperRegistry = io.papermc.paper.registry.PaperRegistry.getRegistry(io.papermc.paper.registry.RegistryKey.CONFIGURED_STRUCTURE_REGISTRY);
|
||||
+ final List<io.papermc.paper.world.structure.ConfiguredStructure> configuredStructures = new ArrayList<>();
|
||||
+ for (Holder<net.minecraft.world.level.levelgen.feature.ConfiguredStructureFeature<?, ?>> holder : holderset) {
|
||||
+ configuredStructures.add(paperRegistry.convertToApi(holder));
|
||||
+ }
|
||||
+ final io.papermc.paper.event.world.StructuresLocateEvent event = new io.papermc.paper.event.world.StructuresLocateEvent(world, origin, configuredStructures, radius, skipExistingChunks);
|
||||
+ if (!event.callEvent()) {
|
||||
+ return null;
|
||||
+ }
|
||||
+ if (event.getResult() != null) {
|
||||
+ return Pair.of(net.minecraft.server.MCUtil.toBlockPosition(event.getResult().position()), paperRegistry.getMinecraftHolder(event.getResult().configuredStructure()));
|
||||
+ }
|
||||
+ center = net.minecraft.server.MCUtil.toBlockPosition(event.getOrigin());
|
||||
+ radius = event.getRadius();
|
||||
+ skipExistingChunks = event.shouldFindUnexplored();
|
||||
+ holderset = HolderSet.direct(paperRegistry::getMinecraftHolder, event.getConfiguredStructures());
|
||||
+ // Paper end
|
||||
Set<Holder<Biome>> set = (Set) holderset.stream().flatMap((holder) -> {
|
||||
return ((ConfiguredStructureFeature) holder.value()).biomes().stream();
|
||||
}).collect(Collectors.toSet());
|
||||
diff --git a/src/main/java/net/minecraft/world/level/levelgen/feature/ConfiguredStructureFeature.java b/src/main/java/net/minecraft/world/level/levelgen/feature/ConfiguredStructureFeature.java
|
||||
index af9ef29f5c5a600e4544ba735c833699cc93f93a..473a54963fbe08beeff26a828827f9f72d8a29b8 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/levelgen/feature/ConfiguredStructureFeature.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/levelgen/feature/ConfiguredStructureFeature.java
|
||||
@@ -38,6 +38,7 @@ public class ConfiguredStructureFeature<FC extends FeatureConfiguration, F exten
|
||||
public final HolderSet<Biome> biomes;
|
||||
public final Map<MobCategory, StructureSpawnOverride> spawnOverrides;
|
||||
public final boolean adaptNoise;
|
||||
+ static { io.papermc.paper.world.structure.PaperConfiguredStructure.init(); } // Paper
|
||||
|
||||
public ConfiguredStructureFeature(F feature, FC config, HolderSet<Biome> biomes, boolean bl, Map<MobCategory, StructureSpawnOverride> map) {
|
||||
this.feature = feature;
|
||||
diff --git a/src/test/java/io/papermc/paper/world/structure/ConfiguredStructureTest.java b/src/test/java/io/papermc/paper/world/structure/ConfiguredStructureTest.java
|
||||
new file mode 100644
|
||||
index 0000000000000000000000000000000000000000..29c0209327374d5a4dad4e3bacdba7fa56d80749
|
||||
--- /dev/null
|
||||
+++ b/src/test/java/io/papermc/paper/world/structure/ConfiguredStructureTest.java
|
||||
@@ -0,0 +1,89 @@
|
||||
+package io.papermc.paper.world.structure;
|
||||
+
|
||||
+import io.papermc.paper.registry.Reference;
|
||||
+import net.minecraft.data.BuiltinRegistries;
|
||||
+import net.minecraft.resources.ResourceKey;
|
||||
+import net.minecraft.resources.ResourceLocation;
|
||||
+import net.minecraft.server.Bootstrap;
|
||||
+import net.minecraft.world.level.levelgen.feature.ConfiguredStructureFeature;
|
||||
+import net.minecraft.world.level.levelgen.structure.BuiltinStructures;
|
||||
+import org.bukkit.NamespacedKey;
|
||||
+import org.bukkit.craftbukkit.util.CraftNamespacedKey;
|
||||
+import org.bukkit.support.AbstractTestingBase;
|
||||
+import org.junit.AfterClass;
|
||||
+import org.junit.BeforeClass;
|
||||
+import org.junit.Test;
|
||||
+
|
||||
+import java.io.PrintStream;
|
||||
+import java.lang.reflect.Field;
|
||||
+import java.lang.reflect.Modifier;
|
||||
+import java.util.LinkedHashMap;
|
||||
+import java.util.Map;
|
||||
+import java.util.StringJoiner;
|
||||
+
|
||||
+import static org.junit.Assert.assertEquals;
|
||||
+import static org.junit.Assert.assertNotNull;
|
||||
+import static org.junit.Assert.assertTrue;
|
||||
+
|
||||
+public class ConfiguredStructureTest extends AbstractTestingBase {
|
||||
+
|
||||
+ private static final Map<ResourceLocation, String> BUILT_IN_STRUCTURES = new LinkedHashMap<>();
|
||||
+ private static final Map<NamespacedKey, Reference<?>> DEFAULT_CONFIGURED_STRUCTURES = new LinkedHashMap<>();
|
||||
+
|
||||
+ private static PrintStream out;
|
||||
+
|
||||
+ @BeforeClass
|
||||
+ public static void collectStructures() throws ReflectiveOperationException {
|
||||
+ out = System.out;
|
||||
+ System.setOut(Bootstrap.STDOUT);
|
||||
+ for (Field field : BuiltinStructures.class.getDeclaredFields()) {
|
||||
+ if (field.getType().equals(ResourceKey.class) && Modifier.isStatic(field.getModifiers())) {
|
||||
+ BUILT_IN_STRUCTURES.put(((ResourceKey<?>) field.get(null)).location(), field.getName());
|
||||
+ }
|
||||
+ }
|
||||
+ for (Field field : ConfiguredStructure.class.getDeclaredFields()) {
|
||||
+ if (field.getType().equals(Reference.class) && Modifier.isStatic(field.getModifiers())) {
|
||||
+ final Reference<?> ref = (Reference<?>) field.get(null);
|
||||
+ DEFAULT_CONFIGURED_STRUCTURES.put(ref.getKey(), ref);
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ @Test
|
||||
+ public void testMinecraftToApi() {
|
||||
+ assertEquals("configured structure maps should be the same size", BUILT_IN_STRUCTURES.size(), BuiltinRegistries.CONFIGURED_STRUCTURE_FEATURE.size());
|
||||
+
|
||||
+ Map<ResourceLocation, ConfiguredStructureFeature<?, ?>> missing = new LinkedHashMap<>();
|
||||
+ for (ConfiguredStructureFeature<?, ?> feature : BuiltinRegistries.CONFIGURED_STRUCTURE_FEATURE) {
|
||||
+ final ResourceLocation key = BuiltinRegistries.CONFIGURED_STRUCTURE_FEATURE.getKey(feature);
|
||||
+ assertNotNull("Missing built-in registry key", key);
|
||||
+ if (DEFAULT_CONFIGURED_STRUCTURES.get(CraftNamespacedKey.fromMinecraft(key)) == null) {
|
||||
+ missing.put(key, feature);
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ assertTrue(printMissing(missing), missing.isEmpty());
|
||||
+ }
|
||||
+
|
||||
+ @Test
|
||||
+ public void testApiToMinecraft() {
|
||||
+ for (NamespacedKey apiKey : DEFAULT_CONFIGURED_STRUCTURES.keySet()) {
|
||||
+ assertTrue(apiKey + " does not have a minecraft counterpart", BuiltinRegistries.CONFIGURED_STRUCTURE_FEATURE.containsKey(CraftNamespacedKey.toMinecraft(apiKey)));
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ private static String printMissing(Map<ResourceLocation, ConfiguredStructureFeature<?, ?>> missing) {
|
||||
+ final StringJoiner joiner = new StringJoiner("\n", "Missing: \n", "");
|
||||
+
|
||||
+ missing.forEach((key, configuredFeature) -> {
|
||||
+ joiner.add("public static final Reference<ConfiguredStructure> " + BUILT_IN_STRUCTURES.get(key) + " = create(\"" + key.getPath() + "\");");
|
||||
+ });
|
||||
+
|
||||
+ return joiner.toString();
|
||||
+ }
|
||||
+
|
||||
+ @AfterClass
|
||||
+ public static void after() {
|
||||
+ System.setOut(out);
|
||||
+ }
|
||||
+}
|
|
@ -1,65 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Mariell Hoversholm <proximyst@proximyst.com>
|
||||
Date: Sat, 14 Nov 2020 16:48:37 +0100
|
||||
Subject: [PATCH] Collision option for requiring a player participant
|
||||
|
||||
|
||||
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
index 96fd9803810db0f8a4b25e070a56da05862e1e4e..2b3e034d6cddbe5c94f2be856833680dd7b3b4f0 100644
|
||||
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
@@ -115,6 +115,18 @@ public class PaperWorldConfig {
|
||||
}
|
||||
}
|
||||
|
||||
+ public boolean onlyPlayersCollide = false;
|
||||
+ public boolean allowVehicleCollisions = true;
|
||||
+ private void onlyPlayersCollide() {
|
||||
+ onlyPlayersCollide = getBoolean("only-players-collide", onlyPlayersCollide);
|
||||
+ allowVehicleCollisions = getBoolean("allow-vehicle-collisions", allowVehicleCollisions);
|
||||
+ if (onlyPlayersCollide && !allowVehicleCollisions) {
|
||||
+ log("Collisions will only work if a player is one of the two entities colliding.");
|
||||
+ } else if (onlyPlayersCollide) {
|
||||
+ log("Collisions will only work if a player OR a vehicle is one of the two entities colliding.");
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
public int wanderingTraderSpawnMinuteTicks = 1200;
|
||||
public int wanderingTraderSpawnDayTicks = 24000;
|
||||
public int wanderingTraderSpawnChanceFailureIncrement = 25;
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/Entity.java b/src/main/java/net/minecraft/world/entity/Entity.java
|
||||
index e53d8fe713a4c9920f40bf91d6453d36520b45f7..c14cbbf7d88d99bf5f24aad5c45fcb1504187a16 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/Entity.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/Entity.java
|
||||
@@ -1631,6 +1631,7 @@ public abstract class Entity implements Nameable, EntityAccess, CommandSource {
|
||||
public void push(Entity entity) {
|
||||
if (!this.isPassengerOfSameVehicle(entity)) {
|
||||
if (!entity.noPhysics && !this.noPhysics) {
|
||||
+ if (this.level.paperConfig.onlyPlayersCollide && !(entity instanceof ServerPlayer || this instanceof ServerPlayer)) return; // Paper
|
||||
double d0 = entity.getX() - this.getX();
|
||||
double d1 = entity.getZ() - this.getZ();
|
||||
double d2 = Mth.absMax(d0, d1);
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/vehicle/AbstractMinecart.java b/src/main/java/net/minecraft/world/entity/vehicle/AbstractMinecart.java
|
||||
index 110006087af3f87457031dad7756235363af0506..96a7bfd921e59f298f0ee502d356cc3552c30ce8 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/vehicle/AbstractMinecart.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/vehicle/AbstractMinecart.java
|
||||
@@ -831,6 +831,7 @@ public abstract class AbstractMinecart extends Entity {
|
||||
public void push(Entity entity) {
|
||||
if (!this.level.isClientSide) {
|
||||
if (!entity.noPhysics && !this.noPhysics) {
|
||||
+ if (!this.level.paperConfig.allowVehicleCollisions && this.level.paperConfig.onlyPlayersCollide && !(entity instanceof Player)) return; // Paper
|
||||
if (!this.hasPassenger(entity)) {
|
||||
// CraftBukkit start
|
||||
VehicleEntityCollisionEvent collisionEvent = new VehicleEntityCollisionEvent((Vehicle) this.getBukkitEntity(), entity.getBukkitEntity());
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/vehicle/Boat.java b/src/main/java/net/minecraft/world/entity/vehicle/Boat.java
|
||||
index c75e45bcb8cd6da154c7ca1719711622c009f463..a8f37fab9c8020e884bf029145d03e3be57b7f2b 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/vehicle/Boat.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/vehicle/Boat.java
|
||||
@@ -239,6 +239,7 @@ public class Boat extends Entity {
|
||||
|
||||
@Override
|
||||
public void push(Entity entity) {
|
||||
+ if (!this.level.paperConfig.allowVehicleCollisions && this.level.paperConfig.onlyPlayersCollide && !(entity instanceof Player)) return; // Paper
|
||||
if (entity instanceof Boat) {
|
||||
if (entity.getBoundingBox().minY < this.getBoundingBox().maxY) {
|
||||
// CraftBukkit start
|
|
@ -1,21 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Aikar <aikar@aikar.co>
|
||||
Date: Sat, 16 Jan 2021 14:30:12 -0500
|
||||
Subject: [PATCH] Remove ProjectileHitEvent call when fireballs dead
|
||||
|
||||
The duplicate ProjectileHitEvent in EntityFireball was removed. The
|
||||
event was always called before the duplicate call.
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/projectile/AbstractHurtingProjectile.java b/src/main/java/net/minecraft/world/entity/projectile/AbstractHurtingProjectile.java
|
||||
index 3de3258418f638a1b523c6a9178bb3ef1aaf2915..fa4e930388baa2ee0a752873b2ec1a67cc020de6 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/projectile/AbstractHurtingProjectile.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/projectile/AbstractHurtingProjectile.java
|
||||
@@ -97,7 +97,7 @@ public abstract class AbstractHurtingProjectile extends Projectile {
|
||||
|
||||
// CraftBukkit start - Fire ProjectileHitEvent
|
||||
if (this.isRemoved()) {
|
||||
- CraftEventFactory.callProjectileHitEvent(this, movingobjectposition);
|
||||
+ // CraftEventFactory.callProjectileHitEvent(this, movingobjectposition); // Paper - this is an undesired duplicate event
|
||||
}
|
||||
// CraftBukkit end
|
||||
}
|
|
@ -1,33 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: CDFN <codefun@protonmail.com>
|
||||
Date: Tue, 7 Jul 2020 17:53:23 +0200
|
||||
Subject: [PATCH] Return chat component with empty text instead of throwing
|
||||
exception
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java b/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java
|
||||
index 3dc87e86dcd4c87e8e87e1dcd2765acb3b258bdf..bc0a49d41bdbc5544f789150ac239617d03b5837 100644
|
||||
--- a/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java
|
||||
+++ b/src/main/java/net/minecraft/world/inventory/AbstractContainerMenu.java
|
||||
@@ -22,6 +22,7 @@ import net.minecraft.ReportedException;
|
||||
import net.minecraft.core.NonNullList;
|
||||
import net.minecraft.core.Registry;
|
||||
import net.minecraft.network.chat.Component;
|
||||
+import net.minecraft.network.chat.TextComponent;
|
||||
import net.minecraft.network.protocol.game.ClientboundContainerSetSlotPacket;
|
||||
import net.minecraft.server.level.ServerPlayer;
|
||||
import net.minecraft.util.Mth;
|
||||
@@ -88,7 +89,12 @@ public abstract class AbstractContainerMenu {
|
||||
}
|
||||
private Component title;
|
||||
public final Component getTitle() {
|
||||
- Preconditions.checkState(this.title != null, "Title not set");
|
||||
+ // Paper start - return chat component with empty text instead of throwing error
|
||||
+ // Preconditions.checkState(this.title != null, "Title not set");
|
||||
+ if(this.title == null){
|
||||
+ return new TextComponent("");
|
||||
+ }
|
||||
+ // Paper end
|
||||
return this.title;
|
||||
}
|
||||
public final void setTitle(Component title) {
|
|
@ -1,28 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Mon, 4 Jan 2021 19:52:44 -0800
|
||||
Subject: [PATCH] Make schedule command per-world
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/server/commands/ScheduleCommand.java b/src/main/java/net/minecraft/server/commands/ScheduleCommand.java
|
||||
index 210df39e99bfe0f373cbdf7e0cd45ff1db9cd4aa..c0127908a954d3a40ca8829e3f1f63112212f261 100644
|
||||
--- a/src/main/java/net/minecraft/server/commands/ScheduleCommand.java
|
||||
+++ b/src/main/java/net/minecraft/server/commands/ScheduleCommand.java
|
||||
@@ -31,7 +31,7 @@ public class ScheduleCommand {
|
||||
return new TranslatableComponent("commands.schedule.cleared.failure", new Object[]{object});
|
||||
});
|
||||
private static final SuggestionProvider<CommandSourceStack> SUGGEST_SCHEDULE = (commandcontext, suggestionsbuilder) -> {
|
||||
- return SharedSuggestionProvider.suggest((Iterable) ((CommandSourceStack) commandcontext.getSource()).getServer().getWorldData().overworldData().getScheduledEvents().getEventsIds(), suggestionsbuilder);
|
||||
+ return SharedSuggestionProvider.suggest((Iterable) ((net.minecraft.commands.CommandSourceStack) commandcontext.getSource()).getLevel().serverLevelData.getScheduledEvents().getEventsIds(), suggestionsbuilder); // Paper
|
||||
};
|
||||
|
||||
public ScheduleCommand() {}
|
||||
@@ -82,7 +82,7 @@ public class ScheduleCommand {
|
||||
}
|
||||
|
||||
private static int remove(CommandSourceStack source, String eventName) throws CommandSyntaxException {
|
||||
- int i = source.getServer().getWorldData().overworldData().getScheduledEvents().remove(eventName);
|
||||
+ int i = source.getLevel().serverLevelData.getScheduledEvents().remove(eventName); // Paper
|
||||
|
||||
if (i == 0) {
|
||||
throw ScheduleCommand.ERROR_CANT_REMOVE.create(eventName);
|
|
@ -1,45 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Sun, 3 Jan 2021 21:04:03 -0800
|
||||
Subject: [PATCH] Configurable max leash distance
|
||||
|
||||
|
||||
diff --git a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
index 2b3e034d6cddbe5c94f2be856833680dd7b3b4f0..9bb6b6c6ac26790eaf5f8efe55f8db7407fc0065 100644
|
||||
--- a/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
+++ b/src/main/java/com/destroystokyo/paper/PaperWorldConfig.java
|
||||
@@ -342,6 +342,12 @@ public class PaperWorldConfig {
|
||||
}
|
||||
}
|
||||
|
||||
+ public float maxLeashDistance = 10f;
|
||||
+ private void maxLeashDistance() {
|
||||
+ maxLeashDistance = getFloat("max-leash-distance", maxLeashDistance);
|
||||
+ log("Max leash distance: " + maxLeashDistance);
|
||||
+ }
|
||||
+
|
||||
public boolean disableEndCredits;
|
||||
private void disableEndCredits() {
|
||||
disableEndCredits = getBoolean("game-mechanics.disable-end-credits", false);
|
||||
diff --git a/src/main/java/net/minecraft/world/entity/PathfinderMob.java b/src/main/java/net/minecraft/world/entity/PathfinderMob.java
|
||||
index d1ab31d03ae421e628448fe2492ff138dc57c00f..999d18610666ec442bb038da5c452e3cd77e7428 100644
|
||||
--- a/src/main/java/net/minecraft/world/entity/PathfinderMob.java
|
||||
+++ b/src/main/java/net/minecraft/world/entity/PathfinderMob.java
|
||||
@@ -48,7 +48,7 @@ public abstract class PathfinderMob extends Mob {
|
||||
float f = this.distanceTo(entity);
|
||||
|
||||
if (this instanceof TamableAnimal && ((TamableAnimal) this).isInSittingPose()) {
|
||||
- if (f > 10.0F) {
|
||||
+ if (f > entity.level.paperConfig.maxLeashDistance) { // Paper
|
||||
this.level.getCraftServer().getPluginManager().callEvent(new EntityUnleashEvent(this.getBukkitEntity(), EntityUnleashEvent.UnleashReason.DISTANCE)); // CraftBukkit
|
||||
this.dropLeash(true, true);
|
||||
}
|
||||
@@ -57,7 +57,7 @@ public abstract class PathfinderMob extends Mob {
|
||||
}
|
||||
|
||||
this.onLeashDistance(f);
|
||||
- if (f > 10.0F) {
|
||||
+ if (f > entity.level.paperConfig.maxLeashDistance) { // Paper
|
||||
this.level.getCraftServer().getPluginManager().callEvent(new EntityUnleashEvent(this.getBukkitEntity(), EntityUnleashEvent.UnleashReason.DISTANCE)); // CraftBukkit
|
||||
this.dropLeash(true, true);
|
||||
this.goalSelector.disableControlFlag(Goal.Flag.MOVE);
|
|
@ -1,34 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Madeline Miller <mnmiller1@me.com>
|
||||
Date: Sun, 17 Jan 2021 13:16:09 +1000
|
||||
Subject: [PATCH] Implement BlockPreDispenseEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/level/block/DispenserBlock.java b/src/main/java/net/minecraft/world/level/block/DispenserBlock.java
|
||||
index 07d357b5fcb30ed9ff074a196a19de1481fe3738..83ac86b3c1e7b9233f2db8e5488f97c5b44f8843 100644
|
||||
--- a/src/main/java/net/minecraft/world/level/block/DispenserBlock.java
|
||||
+++ b/src/main/java/net/minecraft/world/level/block/DispenserBlock.java
|
||||
@@ -92,6 +92,7 @@ public class DispenserBlock extends BaseEntityBlock {
|
||||
DispenseItemBehavior idispensebehavior = this.getDispenseMethod(itemstack);
|
||||
|
||||
if (idispensebehavior != DispenseItemBehavior.NOOP) {
|
||||
+ if (!org.bukkit.craftbukkit.event.CraftEventFactory.handleBlockPreDispenseEvent(world, pos, itemstack, i)) return; // Paper - BlockPreDispenseEvent is called here
|
||||
DispenserBlock.eventFired = false; // CraftBukkit - reset event status
|
||||
tileentitydispenser.setItem(i, idispensebehavior.dispense(sourceblock, itemstack));
|
||||
}
|
||||
diff --git a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
index dbc777a7d872116da0f60953fc6a650df17d9f5c..30bf86f0f22b783273286b4372541f8a2def0eb2 100644
|
||||
--- a/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
+++ b/src/main/java/org/bukkit/craftbukkit/event/CraftEventFactory.java
|
||||
@@ -1883,5 +1883,11 @@ public class CraftEventFactory {
|
||||
io.papermc.paper.event.block.BlockFailedDispenseEvent event = new io.papermc.paper.event.block.BlockFailedDispenseEvent(block);
|
||||
return event.callEvent();
|
||||
}
|
||||
+
|
||||
+ public static boolean handleBlockPreDispenseEvent(ServerLevel serverLevel, BlockPos pos, ItemStack itemStack, int slot) {
|
||||
+ org.bukkit.block.Block block = serverLevel.getWorld().getBlockAt(pos.getX(), pos.getY(), pos.getZ());
|
||||
+ io.papermc.paper.event.block.BlockPreDispenseEvent event = new io.papermc.paper.event.block.BlockPreDispenseEvent(block, org.bukkit.craftbukkit.inventory.CraftItemStack.asCraftMirror(itemStack), slot);
|
||||
+ return event.callEvent();
|
||||
+ }
|
||||
// Paper end
|
||||
}
|
|
@ -1,29 +0,0 @@
|
|||
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
|
||||
From: Jake Potrebic <jake.m.potrebic@gmail.com>
|
||||
Date: Wed, 24 Jun 2020 15:14:51 -0600
|
||||
Subject: [PATCH] Added firing of PlayerChangeBeaconEffectEvent
|
||||
|
||||
|
||||
diff --git a/src/main/java/net/minecraft/world/inventory/BeaconMenu.java b/src/main/java/net/minecraft/world/inventory/BeaconMenu.java
|
||||
index 063998751c21b4f75cf3bfff6c51c4e8c42bd5f3..a515898e718effe92c91fd0ac45fbb70ddb5d626 100644
|
||||
--- a/src/main/java/net/minecraft/world/inventory/BeaconMenu.java
|
||||
+++ b/src/main/java/net/minecraft/world/inventory/BeaconMenu.java
|
||||
@@ -160,10 +160,16 @@ public class BeaconMenu extends AbstractContainerMenu {
|
||||
|
||||
public void updateEffects(int primaryEffectId, int secondaryEffectId) {
|
||||
if (this.paymentSlot.hasItem()) {
|
||||
- this.beaconData.set(1, primaryEffectId);
|
||||
- this.beaconData.set(2, secondaryEffectId);
|
||||
+ // Paper start
|
||||
+ io.papermc.paper.event.player.PlayerChangeBeaconEffectEvent event = new io.papermc.paper.event.player.PlayerChangeBeaconEffectEvent((org.bukkit.entity.Player) this.player.player.getBukkitEntity(), org.bukkit.potion.PotionEffectType.getById(primaryEffectId), org.bukkit.potion.PotionEffectType.getById(secondaryEffectId), this.access.getLocation().getBlock());
|
||||
+ if (event.callEvent()) {
|
||||
+ this.beaconData.set(1, event.getPrimary() == null ? 0 : event.getPrimary().getId());
|
||||
+ this.beaconData.set(2, event.getSecondary() == null ? 0 : event.getSecondary().getId());
|
||||
+ if (!event.willConsumeItem()) return;
|
||||
this.paymentSlot.remove(1);
|
||||
this.access.execute(Level::blockEntityChanged);
|
||||
+ }
|
||||
+ // Paper end
|
||||
}
|
||||
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue