9
0
mirror of https://github.com/VolmitSoftware/Iris.git synced 2025-12-19 15:09:18 +00:00

improve regen speed

This commit is contained in:
Julian Krings
2025-10-06 14:12:01 +02:00
parent 22118de9e9
commit 317848692e
2 changed files with 100 additions and 23 deletions

View File

@@ -58,7 +58,7 @@ import com.volmit.iris.util.plugin.VolmitSender;
import com.volmit.iris.util.scheduling.J; import com.volmit.iris.util.scheduling.J;
import com.volmit.iris.util.scheduling.O; import com.volmit.iris.util.scheduling.O;
import com.volmit.iris.util.scheduling.PrecisionStopwatch; import com.volmit.iris.util.scheduling.PrecisionStopwatch;
import com.volmit.iris.util.scheduling.jobs.ParallelQueueJob; import com.volmit.iris.util.scheduling.jobs.ParallelRadiusJob;
import io.papermc.lib.PaperLib; import io.papermc.lib.PaperLib;
import org.bukkit.*; import org.bukkit.*;
import org.bukkit.event.inventory.InventoryType; import org.bukkit.event.inventory.InventoryType;
@@ -181,49 +181,40 @@ public class CommandStudio implements DecreeExecutor {
int rad = engine.getMantle().getRadius(); int rad = engine.getMantle().getRadius();
var mantle = engine.getMantle().getMantle(); var mantle = engine.getMantle().getMantle();
var chunkMap = new KMap<Position2, MantleChunk>(); var chunkMap = new KMap<Position2, MantleChunk>();
ParallelQueueJob<Position2> prep = new ParallelQueueJob<>() { ParallelRadiusJob prep = new ParallelRadiusJob(Integer.MAX_VALUE) {
@Override @Override
public void execute(Position2 pos) { protected void execute(int rX, int rZ) {
var cpos = pos.add(x, z); if (Math.abs(rX) <= radius && Math.abs(rZ) <= radius) {
if (Math.abs(pos.getX()) <= radius && Math.abs(pos.getZ()) <= radius) { mantle.deleteChunk(rX + x, rZ + z);
mantle.deleteChunk(cpos.getX(), cpos.getZ());
return; return;
} }
chunkMap.put(cpos, mantle.getChunk(cpos.getX(), cpos.getZ())); rX += x;
mantle.deleteChunk(cpos.getX(), cpos.getZ()); rZ += z;
chunkMap.put(new Position2(rX, rZ), mantle.getChunk(rX, rZ));
mantle.deleteChunk(rX, rZ);
} }
@Override @Override
public String getName() { public String getName() {
return "Preparing Mantle"; return "Preparing Mantle";
} }
}; }.retarget(radius + rad, 0, 0);
for (int xx = -(radius + rad); xx <= radius + rad; xx++) {
for (int zz = -(radius + rad); zz <= radius + rad; zz++) {
prep.queue(new Position2(xx, zz));
}
}
CountDownLatch pLatch = new CountDownLatch(1); CountDownLatch pLatch = new CountDownLatch(1);
prep.execute(sender(), pLatch::countDown); prep.execute(sender(), pLatch::countDown);
pLatch.await(); pLatch.await();
ParallelQueueJob<Position2> job = new ParallelQueueJob<>() { ParallelRadiusJob job = new ParallelRadiusJob(Integer.MAX_VALUE) {
@Override @Override
public void execute(Position2 p) { protected void execute(int x, int z) {
plat.injectChunkReplacement(world, p.getX(), p.getZ(), executor); plat.injectChunkReplacement(world, x, z, executor);
} }
@Override @Override
public String getName() { public String getName() {
return "Regenerating"; return "Regenerating";
} }
}; }.retarget(radius, x, z);
for (int i = -radius; i <= radius; i++) {
for (int j = -radius; j <= radius; j++) {
job.queue(new Position2(i + x, j + z));
}
}
CountDownLatch latch = new CountDownLatch(1); CountDownLatch latch = new CountDownLatch(1);
job.execute(sender(), latch::countDown); job.execute(sender(), latch::countDown);
latch.await(); latch.await();

View File

@@ -0,0 +1,86 @@
package com.volmit.iris.util.scheduling.jobs;
import com.volmit.iris.util.math.Spiraler;
import com.volmit.iris.util.parallel.MultiBurst;
import lombok.SneakyThrows;
import lombok.Synchronized;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Semaphore;
import java.util.concurrent.atomic.AtomicInteger;
public abstract class ParallelRadiusJob implements Job {
private final ExecutorService service;
private final AtomicInteger completed;
private volatile int radiusX, radiusZ;
private volatile int offsetX, offsetZ;
private volatile int total;
private final Semaphore lock;
private final int lockSize;
public ParallelRadiusJob(int concurrent) {
this(concurrent, MultiBurst.burst);
}
public ParallelRadiusJob(int concurrent, ExecutorService service) {
this.service = service;
completed = new AtomicInteger(0);
lock = new Semaphore(concurrent);
lockSize = concurrent;
}
public ParallelRadiusJob retarget(int radius, int offsetX, int offsetZ) {
return retarget(radius, radius, offsetX, offsetZ);
}
@Synchronized
public ParallelRadiusJob retarget(int radiusX, int radiusZ, int offsetX, int offsetZ) {
completed.set(0);
this.radiusX = radiusX;
this.radiusZ = radiusZ;
this.offsetX = offsetX;
this.offsetZ = offsetZ;
total = (radiusX * 2 + 1) * (radiusZ * 2 + 1);
return this;
}
@Override
@SneakyThrows
@Synchronized
public void execute() {
new Spiraler(radiusX * 2 + 3, radiusZ * 2 + 3, this::submit).drain();
lock.acquire(lockSize);
lock.release(lockSize);
}
@SneakyThrows
private void submit(int x, int z) {
if (Math.abs(x) > radiusX || Math.abs(z) > radiusZ) return;
lock.acquire();
service.submit(() -> {
try {
execute(x + offsetX, z + offsetZ);
} finally {
completeWork();
}
});
}
protected abstract void execute(int x, int z);
@Override
public void completeWork() {
completed.incrementAndGet();
lock.release();
}
@Override
public int getTotalWork() {
return total;
}
@Override
public int getWorkCompleted() {
return completed.get();
}
}