1 task instead of task per ChunkWork

This commit is contained in:
YouHaveTrouble
2021-07-23 01:04:34 +02:00
parent 6ee58e3199
commit a93fe5f635
5 changed files with 32 additions and 25 deletions
@@ -13,7 +13,7 @@ public class BEPlayer {
private static final HashMap<UUID, BEPlayer> playerHashMap = new HashMap<>(); private static final HashMap<UUID, BEPlayer> playerHashMap = new HashMap<>();
private BoundingBox selection; private BoundingBox selection;
private Location selectionPoint1, selectionPoint2; private Location selectionPoint1, selectionPoint2;
private World selectionWorld; private UUID selectionWorldUuid;
public BoundingBox getSelection() { public BoundingBox getSelection() {
return selection; return selection;
@@ -32,7 +32,7 @@ public class BEPlayer {
selection = null; selection = null;
return; return;
} }
selectionWorld = selectionPoint1.getWorld(); selectionWorldUuid = selectionPoint1.getWorld().getUID();
selection = BoundingBox.of(selectionPoint1, selectionPoint2); selection = BoundingBox.of(selectionPoint1, selectionPoint2);
// bounding boxes are dumb. // bounding boxes are dumb.
selection.expand(0.5, 0.5, 0.5); selection.expand(0.5, 0.5, 0.5);
@@ -54,8 +54,9 @@ public class BEPlayer {
/** /**
* @return World withinn which the selection is made. * @return World withinn which the selection is made.
*/ */
public World getSelectionWorld() { public UUID getSelectionWorld() {
return selectionWorld; if (selection == null) return null;
return selectionPoint1.getWorld().getUID();
} }
/** /**
@@ -1,14 +1,13 @@
package me.youhavetrouble.blockedit; package me.youhavetrouble.blockedit;
import me.youhavetrouble.blockedit.util.ChunkWork; import me.youhavetrouble.blockedit.util.ChunkWork;
import org.bukkit.World;
import org.bukkit.util.BoundingBox; import org.bukkit.util.BoundingBox;
import java.util.HashSet; import java.util.HashSet;
public class WorkSplitter { public class WorkSplitter {
public static HashSet<ChunkWork> getOperatedOnChunks(BoundingBox boundingBox, World world) { public static HashSet<ChunkWork> getOperatedOnChunks(BoundingBox boundingBox) {
HashSet<ChunkWork> chunks = new HashSet<>(); HashSet<ChunkWork> chunks = new HashSet<>();
ChunkWork chunkWork = new ChunkWork(0,0); ChunkWork chunkWork = new ChunkWork(0,0);
// TODO Find a way to get chunks in the selection more efficiently // TODO Find a way to get chunks in the selection more efficiently
@@ -38,7 +38,7 @@ public class SetCommand implements TabExecutor {
player.sendMessage(Component.text("You need to select 2 points to do this")); player.sendMessage(Component.text("You need to select 2 points to do this"));
return true; return true;
} }
new SetOperation(WorkSplitter.getOperatedOnChunks(selection, bePlayer.getSelectionWorld()), bePlayer.getSelectionWorld(), selection, blockData); new SetOperation(WorkSplitter.getOperatedOnChunks(selection), bePlayer, blockData, 1);
} }
return true; return true;
} }
@@ -1,5 +1,6 @@
package me.youhavetrouble.blockedit.operations; package me.youhavetrouble.blockedit.operations;
import me.youhavetrouble.blockedit.BEPlayer;
import me.youhavetrouble.blockedit.BlockEdit; import me.youhavetrouble.blockedit.BlockEdit;
import me.youhavetrouble.blockedit.util.ChunkWork; import me.youhavetrouble.blockedit.util.ChunkWork;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
@@ -7,24 +8,40 @@ import org.bukkit.World;
import org.bukkit.block.Block; import org.bukkit.block.Block;
import org.bukkit.block.data.BlockData; import org.bukkit.block.data.BlockData;
import org.bukkit.util.BoundingBox; import org.bukkit.util.BoundingBox;
import java.util.ArrayList;
import java.util.HashSet; import java.util.HashSet;
import java.util.List;
import java.util.UUID;
import java.util.concurrent.atomic.AtomicInteger;
public class SetOperation { public class SetOperation {
private final BoundingBox selection; private final BoundingBox selection;
private final BlockData blockToSet; private final BlockData blockToSet;
private final List<ChunkWork> chunkwork = new ArrayList<>();
public SetOperation(HashSet<ChunkWork> chunkWorks, World world, BoundingBox selection, BlockData blockToSet) { public SetOperation(HashSet<ChunkWork> chunkWorks, BEPlayer bePlayer, BlockData blockToSet, int chunksPerTick) {
this.selection = selection; this.selection = bePlayer.getSelection();
this.blockToSet = blockToSet; this.blockToSet = blockToSet;
int stagger = 0; this.chunkwork.addAll(chunkWorks);
for (ChunkWork chunkWork : chunkWorks) { AtomicInteger element = new AtomicInteger(chunkwork.size()-1);
Bukkit.getScheduler().runTaskLater(BlockEdit.getPlugin(), () -> processChunkWork(chunkWork, world), stagger++);
Bukkit.getScheduler().runTaskTimer(BlockEdit.getPlugin(), (task) -> {
if (element.get() < 0) {
task.cancel();
return;
} }
for (int i = 0; i<= chunksPerTick; i++) {
processChunkWork(chunkwork.get(element.getAndDecrement()), bePlayer.getSelectionWorld());
}
}, 0, 1);
} }
private void processChunkWork(ChunkWork chunkWork, World world) { private void processChunkWork(ChunkWork chunkWork, UUID worldUuid) {
World world = Bukkit.getWorld(worldUuid);
if (world == null) return;
chunkWork.getChunkAsync(world).thenAccept(chunk -> { chunkWork.getChunkAsync(world).thenAccept(chunk -> {
// skip y levels that are not in the selection // skip y levels that are not in the selection
for (int y = (int) selection.getMinY(); y <= selection.getMaxY(); y++) { for (int y = (int) selection.getMinY(); y <= selection.getMaxY(); y++) {
@@ -2,7 +2,6 @@ package me.youhavetrouble.blockedit.util;
import org.bukkit.Chunk; import org.bukkit.Chunk;
import org.bukkit.World; import org.bukkit.World;
import org.bukkit.util.BoundingBox;
import java.util.concurrent.CompletableFuture; import java.util.concurrent.CompletableFuture;
@@ -14,19 +13,10 @@ public class ChunkWork {
setCoords(x,z); setCoords(x,z);
} }
public BoundingBox getWorkspace(BoundingBox selection, World world) {
// TODO make it return shared space of getChunkBox and selection to cull some of the blocks from iterations
return getChunkBox(world);
}
public CompletableFuture<Chunk> getChunkAsync(World world) { public CompletableFuture<Chunk> getChunkAsync(World world) {
return world.getChunkAtAsync(x,z, true); return world.getChunkAtAsync(x,z, true);
} }
private BoundingBox getChunkBox(World world) {
return new BoundingBox(x*16, world.getMinHeight(), z*16, (x+1)*16, world.getMaxHeight(), (z+1)*16);
}
public int getX() { public int getX() {
return x; return x;
} }