From bdbf30d328ccc4a3a1ca6b8885955a651cd7b17f Mon Sep 17 00:00:00 2001 From: bigguy345 Date: Sun, 29 Jun 2025 21:06:15 +0300 Subject: [PATCH] Another ActionThread overhaul --- .../npcs/controllers/data/action/Action.java | 28 +++++++------ .../controllers/data/action/ActionThread.java | 41 +++++++++---------- 2 files changed, 36 insertions(+), 33 deletions(-) diff --git a/src/main/java/noppes/npcs/controllers/data/action/Action.java b/src/main/java/noppes/npcs/controllers/data/action/Action.java index e402fea58..770487714 100644 --- a/src/main/java/noppes/npcs/controllers/data/action/Action.java +++ b/src/main/java/noppes/npcs/controllers/data/action/Action.java @@ -67,23 +67,27 @@ public class Action implements IAction { startAfterTicks--; return; } - if (maxDuration != -1 && duration >= maxDuration) { + if (maxDuration > -1 && duration >= maxDuration) { markDone(); return; } if (ticksExisted % updateEveryXTick == 0 && task != null) { if (isThreaded) - actionThread.run(); - else { - try { - task.accept(this); - count++; - } catch (Throwable t) { - System.err.println("Scripted action '" + name + "' threw an exception:"); - t.printStackTrace(); - markDone(); - } - } + actionThread.execute(this::executeTask); + else + executeTask(); + } + duration++; + } + + protected void executeTask() { + try { + task.accept(this); + count++; + } catch (Throwable t) { + System.err.println("IAction '" + name + "' threw an exception:"); + t.printStackTrace(); + markDone(); } duration++; } diff --git a/src/main/java/noppes/npcs/controllers/data/action/ActionThread.java b/src/main/java/noppes/npcs/controllers/data/action/ActionThread.java index e00607e76..8c381aa4d 100644 --- a/src/main/java/noppes/npcs/controllers/data/action/ActionThread.java +++ b/src/main/java/noppes/npcs/controllers/data/action/ActionThread.java @@ -1,24 +1,24 @@ package noppes.npcs.controllers.data.action; +import java.util.Queue; +import java.util.concurrent.ConcurrentLinkedQueue; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.Future; +import java.util.concurrent.atomic.AtomicReference; import java.util.function.Supplier; public class ActionThread { - private final Action action; - private final Object lock = new Object(); private Thread thread; ExecutorService executor; - private Future currentExecution; + private final Queue> runningTasks = new ConcurrentLinkedQueue<>(); + private volatile boolean threadPaused, threadSleeping; private Supplier pauseUntil; public ActionThread(Action action) { - this.action = action; - executor = Executors.newSingleThreadExecutor(r -> { thread = new Thread(r); thread.setName(String.format("ActionThread (%s)", action.getName())); @@ -27,8 +27,10 @@ public class ActionThread { } public void stop() { - if (isThreadRunning()) - currentExecution.cancel(true); + runningTasks.forEach((task) -> { + if (!task.isDone()) + task.cancel(true); + }); executor.shutdown(); } @@ -79,8 +81,8 @@ public class ActionThread { lock.notify(); } - if (threadSleeping && currentExecution != null) - currentExecution.cancel(true); + if (threadSleeping) + thread.interrupt(); } } @@ -93,27 +95,24 @@ public class ActionThread { } public boolean isThreadRunning() { - return currentExecution != null && !currentExecution.isDone(); + return runningTasks.stream().anyMatch(task -> !task.isDone()); } - - protected void run() { + protected void execute(Runnable task) { if (threadPaused && pauseUntil != null && pauseUntil.get()) resume(); if (isThreadRunning()) return; - currentExecution = executor.submit(() -> { + final AtomicReference> taskRef = new AtomicReference<>(); + taskRef.set(executor.submit(() -> { + runningTasks.add(taskRef.get()); try { - action.task.accept(action); - action.count++; - } catch (Throwable t) { - System.err.println("Scripted threaded action '" + action.name + "' threw an exception:"); - t.printStackTrace(); - action.markDone(); + task.run(); + } finally { + runningTasks.remove(taskRef.get()); } - }); - + })); } }