-
-
Notifications
You must be signed in to change notification settings - Fork 73
大量紧急修复 #1188
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
大量紧急修复 #1188
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 无需更改 |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,16 +1,12 @@ | ||
| package io.github.thebusybiscuit.slimefun4.implementation.listeners; | ||
|
|
||
| import com.xzavier0722.mc.plugin.slimefun4.storage.callback.IAsyncReadCallback; | ||
| import com.xzavier0722.mc.plugin.slimefun4.storage.controller.ASlimefunDataContainer; | ||
| import com.xzavier0722.mc.plugin.slimefun4.storage.util.StorageCacheUtils; | ||
| import io.github.thebusybiscuit.slimefun4.api.items.SlimefunItem; | ||
| import io.github.thebusybiscuit.slimefun4.core.attributes.WitherProof; | ||
| import io.github.thebusybiscuit.slimefun4.core.handlers.BlockBreakHandler; | ||
| import io.github.thebusybiscuit.slimefun4.implementation.Slimefun; | ||
| import io.github.thebusybiscuit.slimefun4.utils.tags.SlimefunTag; | ||
| import io.papermc.lib.PaperLib; | ||
| import io.papermc.lib.features.blockstatesnapshot.BlockStateSnapshotResult; | ||
| import java.util.ArrayList; | ||
| import java.util.Objects; | ||
| import javax.annotation.Nonnull; | ||
| import org.bukkit.Location; | ||
|
|
@@ -67,58 +63,35 @@ public void onBlockFall(EntityChangeBlockEvent e) { | |
| } | ||
| } | ||
|
|
||
| case WITHER, WITHER_SKULL -> { | ||
| case WITHER -> { | ||
| // fix issue 1126 | ||
| // the wither break is handled in the WitherListener, then the data is removed there, so it will | ||
| // conflict with this listener | ||
| var block = e.getBlock(); | ||
| var item = SlimefunItem.getById(blockData.getSfId()); | ||
|
|
||
| var controller = Slimefun.getDatabaseManager().getBlockDataController(); | ||
| if (item != null | ||
| && !(item instanceof WitherProof) | ||
| && !item.callItemHandler(BlockBreakHandler.class, handler -> { | ||
| if (blockData.isDataLoaded()) { | ||
| callHandler(handler, block); | ||
| } else { | ||
| blockData.setPendingRemove(true); | ||
| controller.loadDataAsync(blockData, new IAsyncReadCallback<>() { | ||
| @Override | ||
| public boolean runOnMainThread() { | ||
| return true; | ||
| } | ||
|
|
||
| @Override | ||
| public void onResult(ASlimefunDataContainer result) { | ||
| callHandler(handler, block); | ||
| blockData.setPendingRemove(false); | ||
| } | ||
| }); | ||
| } | ||
| })) { | ||
| if (item != null) { | ||
| if (item instanceof WitherProof witherProof) { | ||
| witherProof.onAttackEvent(e); | ||
| if (!e.isCancelled()) { | ||
| return; | ||
| } | ||
| } | ||
| controller.removeBlock(block.getLocation()); | ||
| block.setType(Material.AIR); | ||
| for (var drop : item.getDrops()) { | ||
| if (drop != null && !drop.getType().isAir()) { | ||
| block.getWorld().dropItemNaturally(block.getLocation(), drop); | ||
| } | ||
| } | ||
| } | ||
|
Comment on lines
+66
to
87
|
||
| } | ||
|
|
||
| // fix: issue 1126 there is not such EntityChangeBlockEvent about WitherSkull | ||
| // Don't move my machine :| | ||
| case ENDERMAN -> e.setCancelled(true); | ||
| } | ||
| } | ||
|
|
||
| private void callHandler(BlockBreakHandler handler, Block b) { | ||
| if (handler.isExplosionAllowed(b)) { | ||
| b.setType(Material.AIR); | ||
|
|
||
| var drops = new ArrayList<ItemStack>(); | ||
| handler.onExplode(b, drops); | ||
| Slimefun.getDatabaseManager().getBlockDataController().removeBlock(b.getLocation()); | ||
|
|
||
| for (var drop : drops) { | ||
| if (drop != null && !drop.getType().isAir()) { | ||
| b.getWorld().dropItemNaturally(b.getLocation(), drop); | ||
| } | ||
| } | ||
| } | ||
| } | ||
|
|
||
| @EventHandler(ignoreCancelled = true) | ||
| public void onPistonExtend(BlockPistonExtendEvent e) { | ||
| if (StorageCacheUtils.hasSlimefunBlock(e.getBlock().getLocation())) { | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -13,7 +13,6 @@ | |
| import java.util.ArrayList; | ||
| import java.util.Iterator; | ||
| import java.util.List; | ||
| import java.util.concurrent.atomic.AtomicBoolean; | ||
| import javax.annotation.Nonnull; | ||
| import javax.annotation.ParametersAreNonnullByDefault; | ||
| import org.bukkit.ExplosionResult; | ||
|
|
@@ -69,9 +68,6 @@ public void onBlockExplode(BlockExplodeEvent e) { | |
| } | ||
|
|
||
| private void removeResistantBlocks(@Nonnull Iterator<Block> blocks) { | ||
| // For explosion handling, only update network once for a random affected block to improve performance. | ||
| AtomicBoolean networkUpdated = new AtomicBoolean(false); | ||
|
|
||
| while (blocks.hasNext()) { | ||
| Block block = blocks.next(); | ||
| var loc = block.getLocation(); | ||
|
|
@@ -80,21 +76,28 @@ private void removeResistantBlocks(@Nonnull Iterator<Block> blocks) { | |
|
|
||
| if (item != null) { | ||
| blocks.remove(); | ||
|
|
||
| if (!(item instanceof WitherProof) && !callBreakHandler(item, blockData, block, networkUpdated)) { | ||
| Slimefun.getDatabaseManager().getBlockDataController().removeBlock(loc); | ||
| block.setType(Material.AIR); | ||
| updateNearbyNetwork(item, loc, networkUpdated); | ||
| // add WitherProof api | ||
| if (item instanceof WitherProof) { | ||
| continue; | ||
| } else { | ||
| Runnable destroyTask = () -> { | ||
| block.setType(Material.AIR); | ||
| Slimefun.getDatabaseManager().getBlockDataController().removeBlock(loc); | ||
| updateNearbyNetwork(item, loc); | ||
| }; | ||
| // fix # 1187, the callBreakHandler returns true if there is no handler exist actually, so it | ||
| // shouldn't be added a ! | ||
| callBreakHandler(item, blockData, block, destroyTask); | ||
| } | ||
| } | ||
| } | ||
| } | ||
|
|
||
| private boolean callBreakHandler( | ||
| SlimefunItem item, ASlimefunDataContainer blockData, Block block, AtomicBoolean updateRef) { | ||
| return !item.callItemHandler(BlockBreakHandler.class, handler -> { | ||
| private void callBreakHandler( | ||
| SlimefunItem item, ASlimefunDataContainer blockData, Block block, Runnable destroyBlockCb) { | ||
| if (!item.callItemHandler(BlockBreakHandler.class, handler -> { | ||
| if (blockData.isDataLoaded()) { | ||
| handleExplosion(handler, block, item, updateRef); | ||
| handleExplosion(handler, block, item, destroyBlockCb); | ||
| } else { | ||
| Slimefun.getDatabaseManager() | ||
| .getBlockDataController() | ||
|
|
@@ -106,44 +109,37 @@ public boolean runOnMainThread() { | |
|
|
||
| @Override | ||
| public void onResult(ASlimefunDataContainer result) { | ||
| handleExplosion(handler, block, item, updateRef); | ||
| handleExplosion(handler, block, item, destroyBlockCb); | ||
| } | ||
| }); | ||
| } | ||
| }); | ||
| })) { | ||
| destroyBlockCb.run(); | ||
| } | ||
| } | ||
|
|
||
| @ParametersAreNonnullByDefault | ||
| private void handleExplosion(BlockBreakHandler handler, Block block, SlimefunItem item, AtomicBoolean ref) { | ||
| private void handleExplosion(BlockBreakHandler handler, Block block, SlimefunItem item, Runnable destroyBlockCb) { | ||
| if (handler.isExplosionAllowed(block)) { | ||
| block.setType(Material.AIR); | ||
|
|
||
| List<ItemStack> drops = new ArrayList<>(); | ||
| // fix : 1187, machine should drop themselves first, in explosion | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 这里之前反复修过几次,看看有没有其他地方监听了导致刷物的情况
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 应该没有 正常onBlockBreak也是需要从getDrops开始的, 而且目前就是不掉机器本体 |
||
| List<ItemStack> drops = new ArrayList<>(item.getDrops()); | ||
| handler.onExplode(block, drops); | ||
| Slimefun.getDatabaseManager().getBlockDataController().removeBlock(block.getLocation()); | ||
|
|
||
| for (ItemStack drop : drops) { | ||
| if (drop != null && !drop.getType().isAir()) { | ||
| block.getWorld().dropItemNaturally(block.getLocation(), drop); | ||
| } | ||
| } | ||
|
|
||
| updateNearbyNetwork(item, block.getLocation(), ref); | ||
| destroyBlockCb.run(); | ||
| } | ||
| } | ||
|
|
||
| @ParametersAreNonnullByDefault | ||
| private void updateNearbyNetwork(SlimefunItem item, Location loc, AtomicBoolean updated) { | ||
| if (updated.get()) { | ||
| return; | ||
| } | ||
|
|
||
| private void updateNearbyNetwork(SlimefunItem item, Location loc) { | ||
| if (!(item instanceof EnergyNetComponent) && !(item instanceof CargoNode)) { | ||
| return; | ||
| } | ||
|
|
||
| Slimefun.getNetworkManager().updateAllNetworks(loc); | ||
|
|
||
| updated.getAndSet(true); | ||
| } | ||
| } | ||
Uh oh!
There was an error while loading. Please reload this page.