diff --git a/data/ChestReward.json b/data/ChestReward.json new file mode 100644 index 000000000..a9c847b16 --- /dev/null +++ b/data/ChestReward.json @@ -0,0 +1,135 @@ +[ + { + "objNames" : [ + "SceneObj_Chest_Default_Lv1", + "SceneObj_Chest_Locked_Lv1", + "SceneObj_Chest_Bramble_Lv1", + "SceneObj_Chest_Frozen_Lv1", + "SceneObj_Chest_Rock_Lv1", + "SceneObj_EssenceChest_Default_Lv1", + "SceneObj_EssenceChest_Locked_Lv1" + ], + "advExp" : 10, + "resin" : 0, + "mora" : 257, + "sigil" : 1, + "content" : [ + { + "itemId" : 104011, + "count": 3 + }, + { + "itemId" : 104001, + "count": 1 + } + ], + "randomCount": 4, + "randomContent": [ + { + "itemId" : 11101, + "count": 1 + }, + { + "itemId" : 11201, + "count": 1 + }, + { + "itemId" : 12101, + "count": 1 + }, + { + "itemId" : 12201, + "count": 1 + }, + { + "itemId" : 13101, + "count": 1 + }, + { + "itemId" : 13201, + "count": 1 + }, + { + "itemId" : 14101, + "count": 1 + }, + { + "itemId" : 14201, + "count": 1 + }, + { + "itemId" : 15101, + "count": 1 + }, + { + "itemId" : 15201, + "count": 1 + } + ] + }, + { + "objNames" : [ + "SceneObj_Chest_Default_Lv2", + "SceneObj_Chest_Locked_Lv2", + "SceneObj_Chest_Bramble_Lv2", + "SceneObj_Chest_Frozen_Lv2" + ], + "advExp" : 20, + "resin" : 2, + "mora" : 756, + "sigil" : 2, + "content" : [ + { + "itemId" : 104012, + "count": 3 + }, + { + "itemId" : 104002, + "count": 1 + } + ], + "randomCount": 4, + "randomContent": [ + { + "itemId" : 11201, + "count": 1 + }, + { + "itemId" : 11301, + "count": 1 + }, + { + "itemId" : 12201, + "count": 1 + }, + { + "itemId" : 12301, + "count": 1 + }, + { + "itemId" : 13201, + "count": 1 + }, + { + "itemId" : 13301, + "count": 1 + }, + { + "itemId" : 14201, + "count": 1 + }, + { + "itemId" : 14301, + "count": 1 + }, + { + "itemId" : 15201, + "count": 1 + }, + { + "itemId" : 15301, + "count": 1 + } + ] + } +] \ No newline at end of file diff --git a/src/main/java/emu/grasscutter/game/entity/EntityGadget.java b/src/main/java/emu/grasscutter/game/entity/EntityGadget.java index af1d2c68c..6b4c677b2 100644 --- a/src/main/java/emu/grasscutter/game/entity/EntityGadget.java +++ b/src/main/java/emu/grasscutter/game/entity/EntityGadget.java @@ -1,23 +1,21 @@ package emu.grasscutter.game.entity; -import java.util.Arrays; -import java.util.List; - +import emu.grasscutter.Grasscutter; import emu.grasscutter.data.GameData; import emu.grasscutter.data.def.GadgetData; import emu.grasscutter.game.entity.gadget.GadgetContent; import emu.grasscutter.game.entity.gadget.GadgetGatherPoint; import emu.grasscutter.game.entity.gadget.GadgetRewardStatue; import emu.grasscutter.game.entity.gadget.GadgetWorktop; +import emu.grasscutter.game.player.Player; import emu.grasscutter.game.props.EntityIdType; import emu.grasscutter.game.props.EntityType; import emu.grasscutter.game.props.FightProperty; import emu.grasscutter.game.props.PlayerProperty; import emu.grasscutter.game.world.Scene; -import emu.grasscutter.game.world.World; -import emu.grasscutter.net.proto.ClientGadgetInfoOuterClass; import emu.grasscutter.net.proto.AbilitySyncStateInfoOuterClass.AbilitySyncStateInfo; import emu.grasscutter.net.proto.AnimatorParameterValueInfoPairOuterClass.AnimatorParameterValueInfoPair; +import emu.grasscutter.net.proto.BossChestInfoOuterClass; import emu.grasscutter.net.proto.EntityAuthorityInfoOuterClass.EntityAuthorityInfo; import emu.grasscutter.net.proto.EntityClientDataOuterClass.EntityClientData; import emu.grasscutter.net.proto.EntityRendererChangedInfoOuterClass.EntityRendererChangedInfo; @@ -32,11 +30,14 @@ import emu.grasscutter.net.proto.WorktopInfoOuterClass.WorktopInfo; import emu.grasscutter.utils.Position; import emu.grasscutter.utils.ProtoHelper; import it.unimi.dsi.fastutil.ints.Int2FloatOpenHashMap; -import it.unimi.dsi.fastutil.ints.IntArrayList; -import it.unimi.dsi.fastutil.ints.IntList; import it.unimi.dsi.fastutil.ints.IntOpenHashSet; import it.unimi.dsi.fastutil.ints.IntSet; +import lombok.ToString; +import java.util.Arrays; +import java.util.Random; + +@ToString(callSuper = true) public class EntityGadget extends EntityBaseGadget { private final GadgetData data; private final Position pos; @@ -175,4 +176,30 @@ public class EntityGadget extends EntityBaseGadget { return entityInfo.build(); } + + public void openChest(Player player) { + var chestRewardMap = getScene().getWorld().getServer().getWorldDataManager().getChestRewardMap(); + var chestReward = chestRewardMap.get(this.getGadgetData().getJsonName()); + if(chestReward == null){ + Grasscutter.getLogger().warn("Could not found the config of this type of Chests {}", this.getGadgetData().getJsonName()); + return; + } + + player.earnExp(chestReward.getAdvExp()); + player.getInventory().addItem(201, chestReward.getResin()); + + var mora = chestReward.getMora() * (1 + (player.getWorldLevel() - 1) * 0.5); + player.getInventory().addItem(202, (int)mora); + + for(int i=0;i objNames; + int advExp; + int resin; + int mora; + int sigil; + List content; + int randomCount; + List randomContent; + +} diff --git a/src/main/java/emu/grasscutter/game/world/Scene.java b/src/main/java/emu/grasscutter/game/world/Scene.java index c53ad0b21..b7c34a3e1 100644 --- a/src/main/java/emu/grasscutter/game/world/Scene.java +++ b/src/main/java/emu/grasscutter/game/world/Scene.java @@ -3,10 +3,7 @@ package emu.grasscutter.game.world; import emu.grasscutter.Grasscutter; import emu.grasscutter.data.GameData; import emu.grasscutter.data.GameDepot; -import emu.grasscutter.data.def.DungeonData; -import emu.grasscutter.data.def.MonsterData; -import emu.grasscutter.data.def.SceneData; -import emu.grasscutter.data.def.WorldLevelData; +import emu.grasscutter.data.def.*; import emu.grasscutter.game.dungeons.DungeonChallenge; import emu.grasscutter.game.dungeons.DungeonSettleListener; import emu.grasscutter.game.entity.*; @@ -25,11 +22,8 @@ import emu.grasscutter.scripts.SceneScriptManager; import emu.grasscutter.scripts.data.SceneBlock; import emu.grasscutter.scripts.data.SceneGadget; import emu.grasscutter.scripts.data.SceneGroup; -import emu.grasscutter.server.packet.send.PacketAvatarSkillInfoNotify; -import emu.grasscutter.server.packet.send.PacketDungeonChallengeFinishNotify; -import emu.grasscutter.server.packet.send.PacketLifeStateChangeNotify; -import emu.grasscutter.server.packet.send.PacketSceneEntityAppearNotify; -import emu.grasscutter.server.packet.send.PacketSceneEntityDisappearNotify; +import emu.grasscutter.server.packet.send.*; +import emu.grasscutter.utils.Position; import it.unimi.dsi.fastutil.ints.Int2ObjectMap; import it.unimi.dsi.fastutil.ints.Int2ObjectMaps; import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap; @@ -38,6 +32,8 @@ import org.danilopianini.util.SpatialIndex; import java.util.*; import java.util.stream.Collectors; +import static emu.grasscutter.utils.Language.translate; + public class Scene { private final World world; private final SceneData sceneData; @@ -595,8 +591,10 @@ public class Scene { do { var suiteData = group.getSuiteByIndex(suite); + suiteData.sceneTriggers.forEach(getScriptManager()::registerTrigger); + entities.addAll(suiteData.sceneGadgets.stream() - .map(g -> scriptManager.createGadgets(group.id, group.block_id, g)).toList()); + .map(g -> scriptManager.createGadget(group.id, group.block_id, g)).toList()); entities.addAll(suiteData.sceneMonsters.stream() .map(mob -> scriptManager.createMonster(group.id, group.block_id, mob)).toList()); suite++; @@ -618,7 +616,7 @@ public class Scene { for (SceneGroup group : block.groups) { if(group.triggers != null){ - group.triggers.forEach(getScriptManager()::deregisterTrigger); + group.triggers.values().forEach(getScriptManager()::deregisterTrigger); } if(group.regions != null){ group.regions.forEach(getScriptManager()::deregisterRegion); @@ -690,4 +688,27 @@ public class Scene { player.getSession().send(packet); } } + + public void addItemEntity(int itemId, int amount, GameEntity bornForm){ + ItemData itemData = GameData.getItemDataMap().get(itemId); + if (itemData == null) { + return; + } + if (itemData.isEquip()) { + float range = (3f + (.1f * amount)); + for (int i = 0; i < amount; i++) { + Position pos = bornForm.getPosition().clone().addX((float) (Math.random() * range) - (range / 2)).addZ((float) (Math.random() * range) - (range / 2)).addZ(.9f); + EntityItem entity = new EntityItem(this, null, itemData, pos, 1); + addEntity(entity); + } + } else { + EntityItem entity = new EntityItem(this, null, itemData, bornForm.getPosition().clone().addZ(.9f), amount); + addEntity(entity); + } + } + + public void updateGadgetState(EntityGadget gadget, int state){ + gadget.setState(state); + broadcastPacket(new PacketGadgetStateNotify(gadget, state)); + } } diff --git a/src/main/java/emu/grasscutter/game/world/WorldDataManager.java b/src/main/java/emu/grasscutter/game/world/WorldDataManager.java new file mode 100644 index 000000000..c7466880b --- /dev/null +++ b/src/main/java/emu/grasscutter/game/world/WorldDataManager.java @@ -0,0 +1,41 @@ +package emu.grasscutter.game.world; + +import com.google.gson.reflect.TypeToken; +import emu.grasscutter.Grasscutter; +import emu.grasscutter.server.game.GameServer; + +import java.nio.file.Files; +import java.nio.file.Path; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import static emu.grasscutter.Configuration.DATA; + +public class WorldDataManager { + private final GameServer gameServer; + private final Map chestRewardMap; + + public WorldDataManager(GameServer gameServer){ + this.gameServer = gameServer; + this.chestRewardMap = new HashMap<>(); + load(); + } + + public synchronized void load(){ + try { + List chestReward = Grasscutter.getGsonFactory().fromJson( + Files.readString(Path.of(DATA("ChestReward.json"))), + TypeToken.getParameterized(List.class, ChestReward.class).getType()); + chestReward.forEach(reward -> + reward.getObjNames().forEach(name -> chestRewardMap.put(name, reward))); + + } catch (Exception e) { + Grasscutter.getLogger().error("Unable to load chest reward config.", e); + } + } + + public Map getChestRewardMap() { + return chestRewardMap; + } +} diff --git a/src/main/java/emu/grasscutter/scripts/SceneScriptManager.java b/src/main/java/emu/grasscutter/scripts/SceneScriptManager.java index 99755a18f..539fef5b2 100644 --- a/src/main/java/emu/grasscutter/scripts/SceneScriptManager.java +++ b/src/main/java/emu/grasscutter/scripts/SceneScriptManager.java @@ -42,7 +42,6 @@ public class SceneScriptManager { private final Int2ObjectOpenHashMap> currentTriggers; private final Int2ObjectOpenHashMap regions; private Map sceneGroups; - private SceneGroup currentGroup; private ScriptMonsterTideService scriptMonsterTideService; private ScriptMonsterSpawnService scriptMonsterSpawnService; /** @@ -94,10 +93,6 @@ public class SceneScriptManager { return meta.config; } - public SceneGroup getCurrentGroup() { - return currentGroup; - } - public Map getBlocks() { return meta.blocks; } @@ -118,20 +113,19 @@ public class SceneScriptManager { this.triggers.remove(trigger.name); getTriggersByEvent(trigger.event).remove(trigger); } - public void resetTriggers(List triggerNames) { - for(var name : triggerNames){ - var instance = triggers.get(name); - this.currentTriggers.get(instance.event).clear(); - this.currentTriggers.get(instance.event).add(instance); - } + public void resetTriggers(int eventId) { + currentTriggers.put(eventId, new HashSet<>()); } public void refreshGroup(SceneGroup group, int suiteIndex){ var suite = group.getSuiteByIndex(suiteIndex); if(suite == null){ return; } - if(suite.triggers.size() > 0){ - resetTriggers(suite.triggers); + if(suite.sceneTriggers.size() > 0){ + for(var trigger : suite.sceneTriggers){ + resetTriggers(trigger.event); + this.currentTriggers.get(trigger.event).add(trigger); + } } spawnMonstersInGroup(group, suite); spawnGadgetsInGroup(group, suite); @@ -158,7 +152,7 @@ public class SceneScriptManager { for (SceneGroup group : block.groups) { if (group.id == groupId) { if(!group.isLoaded()){ - loadGroupFromScript(group); + getScene().onLoadGroup(List.of(group)); } return group; } @@ -204,9 +198,6 @@ public class SceneScriptManager { group.variables.forEach(var -> this.getVariables().put(var.name, var.value)); this.sceneGroups.put(group.id, group); - if(group.triggers != null){ - group.triggers.forEach(this::registerTrigger); - } if(group.regions != null){ group.regions.forEach(this::registerRegion); } @@ -248,7 +239,7 @@ public class SceneScriptManager { } var toCreate = gadgets.stream() - .map(g -> createGadgets(g.groupId, group.block_id, g)) + .map(g -> createGadget(g.groupId, group.block_id, g)) .filter(Objects::nonNull) .toList(); this.addEntities(toCreate); @@ -265,20 +256,17 @@ public class SceneScriptManager { if(suite == null || suite.sceneMonsters.size() <= 0){ return; } - this.currentGroup = group; this.addEntities(suite.sceneMonsters.stream() .map(mob -> createMonster(group.id, group.block_id, mob)).toList()); } public void spawnMonstersInGroup(SceneGroup group) { - this.currentGroup = group; this.addEntities(group.monsters.values().stream() .map(mob -> createMonster(group.id, group.block_id, mob)).toList()); } public void startMonsterTideInGroup(SceneGroup group, Integer[] ordersConfigId, int tideCount, int sceneLimit) { - this.currentGroup = group; this.scriptMonsterTideService = new ScriptMonsterTideService(this, group, tideCount, sceneLimit, ordersConfigId); @@ -289,15 +277,15 @@ public class SceneScriptManager { } this.getScriptMonsterTideService().unload(); } - public void spawnMonstersByConfigId(int configId, int delayTime) { + public void spawnMonstersByConfigId(SceneGroup group, int configId, int delayTime) { // TODO delay - getScene().addEntity( - createMonster(this.currentGroup.id, this.currentGroup.block_id, this.currentGroup.monsters.get(configId))); + getScene().addEntity(createMonster(group.id, group.block_id, group.monsters.get(configId))); } // Events public void callEvent(int eventType, ScriptArgs params) { for (SceneTrigger trigger : this.getTriggersByEvent(eventType)) { + scriptLib.setCurrentGroup(trigger.currentGroup); LuaValue condition = null; if (trigger.condition != null && !trigger.condition.isEmpty()) { @@ -330,6 +318,7 @@ public class SceneScriptManager { safetyCall(trigger.action, action, args); } //TODO some ret may not bool + scriptLib.removeCurrentGroup(); } } @@ -337,7 +326,7 @@ public class SceneScriptManager { try{ return func.call(this.getScriptLibLua(), args); }catch (LuaError error){ - ScriptLib.logger.error("[LUA] call trigger failed {},{}",name,args,error); + ScriptLib.logger.error("[LUA] call trigger failed {},{},{}",name,args,error.getMessage()); return LuaValue.valueOf(-1); } } @@ -350,7 +339,7 @@ public class SceneScriptManager { return scriptMonsterSpawnService; } - public EntityGadget createGadgets(int groupId, int blockId, SceneGadget g) { + public EntityGadget createGadget(int groupId, int blockId, SceneGadget g) { EntityGadget entity = new EntityGadget(getScene(), g.gadget_id, g.pos); if (entity.getGadgetData() == null){ diff --git a/src/main/java/emu/grasscutter/scripts/ScriptLib.java b/src/main/java/emu/grasscutter/scripts/ScriptLib.java index f436df321..74aa8b6b6 100644 --- a/src/main/java/emu/grasscutter/scripts/ScriptLib.java +++ b/src/main/java/emu/grasscutter/scripts/ScriptLib.java @@ -24,6 +24,7 @@ public class ScriptLib { public ScriptLib(SceneScriptManager sceneScriptManager) { this.sceneScriptManager = sceneScriptManager; + this.currentGroup = new ThreadLocal<>(); } public SceneScriptManager getSceneScriptManager() { @@ -39,7 +40,17 @@ public class ScriptLib { sb.append("}"); return sb.toString(); } - + private final ThreadLocal currentGroup; + public void setCurrentGroup(SceneGroup currentGroup){ + logger.debug("current {}", currentGroup); + this.currentGroup.set(currentGroup); + } + public Optional getCurrentGroup(){ + return Optional.ofNullable(this.currentGroup.get()); + } + public void removeCurrentGroup(){ + this.currentGroup.remove(); + } public int SetGadgetStateByConfigId(int configId, int gadgetState) { logger.debug("[LUA] Call SetGadgetStateByConfigId with {},{}", configId,gadgetState); @@ -102,7 +113,12 @@ public class ScriptLib { return 0; } - + + public int SetWorktopOptions(LuaTable table){ + logger.debug("[LUA] Call SetWorktopOptions with {}", printTable(table)); + // TODO + return 0; + } public int DelWorktopOptionByGroupId(int groupId, int configId, int option) { logger.debug("[LUA] Call DelWorktopOptionByGroupId with {},{},{}",groupId,configId,option); @@ -273,7 +289,8 @@ public class ScriptLib { var1); return (int) getSceneScriptManager().getScene().getEntities().values().stream() - .filter(e -> e instanceof EntityMonster && e.getGroupId() == getSceneScriptManager().getCurrentGroup().id) + .filter(e -> e instanceof EntityMonster && + e.getGroupId() == getCurrentGroup().map(sceneGroup -> sceneGroup.id).orElse(-1)) .count(); } public int SetMonsterBattleByGroup(int var1, int var2, int var3){ @@ -335,7 +352,11 @@ public class ScriptLib { var configId = table.get("config_id").toint(); var delayTime = table.get("delay_time").toint(); - getSceneScriptManager().spawnMonstersByConfigId(configId, delayTime); + if(getCurrentGroup().isEmpty()){ + return 1; + } + + getSceneScriptManager().spawnMonstersByConfigId(getCurrentGroup().get(), configId, delayTime); return 0; } @@ -354,7 +375,13 @@ public class ScriptLib { printTable(table)); var configId = table.get("config_id").toint(); - //TODO + var group = getCurrentGroup(); + if(group.isEmpty()){ + return 1; + } + var gadget = group.get().gadgets.get(configId); + var entity = getSceneScriptManager().createGadget(group.get().id, group.get().block_id, gadget); + getSceneScriptManager().addEntity(entity); return 0; } @@ -377,14 +404,42 @@ public class ScriptLib { .filter(g -> g.getConfigId() == configId) .findFirst(); if(gadget.isEmpty()){ - return 0; + return 1; } - var stat = ((EntityGadget)gadget.get()).getState(); - return stat; + return ((EntityGadget)gadget.get()).getState(); } - public int SetGadgetStateByConfigId(int configId, LuaTable gadgetState){ - logger.debug("[LUA] Call SetGadgetStateByConfigId with {},{}", - configId, printTable(gadgetState)); + + public int MarkPlayerAction(int var1, int var2, int var3, int var4){ + logger.debug("[LUA] Call MarkPlayerAction with {},{}", + var1, var2); + + return 0; + } + + public int AddQuestProgress(String var1){ + logger.debug("[LUA] Call AddQuestProgress with {}", + var1); + + return 0; + } + + /** + * change the state of gadget + */ + public int ChangeGroupGadget(LuaTable table){ + logger.debug("[LUA] Call ChangeGroupGadget with {}", + printTable(table)); + var configId = table.get("config_id").toint(); + var state = table.get("state").toint(); + + var entity = getSceneScriptManager().getScene().getEntityByConfigId(configId); + if(entity == null){ + return 1; + } + + if(entity instanceof EntityGadget entityGadget){ + getSceneScriptManager().getScene().updateGadgetState(entityGadget, state); + } return 0; } diff --git a/src/main/java/emu/grasscutter/scripts/constants/EventType.java b/src/main/java/emu/grasscutter/scripts/constants/EventType.java index 58d8dc3ab..b7236b85c 100644 --- a/src/main/java/emu/grasscutter/scripts/constants/EventType.java +++ b/src/main/java/emu/grasscutter/scripts/constants/EventType.java @@ -2,6 +2,9 @@ package emu.grasscutter.scripts.constants; public class EventType { public static final int EVENT_NONE = 0; + /** + * param1: monster.configId + */ public static final int EVENT_ANY_MONSTER_DIE = 1; public static final int EVENT_ANY_GADGET_DIE = 2; public static final int EVENT_VARIABLE_CHANGE = 3; diff --git a/src/main/java/emu/grasscutter/scripts/data/SceneGroup.java b/src/main/java/emu/grasscutter/scripts/data/SceneGroup.java index 0cef08627..d43961f7b 100644 --- a/src/main/java/emu/grasscutter/scripts/data/SceneGroup.java +++ b/src/main/java/emu/grasscutter/scripts/data/SceneGroup.java @@ -28,8 +28,8 @@ public class SceneGroup { public Map monsters; // public Map gadgets; // - - public List triggers; + public Map triggers; + public List regions; public List suites; public List variables; @@ -94,9 +94,10 @@ public class SceneGroup { .collect(Collectors.toMap(x -> x.config_id, y -> y)); gadgets.values().forEach(m -> m.groupId = id); - triggers = ScriptLoader.getSerializer().toList(SceneTrigger.class, bindings.get("triggers")); - triggers.forEach(t -> t.currentGroup = this); - + triggers = ScriptLoader.getSerializer().toList(SceneTrigger.class, bindings.get("triggers")).stream() + .collect(Collectors.toMap(x -> x.name, y -> y)); + triggers.values().forEach(t -> t.currentGroup = this); + suites = ScriptLoader.getSerializer().toList(SceneSuite.class, bindings.get("suites")); regions = ScriptLoader.getSerializer().toList(SceneRegion.class, bindings.get("regions")); garbages = ScriptLoader.getSerializer().toObject(SceneGarbage.class, bindings.get("garbages")); @@ -120,6 +121,13 @@ public class SceneGroup { .map(gadgets::get) .toList() ); + + suite.sceneTriggers = new ArrayList<>( + suite.triggers.stream() + .filter(triggers::containsKey) + .map(triggers::get) + .toList() + ); } } catch (ScriptException e) { diff --git a/src/main/java/emu/grasscutter/scripts/data/SceneSuite.java b/src/main/java/emu/grasscutter/scripts/data/SceneSuite.java index 2afa9cf72..7555601ca 100644 --- a/src/main/java/emu/grasscutter/scripts/data/SceneSuite.java +++ b/src/main/java/emu/grasscutter/scripts/data/SceneSuite.java @@ -15,4 +15,5 @@ public class SceneSuite { public transient List sceneMonsters; public transient List sceneGadgets; + public transient List sceneTriggers; } diff --git a/src/main/java/emu/grasscutter/scripts/data/SceneTrigger.java b/src/main/java/emu/grasscutter/scripts/data/SceneTrigger.java index 6f5d761ef..34e4df75e 100644 --- a/src/main/java/emu/grasscutter/scripts/data/SceneTrigger.java +++ b/src/main/java/emu/grasscutter/scripts/data/SceneTrigger.java @@ -11,7 +11,7 @@ public class SceneTrigger { public String condition; public String action; - public SceneGroup currentGroup; + public transient SceneGroup currentGroup; @Override public boolean equals(Object obj) { if(obj instanceof SceneTrigger sceneTrigger){ diff --git a/src/main/java/emu/grasscutter/server/game/GameServer.java b/src/main/java/emu/grasscutter/server/game/GameServer.java index 3ebe83997..3159de1aa 100644 --- a/src/main/java/emu/grasscutter/server/game/GameServer.java +++ b/src/main/java/emu/grasscutter/server/game/GameServer.java @@ -19,6 +19,7 @@ import emu.grasscutter.game.quest.ServerQuestHandler; import emu.grasscutter.game.shop.ShopManager; import emu.grasscutter.game.tower.TowerScheduleManager; import emu.grasscutter.game.world.World; +import emu.grasscutter.game.world.WorldDataManager; import emu.grasscutter.net.packet.PacketHandler; import emu.grasscutter.net.proto.SocialDetailOuterClass.SocialDetail; import emu.grasscutter.netty.KcpServer; @@ -57,6 +58,7 @@ public final class GameServer extends KcpServer { private final CombineManger combineManger; private final TowerScheduleManager towerScheduleManager; + private final WorldDataManager worldDataManager; public GameServer() { this(new InetSocketAddress( GAME_INFO.bindAddress, @@ -86,6 +88,7 @@ public final class GameServer extends KcpServer { this.expeditionManager = new ExpeditionManager(this); this.combineManger = new CombineManger(this); this.towerScheduleManager = new TowerScheduleManager(this); + this.worldDataManager = new WorldDataManager(this); // Hook into shutdown event. Runtime.getRuntime().addShutdownHook(new Thread(this::onServerShutdown)); } @@ -153,6 +156,10 @@ public final class GameServer extends KcpServer { return towerScheduleManager; } + public WorldDataManager getWorldDataManager() { + return worldDataManager; + } + public TaskMap getTaskMap() { return this.taskMap; }