mirror of
https://github.com/VolmitSoftware/Iris.git
synced 2026-06-18 23:01:07 +00:00
add kts hook for chunk updates
This commit is contained in:
@@ -1,9 +1,12 @@
|
|||||||
package com.volmit.iris.core.scripting.environment;
|
package com.volmit.iris.core.scripting.environment;
|
||||||
|
|
||||||
import com.volmit.iris.core.loader.IrisRegistrant;
|
import com.volmit.iris.core.loader.IrisRegistrant;
|
||||||
|
import com.volmit.iris.core.scripting.func.UpdateExecutor;
|
||||||
import com.volmit.iris.core.scripting.kotlin.environment.IrisExecutionEnvironment;
|
import com.volmit.iris.core.scripting.kotlin.environment.IrisExecutionEnvironment;
|
||||||
import com.volmit.iris.engine.framework.Engine;
|
import com.volmit.iris.engine.framework.Engine;
|
||||||
|
import com.volmit.iris.util.mantle.MantleChunk;
|
||||||
import lombok.NonNull;
|
import lombok.NonNull;
|
||||||
|
import org.bukkit.Chunk;
|
||||||
import org.bukkit.Location;
|
import org.bukkit.Location;
|
||||||
import org.bukkit.entity.Entity;
|
import org.bukkit.entity.Entity;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
@@ -22,4 +25,6 @@ public interface EngineEnvironment extends PackEnvironment {
|
|||||||
void postSpawnMob(@NonNull String script, @NonNull Location location, @NonNull Entity mob);
|
void postSpawnMob(@NonNull String script, @NonNull Location location, @NonNull Entity mob);
|
||||||
|
|
||||||
void preprocessObject(@NonNull String script, @NonNull IrisRegistrant object);
|
void preprocessObject(@NonNull String script, @NonNull IrisRegistrant object);
|
||||||
|
|
||||||
|
void updateChunk(@NonNull String script, @NonNull MantleChunk mantleChunk, @NonNull Chunk chunk, @NonNull UpdateExecutor executor);
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
package com.volmit.iris.core.scripting.func;
|
||||||
|
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
|
@FunctionalInterface
|
||||||
|
public interface UpdateExecutor {
|
||||||
|
|
||||||
|
@NotNull Runnable wrap(int delay, @NotNull Runnable runnable);
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
default Runnable wrap(@NotNull Runnable runnable) {
|
||||||
|
return wrap(1, runnable);
|
||||||
|
}
|
||||||
|
|
||||||
|
default void execute(@NotNull Runnable runnable) {
|
||||||
|
execute(1, runnable);
|
||||||
|
}
|
||||||
|
|
||||||
|
default void execute(int delay, @NotNull Runnable runnable) {
|
||||||
|
wrap(delay, runnable).run();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -294,7 +294,7 @@ public interface Engine extends DataProvider, Fallible, LootProvider, BlockUpdat
|
|||||||
|
|
||||||
var chunk = mantle.getChunk(c).use();
|
var chunk = mantle.getChunk(c).use();
|
||||||
try {
|
try {
|
||||||
Semaphore semaphore = new Semaphore(3);
|
Semaphore semaphore = new Semaphore(1024);
|
||||||
chunk.raiseFlag(MantleFlag.ETCHED, () -> {
|
chunk.raiseFlag(MantleFlag.ETCHED, () -> {
|
||||||
chunk.raiseFlagUnchecked(MantleFlag.TILE, run(semaphore, () -> {
|
chunk.raiseFlagUnchecked(MantleFlag.TILE, run(semaphore, () -> {
|
||||||
chunk.iterate(TileWrapper.class, (x, y, z, v) -> {
|
chunk.iterate(TileWrapper.class, (x, y, z, v) -> {
|
||||||
@@ -355,8 +355,18 @@ public interface Engine extends DataProvider, Fallible, LootProvider, BlockUpdat
|
|||||||
}, RNG.r.i(1, 20))); //Why is there a random delay here?
|
}, RNG.r.i(1, 20))); //Why is there a random delay here?
|
||||||
});
|
});
|
||||||
|
|
||||||
|
chunk.raiseFlagUnchecked(MantleFlag.SCRIPT, () -> {
|
||||||
|
var scripts = getDimension().getChunkUpdateScripts();
|
||||||
|
if (scripts == null || scripts.isEmpty())
|
||||||
|
return;
|
||||||
|
|
||||||
|
for (var script : scripts) {
|
||||||
|
getExecution().updateChunk(script, chunk, c, (delay, task) -> run(semaphore, task, delay));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
try {
|
try {
|
||||||
semaphore.acquire(3);
|
semaphore.acquire(1024);
|
||||||
} catch (InterruptedException ignored) {}
|
} catch (InterruptedException ignored) {}
|
||||||
} finally {
|
} finally {
|
||||||
chunk.release();
|
chunk.release();
|
||||||
@@ -365,8 +375,11 @@ public interface Engine extends DataProvider, Fallible, LootProvider, BlockUpdat
|
|||||||
|
|
||||||
private static Runnable run(Semaphore semaphore, Runnable runnable, int delay) {
|
private static Runnable run(Semaphore semaphore, Runnable runnable, int delay) {
|
||||||
return () -> {
|
return () -> {
|
||||||
if (!semaphore.tryAcquire())
|
try {
|
||||||
return;
|
semaphore.acquire();
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
|
||||||
J.s(() -> {
|
J.s(() -> {
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -257,6 +257,10 @@ public class IrisDimension extends IrisRegistrant {
|
|||||||
@RegistryListResource(IrisScript.class)
|
@RegistryListResource(IrisScript.class)
|
||||||
@ArrayType(type = String.class, min = 1)
|
@ArrayType(type = String.class, min = 1)
|
||||||
private KList<String> dataScripts = new KList<>();
|
private KList<String> dataScripts = new KList<>();
|
||||||
|
@Desc("A list of scripts executed on chunk update")
|
||||||
|
@RegistryListResource(IrisScript.class)
|
||||||
|
@ArrayType(type = String.class, min = 1)
|
||||||
|
private KList<String> chunkUpdateScripts = new KList<>();
|
||||||
@Desc("Use legacy rarity instead of modern one\nWARNING: Changing this may break expressions and image maps")
|
@Desc("Use legacy rarity instead of modern one\nWARNING: Changing this may break expressions and image maps")
|
||||||
private boolean legacyRarity = true;
|
private boolean legacyRarity = true;
|
||||||
|
|
||||||
|
|||||||
@@ -176,14 +176,26 @@ public class MantleChunk {
|
|||||||
if (guard != null && isFlagged(guard)) return;
|
if (guard != null && isFlagged(guard)) return;
|
||||||
synchronized (flagLocks[flag.ordinal()]) {
|
synchronized (flagLocks[flag.ordinal()]) {
|
||||||
if (flags.compareAndSet(flag.ordinal(), false, true)) {
|
if (flags.compareAndSet(flag.ordinal(), false, true)) {
|
||||||
r.run();
|
try {
|
||||||
|
r.run();
|
||||||
|
} catch (RuntimeException | Error e) {
|
||||||
|
flags.set(flag.ordinal(), false);
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void raiseFlagUnchecked(MantleFlag flag, Runnable r) {
|
public void raiseFlagUnchecked(MantleFlag flag, Runnable r) {
|
||||||
if (closed.get()) throw new IllegalStateException("Chunk is closed!");
|
if (closed.get()) throw new IllegalStateException("Chunk is closed!");
|
||||||
if (flags.compareAndSet(flag.ordinal(), false, true)) r.run();
|
if (flags.compareAndSet(flag.ordinal(), false, true)) {
|
||||||
|
try {
|
||||||
|
r.run();
|
||||||
|
} catch (RuntimeException | Error e) {
|
||||||
|
flags.set(flag.ordinal(), false);
|
||||||
|
throw e;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isFlagged(MantleFlag flag) {
|
public boolean isFlagged(MantleFlag flag) {
|
||||||
|
|||||||
@@ -40,6 +40,7 @@ public sealed interface MantleFlag permits CustomFlag, ReservedFlag {
|
|||||||
MantleFlag CUSTOM = ReservedFlag.CUSTOM;
|
MantleFlag CUSTOM = ReservedFlag.CUSTOM;
|
||||||
MantleFlag DISCOVERED = ReservedFlag.DISCOVERED;
|
MantleFlag DISCOVERED = ReservedFlag.DISCOVERED;
|
||||||
MantleFlag CUSTOM_ACTIVE = ReservedFlag.CUSTOM_ACTIVE;
|
MantleFlag CUSTOM_ACTIVE = ReservedFlag.CUSTOM_ACTIVE;
|
||||||
|
MantleFlag SCRIPT = ReservedFlag.SCRIPT;
|
||||||
|
|
||||||
int RESERVED_FLAGS = ReservedFlag.values().length;
|
int RESERVED_FLAGS = ReservedFlag.values().length;
|
||||||
|
|
||||||
|
|||||||
@@ -16,7 +16,8 @@ public enum ReservedFlag implements MantleFlag {
|
|||||||
TILE,
|
TILE,
|
||||||
CUSTOM,
|
CUSTOM,
|
||||||
DISCOVERED,
|
DISCOVERED,
|
||||||
CUSTOM_ACTIVE;
|
CUSTOM_ACTIVE,
|
||||||
|
SCRIPT;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isCustom() {
|
public boolean isCustom() {
|
||||||
|
|||||||
@@ -0,0 +1,21 @@
|
|||||||
|
package com.volmit.iris.core.scripting.kotlin.base
|
||||||
|
|
||||||
|
import com.volmit.iris.core.scripting.func.UpdateExecutor
|
||||||
|
import com.volmit.iris.util.mantle.MantleChunk
|
||||||
|
import org.bukkit.Chunk
|
||||||
|
import kotlin.script.experimental.annotations.KotlinScript
|
||||||
|
import kotlin.script.experimental.api.ScriptCompilationConfiguration
|
||||||
|
import kotlin.script.experimental.api.providedProperties
|
||||||
|
|
||||||
|
@KotlinScript(fileExtension = "update.kts", compilationConfiguration = ChunkUpdateScriptDefinition::class)
|
||||||
|
abstract class ChunkUpdateScript
|
||||||
|
|
||||||
|
object ChunkUpdateScriptDefinition : ScriptCompilationConfiguration(listOf(EngineScriptDefinition), {
|
||||||
|
providedProperties(
|
||||||
|
"mantleChunk" to MantleChunk::class,
|
||||||
|
"chunk" to Chunk::class,
|
||||||
|
"executor" to UpdateExecutor::class
|
||||||
|
)
|
||||||
|
}) {
|
||||||
|
private fun readResolve(): Any = MobSpawningScriptDefinition
|
||||||
|
}
|
||||||
+7
@@ -3,11 +3,15 @@ package com.volmit.iris.core.scripting.kotlin.environment
|
|||||||
import com.volmit.iris.core.loader.IrisRegistrant
|
import com.volmit.iris.core.loader.IrisRegistrant
|
||||||
import com.volmit.iris.core.scripting.environment.EngineEnvironment
|
import com.volmit.iris.core.scripting.environment.EngineEnvironment
|
||||||
import com.volmit.iris.core.scripting.func.BiomeLookup
|
import com.volmit.iris.core.scripting.func.BiomeLookup
|
||||||
|
import com.volmit.iris.core.scripting.func.UpdateExecutor
|
||||||
|
import com.volmit.iris.core.scripting.kotlin.base.ChunkUpdateScript
|
||||||
import com.volmit.iris.core.scripting.kotlin.base.EngineScript
|
import com.volmit.iris.core.scripting.kotlin.base.EngineScript
|
||||||
import com.volmit.iris.core.scripting.kotlin.base.MobSpawningScript
|
import com.volmit.iris.core.scripting.kotlin.base.MobSpawningScript
|
||||||
import com.volmit.iris.core.scripting.kotlin.base.PostMobSpawningScript
|
import com.volmit.iris.core.scripting.kotlin.base.PostMobSpawningScript
|
||||||
import com.volmit.iris.core.scripting.kotlin.base.PreprocessorScript
|
import com.volmit.iris.core.scripting.kotlin.base.PreprocessorScript
|
||||||
import com.volmit.iris.engine.framework.Engine
|
import com.volmit.iris.engine.framework.Engine
|
||||||
|
import com.volmit.iris.util.mantle.MantleChunk
|
||||||
|
import org.bukkit.Chunk
|
||||||
import org.bukkit.Location
|
import org.bukkit.Location
|
||||||
import org.bukkit.entity.Entity
|
import org.bukkit.entity.Entity
|
||||||
|
|
||||||
@@ -31,6 +35,9 @@ data class IrisExecutionEnvironment(
|
|||||||
override fun preprocessObject(script: String, `object`: IrisRegistrant) =
|
override fun preprocessObject(script: String, `object`: IrisRegistrant) =
|
||||||
execute(script, PreprocessorScript::class.java, engine.parameters("object" to `object`))
|
execute(script, PreprocessorScript::class.java, engine.parameters("object" to `object`))
|
||||||
|
|
||||||
|
override fun updateChunk(script: String, mantleChunk: MantleChunk, chunk: Chunk, executor: UpdateExecutor) =
|
||||||
|
execute(script, ChunkUpdateScript::class.java, engine.parameters("mantleChunk" to mantleChunk, "chunk" to chunk, "executor" to executor))
|
||||||
|
|
||||||
private fun Engine.parameters(vararg values: Pair<String, Any?>): Map<String, Any?> {
|
private fun Engine.parameters(vararg values: Pair<String, Any?>): Map<String, Any?> {
|
||||||
return mapOf(
|
return mapOf(
|
||||||
"data" to data,
|
"data" to data,
|
||||||
|
|||||||
Reference in New Issue
Block a user