mirror of
https://github.com/PolyhedralDev/Terra.git
synced 2026-06-17 06:11:24 +00:00
implement StateFunction
This commit is contained in:
@@ -16,4 +16,8 @@ public interface BlockState extends Handle {
|
|||||||
BlockData getBlockData();
|
BlockData getBlockData();
|
||||||
|
|
||||||
boolean update(boolean applyPhysics);
|
boolean update(boolean applyPhysics);
|
||||||
|
|
||||||
|
default void applyState(String state) {
|
||||||
|
// Do nothing by default.
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,38 @@
|
|||||||
|
package com.dfsek.terra.api.platform.block.state;
|
||||||
|
|
||||||
|
import com.dfsek.terra.api.platform.world.entity.EntityType;
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
|
public interface MobSpawner extends BlockState {
|
||||||
|
EntityType getSpawnedType();
|
||||||
|
|
||||||
|
void setSpawnedType(@NotNull EntityType creatureType);
|
||||||
|
|
||||||
|
int getDelay();
|
||||||
|
|
||||||
|
void setDelay(int delay);
|
||||||
|
|
||||||
|
int getMinSpawnDelay();
|
||||||
|
|
||||||
|
void setMinSpawnDelay(int delay);
|
||||||
|
|
||||||
|
int getMaxSpawnDelay();
|
||||||
|
|
||||||
|
void setMaxSpawnDelay(int delay);
|
||||||
|
|
||||||
|
int getSpawnCount();
|
||||||
|
|
||||||
|
void setSpawnCount(int spawnCount);
|
||||||
|
|
||||||
|
int getMaxNearbyEntities();
|
||||||
|
|
||||||
|
void setMaxNearbyEntities(int maxNearbyEntities);
|
||||||
|
|
||||||
|
int getRequiredPlayerRange();
|
||||||
|
|
||||||
|
void setRequiredPlayerRange(int requiredPlayerRange);
|
||||||
|
|
||||||
|
int getSpawnRange();
|
||||||
|
|
||||||
|
void setSpawnRange(int spawnRange);
|
||||||
|
}
|
||||||
@@ -0,0 +1,94 @@
|
|||||||
|
package com.dfsek.terra.api.platform.block.state;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
public class SerialState {
|
||||||
|
protected final Map<String, Property<?>> properties = new HashMap<>();
|
||||||
|
|
||||||
|
public SerialState() {
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Map<String, String> parse(String props) {
|
||||||
|
String[] sep = props.split(",");
|
||||||
|
Map<String, String> map = new HashMap<>();
|
||||||
|
for(String item : sep) {
|
||||||
|
map.put(item.substring(0, item.indexOf('=')), item.substring(item.indexOf('=') + 1));
|
||||||
|
}
|
||||||
|
return map;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void checkExists(String prop) {
|
||||||
|
if(!properties.containsKey(prop)) throw new IllegalArgumentException("No such property \"" + prop + "\"");
|
||||||
|
}
|
||||||
|
|
||||||
|
private void checkType(Class<?> clazz, Object o, String id) {
|
||||||
|
if(!clazz.isInstance(o))
|
||||||
|
throw new IllegalArgumentException("Invalid data for property " + id + ": " + o);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setProperty(String id, Object value) {
|
||||||
|
checkExists(id);
|
||||||
|
Property<?> prop = properties.get(id);
|
||||||
|
checkType(prop.getValueClass(), value, id);
|
||||||
|
prop.setValue(value);
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getInteger(String id) {
|
||||||
|
checkExists(id);
|
||||||
|
Property<?> prop = properties.get(id);
|
||||||
|
checkType(Integer.class, prop.getValue(), id);
|
||||||
|
return (Integer) prop.getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getString(String id) {
|
||||||
|
checkExists(id);
|
||||||
|
Property<?> prop = properties.get(id);
|
||||||
|
checkType(String.class, prop.getValue(), id);
|
||||||
|
return (String) prop.getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
public long getLong(String id) {
|
||||||
|
checkExists(id);
|
||||||
|
Property<?> prop = properties.get(id);
|
||||||
|
checkType(Long.class, prop.getValue(), id);
|
||||||
|
return (Long) prop.getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean getBoolean(String id) {
|
||||||
|
checkExists(id);
|
||||||
|
Property<?> prop = properties.get(id);
|
||||||
|
checkType(Boolean.class, prop.getValue(), id);
|
||||||
|
return (Boolean) prop.getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
public <T> T get(String id, Class<T> clazz) {
|
||||||
|
checkExists(id);
|
||||||
|
Property<?> prop = properties.get(id);
|
||||||
|
checkType(clazz, prop.getValue(), id);
|
||||||
|
return (T) prop.getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected static class Property<T> {
|
||||||
|
private final Class<T> clazz;
|
||||||
|
private Object value;
|
||||||
|
|
||||||
|
public Property(Class<T> clazz) {
|
||||||
|
this.clazz = clazz;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Class<T> getValueClass() {
|
||||||
|
return clazz;
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
public T getValue() {
|
||||||
|
return (T) value;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setValue(Object value) {
|
||||||
|
this.value = value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
package com.dfsek.terra.api.platform.block.state;
|
||||||
|
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
|
public interface Sign extends BlockState {
|
||||||
|
@NotNull String[] getLines();
|
||||||
|
|
||||||
|
@NotNull String getLine(int index) throws IndexOutOfBoundsException;
|
||||||
|
|
||||||
|
void setLine(int index, @NotNull String line) throws IndexOutOfBoundsException;
|
||||||
|
}
|
||||||
@@ -18,6 +18,7 @@ import com.dfsek.terra.api.structures.script.builders.MarkFunctionBuilder;
|
|||||||
import com.dfsek.terra.api.structures.script.builders.PullFunctionBuilder;
|
import com.dfsek.terra.api.structures.script.builders.PullFunctionBuilder;
|
||||||
import com.dfsek.terra.api.structures.script.builders.RandomFunctionBuilder;
|
import com.dfsek.terra.api.structures.script.builders.RandomFunctionBuilder;
|
||||||
import com.dfsek.terra.api.structures.script.builders.RecursionsFunctionBuilder;
|
import com.dfsek.terra.api.structures.script.builders.RecursionsFunctionBuilder;
|
||||||
|
import com.dfsek.terra.api.structures.script.builders.StateFunctionBuilder;
|
||||||
import com.dfsek.terra.api.structures.script.builders.StructureFunctionBuilder;
|
import com.dfsek.terra.api.structures.script.builders.StructureFunctionBuilder;
|
||||||
import com.dfsek.terra.api.structures.script.builders.UnaryNumberFunctionBuilder;
|
import com.dfsek.terra.api.structures.script.builders.UnaryNumberFunctionBuilder;
|
||||||
import com.dfsek.terra.api.structures.script.builders.UnaryStringFunctionBuilder;
|
import com.dfsek.terra.api.structures.script.builders.UnaryStringFunctionBuilder;
|
||||||
@@ -63,6 +64,7 @@ public class StructureScript {
|
|||||||
.registerFunction("entity", new EntityFunctionBuilder(main))
|
.registerFunction("entity", new EntityFunctionBuilder(main))
|
||||||
.registerFunction("getBiome", new BiomeFunctionBuilder(main))
|
.registerFunction("getBiome", new BiomeFunctionBuilder(main))
|
||||||
.registerFunction("getBlock", new CheckBlockFunctionBuilder())
|
.registerFunction("getBlock", new CheckBlockFunctionBuilder())
|
||||||
|
.registerFunction("state", new StateFunctionBuilder(main))
|
||||||
.registerFunction("print", new UnaryStringFunctionBuilder(string -> Debug.info("[" + tempID + "] " + string)))
|
.registerFunction("print", new UnaryStringFunctionBuilder(string -> Debug.info("[" + tempID + "] " + string)))
|
||||||
.registerFunction("abs", new UnaryNumberFunctionBuilder(number -> FastMath.abs(number.doubleValue())))
|
.registerFunction("abs", new UnaryNumberFunctionBuilder(number -> FastMath.abs(number.doubleValue())))
|
||||||
.registerFunction("pow", new BinaryNumberFunctionBuilder((number, number2) -> FastMath.pow(number.doubleValue(), number2.doubleValue())))
|
.registerFunction("pow", new BinaryNumberFunctionBuilder((number, number2) -> FastMath.pow(number.doubleValue(), number2.doubleValue())))
|
||||||
|
|||||||
+44
@@ -0,0 +1,44 @@
|
|||||||
|
package com.dfsek.terra.api.structures.script.builders;
|
||||||
|
|
||||||
|
import com.dfsek.terra.api.platform.TerraPlugin;
|
||||||
|
import com.dfsek.terra.api.structures.parser.exceptions.ParseException;
|
||||||
|
import com.dfsek.terra.api.structures.parser.lang.Returnable;
|
||||||
|
import com.dfsek.terra.api.structures.parser.lang.functions.FunctionBuilder;
|
||||||
|
import com.dfsek.terra.api.structures.script.functions.StateFunction;
|
||||||
|
import com.dfsek.terra.api.structures.tokenizer.Position;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
public class StateFunctionBuilder implements FunctionBuilder<StateFunction> {
|
||||||
|
private final TerraPlugin main;
|
||||||
|
|
||||||
|
public StateFunctionBuilder(TerraPlugin main) {
|
||||||
|
this.main = main;
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
@Override
|
||||||
|
public StateFunction build(List<Returnable<?>> argumentList, Position position) throws ParseException {
|
||||||
|
if(argumentList.size() < 4) throw new ParseException("Expected data", position);
|
||||||
|
return new StateFunction((Returnable<Number>) argumentList.get(0), (Returnable<Number>) argumentList.get(1), (Returnable<Number>) argumentList.get(2), (Returnable<String>) argumentList.get(3), main, position);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int argNumber() {
|
||||||
|
return 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Returnable.ReturnType getArgument(int position) {
|
||||||
|
switch(position) {
|
||||||
|
case 0:
|
||||||
|
case 1:
|
||||||
|
case 2:
|
||||||
|
return Returnable.ReturnType.NUMBER;
|
||||||
|
case 3:
|
||||||
|
return Returnable.ReturnType.STRING;
|
||||||
|
default:
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+49
@@ -0,0 +1,49 @@
|
|||||||
|
package com.dfsek.terra.api.structures.script.functions;
|
||||||
|
|
||||||
|
import com.dfsek.terra.api.math.vector.Vector2;
|
||||||
|
import com.dfsek.terra.api.math.vector.Vector3;
|
||||||
|
import com.dfsek.terra.api.platform.TerraPlugin;
|
||||||
|
import com.dfsek.terra.api.structures.parser.lang.ImplementationArguments;
|
||||||
|
import com.dfsek.terra.api.structures.parser.lang.Returnable;
|
||||||
|
import com.dfsek.terra.api.structures.parser.lang.functions.Function;
|
||||||
|
import com.dfsek.terra.api.structures.script.TerraImplementationArguments;
|
||||||
|
import com.dfsek.terra.api.structures.structure.RotationUtil;
|
||||||
|
import com.dfsek.terra.api.structures.structure.buffer.items.BufferedStateManipulator;
|
||||||
|
import com.dfsek.terra.api.structures.tokenizer.Position;
|
||||||
|
import net.jafama.FastMath;
|
||||||
|
|
||||||
|
public class StateFunction implements Function<Void> {
|
||||||
|
private final Returnable<String> data;
|
||||||
|
private final Returnable<Number> x, y, z;
|
||||||
|
private final Position position;
|
||||||
|
private final TerraPlugin main;
|
||||||
|
|
||||||
|
public StateFunction(Returnable<Number> x, Returnable<Number> y, Returnable<Number> z, Returnable<String> data, TerraPlugin main, Position position) {
|
||||||
|
this.position = position;
|
||||||
|
this.main = main;
|
||||||
|
this.data = data;
|
||||||
|
this.x = x;
|
||||||
|
this.y = y;
|
||||||
|
this.z = z;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Void apply(ImplementationArguments implementationArguments) {
|
||||||
|
TerraImplementationArguments arguments = (TerraImplementationArguments) implementationArguments;
|
||||||
|
Vector2 xz = new Vector2(x.apply(implementationArguments).doubleValue(), z.apply(implementationArguments).doubleValue());
|
||||||
|
RotationUtil.rotateVector(xz, arguments.getRotation());
|
||||||
|
|
||||||
|
arguments.getBuffer().addItem(new BufferedStateManipulator(main, data.apply(implementationArguments)), new Vector3(FastMath.roundToInt(xz.getX()), y.apply(implementationArguments).intValue(), FastMath.roundToInt(xz.getZ())));
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Position getPosition() {
|
||||||
|
return position;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public ReturnType returnType() {
|
||||||
|
return ReturnType.VOID;
|
||||||
|
}
|
||||||
|
}
|
||||||
+26
@@ -0,0 +1,26 @@
|
|||||||
|
package com.dfsek.terra.api.structures.structure.buffer.items;
|
||||||
|
|
||||||
|
import com.dfsek.terra.api.math.vector.Location;
|
||||||
|
import com.dfsek.terra.api.platform.TerraPlugin;
|
||||||
|
import com.dfsek.terra.api.platform.block.state.BlockState;
|
||||||
|
|
||||||
|
public class BufferedStateManipulator implements BufferedItem {
|
||||||
|
private final TerraPlugin main;
|
||||||
|
private final String data;
|
||||||
|
|
||||||
|
public BufferedStateManipulator(TerraPlugin main, String state) {
|
||||||
|
this.main = main;
|
||||||
|
this.data = state;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void paste(Location origin) {
|
||||||
|
BlockState state = origin.getBlock().getState();
|
||||||
|
try {
|
||||||
|
state.applyState(data);
|
||||||
|
state.update(false);
|
||||||
|
} catch(ClassCastException e) {
|
||||||
|
main.getLogger().warning("Could not apply BlockState at " + origin + ": " + e.getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
-27
@@ -1,27 +0,0 @@
|
|||||||
package com.dfsek.terra.api.structures.structure.buffer.items.state;
|
|
||||||
|
|
||||||
import com.dfsek.terra.api.math.vector.Location;
|
|
||||||
import com.dfsek.terra.api.platform.TerraPlugin;
|
|
||||||
import com.dfsek.terra.api.platform.block.state.BlockState;
|
|
||||||
import com.dfsek.terra.api.structures.structure.buffer.items.BufferedItem;
|
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
public abstract class BufferedStateManipulator<T extends BlockState> implements BufferedItem {
|
|
||||||
private final TerraPlugin main;
|
|
||||||
|
|
||||||
protected BufferedStateManipulator(TerraPlugin main) {
|
|
||||||
this.main = main;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void paste(Location origin) {
|
|
||||||
BlockState state = origin.getBlock().getState();
|
|
||||||
try {
|
|
||||||
apply((T) state);
|
|
||||||
} catch(ClassCastException e) {
|
|
||||||
main.getLogger().warning("Could not find expected BlockState at " + origin + "; found " + origin.getBlock().getBlockData().getAsString());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public abstract void apply(T state);
|
|
||||||
}
|
|
||||||
@@ -22,13 +22,11 @@ public class TerraTree implements Tree {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public synchronized boolean plant(Location location, Random random) {
|
public synchronized boolean plant(Location location, Random random) {
|
||||||
structure.get(random).execute(location.clone().add(0, yOffset, 0), random, Rotation.fromDegrees(90 * random.nextInt(4)));
|
return structure.get(random).execute(location.clone().add(0, yOffset, 0), random, Rotation.fromDegrees(90 * random.nextInt(4)));
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public MaterialSet getSpawnable() {
|
public MaterialSet getSpawnable() {
|
||||||
return spawnable;
|
return spawnable;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,8 +55,7 @@ public class EventListener implements Listener {
|
|||||||
TreeRegistry registry = c.getTreeRegistry();
|
TreeRegistry registry = c.getTreeRegistry();
|
||||||
Tree tree = registry.get(TREE_TYPE_STRING_TRANSFORMER.translate(e.getSpecies()));
|
Tree tree = registry.get(TREE_TYPE_STRING_TRANSFORMER.translate(e.getSpecies()));
|
||||||
Debug.info("Overrode tree type: " + e.getSpecies());
|
Debug.info("Overrode tree type: " + e.getSpecies());
|
||||||
org.bukkit.Location location = e.getLocation().subtract(0, 1, 0);
|
org.bukkit.Location location = e.getLocation();
|
||||||
if(!tree.plant(new Location(bukkit, location.getX(), location.getY(), location.getZ()), new FastRandom())) block.setBlockData(data);
|
if(!tree.plant(new Location(bukkit, location.getX(), location.getY(), location.getZ()), new FastRandom())) block.setBlockData(data);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+2
@@ -6,6 +6,7 @@ import com.dfsek.terra.api.platform.block.state.BlockState;
|
|||||||
import com.dfsek.terra.bukkit.world.block.BukkitBlock;
|
import com.dfsek.terra.bukkit.world.block.BukkitBlock;
|
||||||
import com.dfsek.terra.bukkit.world.block.data.BukkitBlockData;
|
import com.dfsek.terra.bukkit.world.block.data.BukkitBlockData;
|
||||||
import org.bukkit.block.Container;
|
import org.bukkit.block.Container;
|
||||||
|
import org.bukkit.block.Sign;
|
||||||
|
|
||||||
public class BukkitBlockState implements BlockState {
|
public class BukkitBlockState implements BlockState {
|
||||||
private final org.bukkit.block.BlockState delegate;
|
private final org.bukkit.block.BlockState delegate;
|
||||||
@@ -16,6 +17,7 @@ public class BukkitBlockState implements BlockState {
|
|||||||
|
|
||||||
public static BukkitBlockState newInstance(org.bukkit.block.BlockState block) {
|
public static BukkitBlockState newInstance(org.bukkit.block.BlockState block) {
|
||||||
if(block instanceof Container) return new BukkitContainer((Container) block);
|
if(block instanceof Container) return new BukkitContainer((Container) block);
|
||||||
|
if(block instanceof Sign) return new BukkitSign((Sign) block);
|
||||||
return new BukkitBlockState(block);
|
return new BukkitBlockState(block);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+2
@@ -5,6 +5,7 @@ import com.dfsek.terra.api.platform.inventory.Inventory;
|
|||||||
import com.dfsek.terra.bukkit.world.inventory.BukkitInventory;
|
import com.dfsek.terra.bukkit.world.inventory.BukkitInventory;
|
||||||
|
|
||||||
public class BukkitContainer extends BukkitBlockState implements Container {
|
public class BukkitContainer extends BukkitBlockState implements Container {
|
||||||
|
|
||||||
protected BukkitContainer(org.bukkit.block.Container block) {
|
protected BukkitContainer(org.bukkit.block.Container block) {
|
||||||
super(block);
|
super(block);
|
||||||
}
|
}
|
||||||
@@ -13,4 +14,5 @@ public class BukkitContainer extends BukkitBlockState implements Container {
|
|||||||
public Inventory getInventory() {
|
public Inventory getInventory() {
|
||||||
return new BukkitInventory(((org.bukkit.block.Container) getHandle()).getInventory());
|
return new BukkitInventory(((org.bukkit.block.Container) getHandle()).getInventory());
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
+32
@@ -0,0 +1,32 @@
|
|||||||
|
package com.dfsek.terra.bukkit.world.block.state;
|
||||||
|
|
||||||
|
import com.dfsek.terra.api.platform.block.state.SerialState;
|
||||||
|
import com.dfsek.terra.api.platform.block.state.Sign;
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
|
public class BukkitSign extends BukkitBlockState implements Sign {
|
||||||
|
protected BukkitSign(org.bukkit.block.Sign block) {
|
||||||
|
super(block);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NotNull String[] getLines() {
|
||||||
|
return ((org.bukkit.block.Sign) getHandle()).getLines();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public @NotNull String getLine(int index) throws IndexOutOfBoundsException {
|
||||||
|
return ((org.bukkit.block.Sign) getHandle()).getLine(index);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void setLine(int index, @NotNull String line) throws IndexOutOfBoundsException {
|
||||||
|
((org.bukkit.block.Sign) getHandle()).setLine(index, line);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void applyState(String state) {
|
||||||
|
SerialState.parse(state).forEach((k, v) -> setLine(Integer.parseInt(k), v));
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user