2019-04-29 02:58:38 +02:00
|
|
|
package com.songoda.ultimatetimber.manager;
|
|
|
|
|
2023-06-29 14:38:33 +02:00
|
|
|
import com.craftaro.core.compatibility.CompatibleMaterial;
|
2019-04-29 02:58:38 +02:00
|
|
|
import com.songoda.ultimatetimber.UltimateTimber;
|
|
|
|
import com.songoda.ultimatetimber.events.TreeFellEvent;
|
|
|
|
import com.songoda.ultimatetimber.tree.ITreeBlock;
|
|
|
|
import org.bukkit.Bukkit;
|
|
|
|
import org.bukkit.Location;
|
|
|
|
import org.bukkit.block.Block;
|
|
|
|
import org.bukkit.block.BlockState;
|
|
|
|
import org.bukkit.event.EventHandler;
|
|
|
|
import org.bukkit.event.EventPriority;
|
|
|
|
import org.bukkit.event.Listener;
|
|
|
|
import org.bukkit.event.block.BlockBreakEvent;
|
|
|
|
import org.bukkit.event.block.BlockPlaceEvent;
|
|
|
|
import org.bukkit.event.block.LeavesDecayEvent;
|
|
|
|
import org.bukkit.event.world.StructureGrowEvent;
|
|
|
|
|
2019-04-30 08:18:45 +02:00
|
|
|
import java.util.Collections;
|
|
|
|
import java.util.LinkedHashMap;
|
|
|
|
import java.util.Map;
|
2019-04-29 02:58:38 +02:00
|
|
|
import java.util.Set;
|
|
|
|
|
|
|
|
public class PlacedBlockManager extends Manager implements Listener {
|
2019-04-30 08:18:45 +02:00
|
|
|
private Set<Location> placedBlocks;
|
2019-04-29 02:58:38 +02:00
|
|
|
private boolean ignorePlacedBlocks;
|
|
|
|
private int maxPlacedBlockMemorySize;
|
|
|
|
|
2023-06-29 14:31:22 +02:00
|
|
|
public PlacedBlockManager(UltimateTimber plugin) {
|
|
|
|
super(plugin);
|
|
|
|
Bukkit.getPluginManager().registerEvents(this, plugin);
|
2019-04-29 02:58:38 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void reload() {
|
|
|
|
this.ignorePlacedBlocks = ConfigurationManager.Setting.IGNORE_PLACED_BLOCKS.getBoolean();
|
|
|
|
this.maxPlacedBlockMemorySize = ConfigurationManager.Setting.IGNORE_PLACED_BLOCKS_MEMORY_SIZE.getInt();
|
2019-04-30 08:18:45 +02:00
|
|
|
|
|
|
|
// Ensures the oldest entry is removed if it exceeds the limit
|
|
|
|
this.placedBlocks = Collections.newSetFromMap(new LinkedHashMap<Location, Boolean>() {
|
|
|
|
@Override
|
|
|
|
protected boolean removeEldestEntry(Map.Entry<Location, Boolean> eldest) {
|
|
|
|
return this.size() > PlacedBlockManager.this.maxPlacedBlockMemorySize;
|
|
|
|
}
|
|
|
|
});
|
2019-04-29 02:58:38 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void disable() {
|
|
|
|
this.placedBlocks.clear();
|
|
|
|
}
|
|
|
|
|
|
|
|
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
|
|
|
public void onBlockPlaced(BlockPlaceEvent event) {
|
2023-06-29 14:31:22 +02:00
|
|
|
if (!this.ignorePlacedBlocks) {
|
2019-04-29 02:58:38 +02:00
|
|
|
return;
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
|
2019-05-03 03:27:08 +02:00
|
|
|
// Ignore stripping logs
|
2023-06-29 14:38:33 +02:00
|
|
|
if (event.getBlockPlaced().getType().name().contains("STRIPPED") && !CompatibleMaterial.isAir(CompatibleMaterial.getMaterial(event.getBlockReplacedState().getType()).get())) {
|
2019-05-03 03:27:08 +02:00
|
|
|
return;
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-05-03 03:27:08 +02:00
|
|
|
|
2019-04-29 02:58:38 +02:00
|
|
|
this.internalProtect(event.getBlock(), true);
|
|
|
|
}
|
|
|
|
|
|
|
|
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
|
|
|
public void onBlockBreak(BlockBreakEvent event) {
|
2023-06-29 14:31:22 +02:00
|
|
|
if (!this.ignorePlacedBlocks) {
|
2019-04-29 02:58:38 +02:00
|
|
|
return;
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
|
|
|
|
this.internalProtect(event.getBlock(), false);
|
|
|
|
}
|
|
|
|
|
|
|
|
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
|
|
|
public void onLeafDecay(LeavesDecayEvent event) {
|
2023-06-29 14:31:22 +02:00
|
|
|
if (!this.ignorePlacedBlocks) {
|
2019-04-29 02:58:38 +02:00
|
|
|
return;
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
|
|
|
|
this.internalProtect(event.getBlock(), false);
|
|
|
|
}
|
|
|
|
|
|
|
|
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
|
|
|
public void onStructureGrow(StructureGrowEvent event) {
|
2023-06-29 14:31:22 +02:00
|
|
|
if (!this.ignorePlacedBlocks) {
|
2019-04-29 02:58:38 +02:00
|
|
|
return;
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
|
2023-06-29 14:31:22 +02:00
|
|
|
for (BlockState blockState : event.getBlocks()) {
|
2019-04-29 02:58:38 +02:00
|
|
|
this.internalProtect(blockState.getBlock(), false);
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
|
|
|
|
public void onTreeFell(TreeFellEvent event) {
|
2023-06-29 14:31:22 +02:00
|
|
|
if (!this.ignorePlacedBlocks) {
|
2019-04-29 02:58:38 +02:00
|
|
|
return;
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
|
2023-06-29 14:31:22 +02:00
|
|
|
for (ITreeBlock<Block> treeBlock : event.getDetectedTree().getDetectedTreeBlocks().getAllTreeBlocks()) {
|
2019-04-29 02:58:38 +02:00
|
|
|
this.internalProtect(treeBlock.getBlock(), false);
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Handles when a block is placed/broken
|
|
|
|
*/
|
|
|
|
private void internalProtect(Block block, boolean isPlaced) {
|
|
|
|
if (isPlaced) {
|
2023-06-29 14:31:22 +02:00
|
|
|
if (this.isBlockPlaced(block)) {
|
2019-04-29 02:58:38 +02:00
|
|
|
return;
|
2023-06-29 14:31:22 +02:00
|
|
|
}
|
2019-04-29 02:58:38 +02:00
|
|
|
|
|
|
|
this.placedBlocks.add(block.getLocation());
|
|
|
|
} else {
|
|
|
|
this.placedBlocks.remove(block.getLocation());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Gets if a block is placed
|
|
|
|
*
|
|
|
|
* @param block The Block to check
|
|
|
|
* @return True if the block is placed, otherwise false
|
|
|
|
*/
|
|
|
|
public boolean isBlockPlaced(Block block) {
|
|
|
|
return this.placedBlocks.contains(block.getLocation());
|
|
|
|
}
|
|
|
|
}
|