mirror of
https://github.com/Melledy/Grasscutter.git
synced 2024-11-26 13:11:09 +00:00
Implement script region check
This commit is contained in:
parent
1ed46df6e8
commit
7e377dff59
@ -34,6 +34,10 @@ public abstract class GameEntity {
|
||||
return this.id;
|
||||
}
|
||||
|
||||
public int getEntityType() {
|
||||
return getId() >> 24;
|
||||
}
|
||||
|
||||
public World getWorld() {
|
||||
return this.getScene().getWorld();
|
||||
}
|
||||
|
@ -508,6 +508,7 @@ public class Scene {
|
||||
}
|
||||
|
||||
group.triggers.forEach(getScriptManager()::registerTrigger);
|
||||
group.regions.forEach(getScriptManager()::registerRegion);
|
||||
}
|
||||
|
||||
// Spawn gadgets AFTER triggers are added
|
||||
@ -526,6 +527,7 @@ public class Scene {
|
||||
|
||||
for (SceneGroup group : block.groups) {
|
||||
group.triggers.forEach(getScriptManager()::deregisterTrigger);
|
||||
group.regions.forEach(getScriptManager()::deregisterRegion);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -35,6 +35,7 @@ import emu.grasscutter.scripts.data.SceneGadget;
|
||||
import emu.grasscutter.scripts.data.SceneGroup;
|
||||
import emu.grasscutter.scripts.data.SceneInitConfig;
|
||||
import emu.grasscutter.scripts.data.SceneMonster;
|
||||
import emu.grasscutter.scripts.data.SceneRegion;
|
||||
import emu.grasscutter.scripts.data.SceneSuite;
|
||||
import emu.grasscutter.scripts.data.SceneTrigger;
|
||||
import emu.grasscutter.scripts.data.SceneVar;
|
||||
@ -51,14 +52,17 @@ public class SceneScriptManager {
|
||||
private Bindings bindings;
|
||||
private SceneConfig config;
|
||||
private List<SceneBlock> blocks;
|
||||
private Int2ObjectOpenHashMap<Set<SceneTrigger>> triggers;
|
||||
private boolean isInit;
|
||||
|
||||
private final Int2ObjectOpenHashMap<Set<SceneTrigger>> triggers;
|
||||
private final Int2ObjectOpenHashMap<SceneRegion> regions;
|
||||
|
||||
public SceneScriptManager(Scene scene) {
|
||||
this.scene = scene;
|
||||
this.scriptLib = new ScriptLib(this);
|
||||
this.scriptLibLua = CoerceJavaToLua.coerce(this.scriptLib);
|
||||
this.triggers = new Int2ObjectOpenHashMap<>();
|
||||
this.regions = new Int2ObjectOpenHashMap<>();
|
||||
this.variables = new HashMap<>();
|
||||
|
||||
// TEMPORARY
|
||||
@ -110,6 +114,18 @@ public class SceneScriptManager {
|
||||
getTriggersByEvent(trigger.event).remove(trigger);
|
||||
}
|
||||
|
||||
public SceneRegion getRegionById(int id) {
|
||||
return regions.get(id);
|
||||
}
|
||||
|
||||
public void registerRegion(SceneRegion region) {
|
||||
regions.put(region.config_id, region);
|
||||
}
|
||||
|
||||
public void deregisterRegion(SceneRegion region) {
|
||||
regions.remove(region.config_id);
|
||||
}
|
||||
|
||||
// TODO optimize
|
||||
public SceneGroup getGroupById(int groupId) {
|
||||
for (SceneBlock block : this.getScene().getLoadedBlocks()) {
|
||||
@ -210,6 +226,7 @@ public class SceneScriptManager {
|
||||
group.gadgets = ScriptLoader.getSerializer().toList(SceneGadget.class, bindings.get("gadgets"));
|
||||
group.triggers = ScriptLoader.getSerializer().toList(SceneTrigger.class, bindings.get("triggers"));
|
||||
group.suites = ScriptLoader.getSerializer().toList(SceneSuite.class, bindings.get("suites"));
|
||||
group.regions = ScriptLoader.getSerializer().toList(SceneRegion.class, bindings.get("regions"));
|
||||
group.init_config = ScriptLoader.getSerializer().toObject(SceneInitConfig.class, bindings.get("init_config"));
|
||||
|
||||
// Add variables to suite
|
||||
@ -234,11 +251,27 @@ public class SceneScriptManager {
|
||||
}
|
||||
|
||||
public void onTick() {
|
||||
checkTriggers();
|
||||
checkRegions();
|
||||
}
|
||||
|
||||
public void checkTriggers() {
|
||||
public void checkRegions() {
|
||||
if (this.regions.size() == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (SceneRegion region : this.regions.values()) {
|
||||
getScene().getEntities().values()
|
||||
.stream()
|
||||
.filter(e -> e.getEntityType() <= 2 && region.contains(e.getPosition()))
|
||||
.forEach(region::addEntity);
|
||||
|
||||
if (region.hasNewEntities()) {
|
||||
// This is not how it works, source_eid should be region entity id, but we dont have an entity for regions yet
|
||||
callEvent(EventType.EVENT_ENTER_REGION, new ScriptArgs(region.config_id).setSourceEntityId(region.config_id));
|
||||
|
||||
region.resetNewEntities();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void spawnGadgetsInGroup(SceneGroup group) {
|
||||
|
@ -17,6 +17,7 @@ import emu.grasscutter.game.entity.GameEntity;
|
||||
import emu.grasscutter.scripts.constants.EventType;
|
||||
import emu.grasscutter.scripts.data.SceneGroup;
|
||||
import emu.grasscutter.scripts.data.SceneMonster;
|
||||
import emu.grasscutter.scripts.data.SceneRegion;
|
||||
import emu.grasscutter.scripts.data.ScriptArgs;
|
||||
import emu.grasscutter.server.packet.send.PacketGadgetStateNotify;
|
||||
import emu.grasscutter.server.packet.send.PacketWorktopOptionNotify;
|
||||
@ -184,6 +185,19 @@ public class ScriptLib {
|
||||
return 0;
|
||||
}
|
||||
|
||||
public int GetRegionEntityCount(LuaTable table) {
|
||||
int regionId = table.get("region_eid").toint();
|
||||
int entityType = table.get("entity_type").toint();
|
||||
|
||||
SceneRegion region = this.getSceneScriptManager().getRegionById(regionId);
|
||||
|
||||
if (region == null) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
return (int) region.getEntities().intStream().filter(e -> e >> 24 == entityType).count();
|
||||
}
|
||||
|
||||
public void PrintContextLog(String msg) {
|
||||
Grasscutter.getLogger().info("[LUA] " + msg);
|
||||
}
|
||||
|
@ -14,6 +14,7 @@ public class SceneGroup {
|
||||
public List<SceneMonster> monsters;
|
||||
public List<SceneGadget> gadgets;
|
||||
public List<SceneTrigger> triggers;
|
||||
public List<SceneRegion> regions;
|
||||
public List<SceneSuite> suites;
|
||||
public SceneInitConfig init_config;
|
||||
|
||||
|
57
src/main/java/emu/grasscutter/scripts/data/SceneRegion.java
Normal file
57
src/main/java/emu/grasscutter/scripts/data/SceneRegion.java
Normal file
@ -0,0 +1,57 @@
|
||||
package emu.grasscutter.scripts.data;
|
||||
|
||||
import emu.grasscutter.game.entity.GameEntity;
|
||||
import emu.grasscutter.scripts.constants.ScriptRegionShape;
|
||||
import emu.grasscutter.utils.Position;
|
||||
import it.unimi.dsi.fastutil.ints.IntOpenHashSet;
|
||||
import it.unimi.dsi.fastutil.ints.IntSet;
|
||||
|
||||
public class SceneRegion {
|
||||
public int config_id;
|
||||
public int shape;
|
||||
public Position pos;
|
||||
public Position size;
|
||||
|
||||
private boolean hasNewEntities;
|
||||
private final IntSet entities; // Ids of entities inside this region
|
||||
|
||||
public SceneRegion() {
|
||||
this.entities = new IntOpenHashSet();
|
||||
}
|
||||
|
||||
public IntSet getEntities() {
|
||||
return entities;
|
||||
}
|
||||
|
||||
public void addEntity(GameEntity entity) {
|
||||
if (this.getEntities().contains(entity.getId())) {
|
||||
return;
|
||||
}
|
||||
this.getEntities().add(entity.getId());
|
||||
this.hasNewEntities = true;
|
||||
}
|
||||
|
||||
public void removeEntity(GameEntity entity) {
|
||||
this.getEntities().remove(entity.getId());
|
||||
}
|
||||
|
||||
public boolean contains(Position p) {
|
||||
switch (shape) {
|
||||
case ScriptRegionShape.CUBIC:
|
||||
return (Math.abs(pos.getX() - p.getX()) <= size.getX()) &&
|
||||
(Math.abs(pos.getZ() - p.getZ()) <= size.getZ());
|
||||
case ScriptRegionShape.SPHERE:
|
||||
return false;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean hasNewEntities() {
|
||||
return hasNewEntities;
|
||||
}
|
||||
|
||||
public void resetNewEntities() {
|
||||
hasNewEntities = false;
|
||||
}
|
||||
}
|
@ -4,6 +4,7 @@ public class ScriptArgs {
|
||||
public int param1;
|
||||
public int param2;
|
||||
public int param3;
|
||||
public int source_eid; // Source entity
|
||||
|
||||
public ScriptArgs() {
|
||||
|
||||
@ -44,4 +45,13 @@ public class ScriptArgs {
|
||||
this.param3 = param3;
|
||||
return this;
|
||||
}
|
||||
|
||||
public int getSourceEntityId() {
|
||||
return source_eid;
|
||||
}
|
||||
|
||||
public ScriptArgs setSourceEntityId(int source_eid) {
|
||||
this.source_eid = source_eid;
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user