mirror of
https://github.com/Melledy/LunarCore.git
synced 2025-12-23 10:44:36 +01:00
Implement summon related techniques
Make sure to redownload config files are as new summon unit configs are required
This commit is contained in:
@@ -24,6 +24,7 @@ public class GameData {
|
||||
@Getter private static Int2ObjectMap<RelicExcel> relicExcelMap = new Int2ObjectOpenHashMap<>();
|
||||
@Getter private static Int2ObjectMap<PropExcel> propExcelMap = new Int2ObjectOpenHashMap<>();
|
||||
@Getter private static Int2ObjectMap<NpcExcel> npcExcelMap = new Int2ObjectOpenHashMap<>();
|
||||
@Getter private static Int2ObjectMap<SummonUnitExcel> summonUnitExcelMap = new Int2ObjectOpenHashMap<>();
|
||||
@Getter private static Int2ObjectMap<MonsterExcel> monsterExcelMap = new Int2ObjectOpenHashMap<>();
|
||||
@Getter private static Int2ObjectMap<NpcMonsterExcel> npcMonsterExcelMap = new Int2ObjectOpenHashMap<>();
|
||||
@Getter private static Int2ObjectMap<StageExcel> stageExcelMap = new Int2ObjectOpenHashMap<>();
|
||||
|
||||
@@ -21,6 +21,7 @@ import emu.lunarcore.data.config.FloorInfo;
|
||||
import emu.lunarcore.data.config.FloorInfo.FloorGroupSimpleInfo;
|
||||
import emu.lunarcore.data.config.GroupInfo;
|
||||
import emu.lunarcore.data.config.SkillAbilityInfo;
|
||||
import emu.lunarcore.data.config.SummonUnitInfo;
|
||||
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
|
||||
|
||||
public class ResourceLoader {
|
||||
@@ -227,8 +228,40 @@ public class ResourceLoader {
|
||||
|
||||
// Might be better to cache
|
||||
private static void loadMazeAbilities() {
|
||||
// Loaded configs count
|
||||
int count = 0;
|
||||
|
||||
// Load summon unit configs
|
||||
for (var summonUnitExcel : GameData.getSummonUnitExcelMap().values()) {
|
||||
if (summonUnitExcel.isIsClient()) {
|
||||
count++;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Get file
|
||||
File file = new File(LunarCore.getConfig().getResourceDir() + "/" + summonUnitExcel.getJsonPath());
|
||||
if (!file.exists()) continue;
|
||||
|
||||
try (FileReader reader = new FileReader(file)) {
|
||||
SummonUnitInfo info = gson.fromJson(reader, SummonUnitInfo.class);
|
||||
info.buildMazeSkillActions();
|
||||
|
||||
summonUnitExcel.setInfo(info);
|
||||
count++;
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
// Notify the server owner if we are missing any files
|
||||
if (count < GameData.getSummonUnitExcelMap().size()) {
|
||||
LunarCore.getLogger().warn("Summon unit configs are missing, please check your resources folder: {resources}/Config/ConfigSummonUnit. Character summon techniques may not work!");
|
||||
}
|
||||
|
||||
// Reset loaded count
|
||||
count = 0;
|
||||
|
||||
// Load maze abilities
|
||||
for (var avatarExcel : GameData.getAvatarExcelMap().values()) {
|
||||
// Get file
|
||||
File file = new File(LunarCore.getConfig().getResourceDir() + "/Config/ConfigAdventureAbility/LocalPlayer/LocalPlayer_" + avatarExcel.getNameKey() + "_Ability.json");
|
||||
|
||||
@@ -2,6 +2,7 @@ package emu.lunarcore.data.config;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import emu.lunarcore.data.GameData;
|
||||
import emu.lunarcore.data.excel.AvatarExcel;
|
||||
import emu.lunarcore.game.battle.skills.*;
|
||||
import lombok.Getter;
|
||||
@@ -27,6 +28,13 @@ public class SkillAbilityInfo {
|
||||
avatarExcel.setMazeSkill(skill);
|
||||
|
||||
actionList = skill.getCastActions();
|
||||
|
||||
// Hacky way to check if an avatar can summon with their skill
|
||||
var summonUnitExcel = GameData.getSummonUnitExcelMap().get((skill.getId() * 10) + 1);
|
||||
if (summonUnitExcel != null && !summonUnitExcel.isIsClient()) {
|
||||
// TODO duration is hardcoded
|
||||
skill.getCastActions().add(new MazeSkillSummonUnit(summonUnitExcel, 20));
|
||||
}
|
||||
} else if (ability.getName().contains("NormalAtk")) {
|
||||
skill = new MazeSkill(avatarExcel, 0);
|
||||
avatarExcel.setMazeAttack(skill);
|
||||
@@ -46,6 +54,7 @@ public class SkillAbilityInfo {
|
||||
}
|
||||
|
||||
// "Simple" way to parse maze attacks/skills
|
||||
// TODO parse tasks better
|
||||
private void parseTask(MazeSkill skill, List<MazeSkillAction> actionList, TaskInfo task) {
|
||||
if (task.getType().contains("AddMazeBuff")) {
|
||||
// TODO get duration from params if buff duration is dynamic
|
||||
@@ -59,7 +68,7 @@ public class SkillAbilityInfo {
|
||||
// TODO get sp increase value from params, also handle target alias
|
||||
actionList.add(new MazeSkillModifySP(50));
|
||||
} else if (task.getType().contains("CreateSummonUnit")) {
|
||||
|
||||
// Ignored
|
||||
} else if (task.getSuccessTaskList() != null) {
|
||||
for (TaskInfo t : task.getSuccessTaskList()) {
|
||||
parseTask(skill, actionList, t);
|
||||
|
||||
75
src/main/java/emu/lunarcore/data/config/SummonUnitInfo.java
Normal file
75
src/main/java/emu/lunarcore/data/config/SummonUnitInfo.java
Normal file
@@ -0,0 +1,75 @@
|
||||
package emu.lunarcore.data.config;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import emu.lunarcore.game.battle.skills.MazeSkillAction;
|
||||
import emu.lunarcore.game.battle.skills.MazeSkillAddBuff;
|
||||
import lombok.Getter;
|
||||
|
||||
/**
|
||||
* Original name: SummonUnitConfig
|
||||
*/
|
||||
@Getter
|
||||
public class SummonUnitInfo {
|
||||
private String AttachPoint;
|
||||
private SummonUnitTriggers TriggerConfig;
|
||||
|
||||
public List<SummonUnitCustomTrigger> getCustomTriggers() {
|
||||
return TriggerConfig.getCustomTriggers();
|
||||
}
|
||||
|
||||
public SummonUnitCustomTrigger getTriggerByName(String name) {
|
||||
return getCustomTriggers().stream()
|
||||
.filter(c -> c.getTriggerName().equals(name))
|
||||
.findFirst()
|
||||
.orElse(null);
|
||||
}
|
||||
|
||||
public void buildMazeSkillActions() {
|
||||
for (var customTrigger : getCustomTriggers()) {
|
||||
customTrigger.buildMazeSkillActions();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Original name: SummonUnitTriggerConfig
|
||||
*/
|
||||
@Getter
|
||||
public static class SummonUnitTriggers {
|
||||
private List<SummonUnitCustomTrigger> CustomTriggers;
|
||||
}
|
||||
|
||||
/**
|
||||
* Original name: UnitCustomTriggerConfig
|
||||
*/
|
||||
@Getter
|
||||
public static class SummonUnitCustomTrigger {
|
||||
private String TriggerName;
|
||||
private List<TaskInfo> OnTriggerEnter;
|
||||
|
||||
private transient List<MazeSkillAction> actions;
|
||||
|
||||
public void buildMazeSkillActions() {
|
||||
// Create actions list
|
||||
this.actions = new ArrayList<>();
|
||||
|
||||
// Sanity check
|
||||
if (this.OnTriggerEnter == null) return;
|
||||
|
||||
// Build maze actions
|
||||
for (var task : this.OnTriggerEnter) {
|
||||
if (task.getType().contains("AddMazeBuff")) {
|
||||
// TODO get duration from params if buff duration is dynamic
|
||||
var actionAddBuff = new MazeSkillAddBuff(task.getID(), 15);
|
||||
actionAddBuff.setSendBuffPacket(true);
|
||||
|
||||
actions.add(actionAddBuff);
|
||||
} else if (task.getType().contains("TriggerHitProp")) {
|
||||
// actions.add(new MazeSkillAddBuff(task.getID(), 20));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
28
src/main/java/emu/lunarcore/data/excel/SummonUnitExcel.java
Normal file
28
src/main/java/emu/lunarcore/data/excel/SummonUnitExcel.java
Normal file
@@ -0,0 +1,28 @@
|
||||
package emu.lunarcore.data.excel;
|
||||
|
||||
import emu.lunarcore.data.GameResource;
|
||||
import emu.lunarcore.data.ResourceType;
|
||||
import emu.lunarcore.data.config.SummonUnitInfo;
|
||||
import lombok.Getter;
|
||||
|
||||
@Getter
|
||||
@ResourceType(name = {"SummonUnitData.json"})
|
||||
public class SummonUnitExcel extends GameResource {
|
||||
private int ID;
|
||||
private String JsonPath;
|
||||
private boolean IsClient;
|
||||
|
||||
private transient SummonUnitInfo info;
|
||||
|
||||
@Override
|
||||
public int getId() {
|
||||
return ID;
|
||||
}
|
||||
|
||||
public void setInfo(SummonUnitInfo info) {
|
||||
if (this.info == null && !this.IsClient) {
|
||||
this.info = info;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -80,9 +80,9 @@ public class BattleService extends BaseGameService {
|
||||
|
||||
if (entity instanceof EntityMonster monster) {
|
||||
monsters.add(monster);
|
||||
} else if (entity instanceof EntityProp) {
|
||||
} else if (entity instanceof EntityProp prop) {
|
||||
it.remove();
|
||||
player.getScene().removeEntity(entity);
|
||||
player.getScene().destroyProp(prop);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@ import java.util.List;
|
||||
import emu.lunarcore.data.excel.AvatarExcel;
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.entity.EntityMonster;
|
||||
import emu.lunarcore.game.scene.entity.GameEntity;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
@@ -47,11 +47,11 @@ public class MazeSkill {
|
||||
}
|
||||
|
||||
// Triggered when player attacks an enemy
|
||||
public void onAttack(GameAvatar caster, List<EntityMonster> monsters) {
|
||||
public void onAttack(GameAvatar caster, List<? extends GameEntity> entities) {
|
||||
if (this.getAttackActions().size() == 0) return;
|
||||
|
||||
for (var action : this.getAttackActions()) {
|
||||
action.onAttack(caster, monsters);
|
||||
action.onAttack(caster, entities);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,7 +4,7 @@ import java.util.List;
|
||||
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.entity.EntityMonster;
|
||||
import emu.lunarcore.game.scene.entity.GameEntity;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
|
||||
public abstract class MazeSkillAction {
|
||||
@@ -13,6 +13,6 @@ public abstract class MazeSkillAction {
|
||||
|
||||
public abstract void onAttack(GameAvatar caster, Battle battle);
|
||||
|
||||
public abstract void onAttack(GameAvatar caster, List<EntityMonster> monsters);
|
||||
public abstract void onAttack(GameAvatar caster, List<? extends GameEntity> entities);
|
||||
|
||||
}
|
||||
|
||||
@@ -5,14 +5,20 @@ import java.util.List;
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.entity.EntityMonster;
|
||||
import emu.lunarcore.game.scene.entity.GameEntity;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
import emu.lunarcore.server.packet.send.PacketSyncEntityBuffChangeListScNotify;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
|
||||
@Getter
|
||||
public class MazeSkillAddBuff extends MazeSkillAction {
|
||||
private int buffId;
|
||||
private int duration;
|
||||
|
||||
@Setter
|
||||
private boolean sendBuffPacket;
|
||||
|
||||
public MazeSkillAddBuff(int buffId, int duration) {
|
||||
this.buffId = buffId;
|
||||
this.duration = duration;
|
||||
@@ -34,9 +40,17 @@ public class MazeSkillAddBuff extends MazeSkillAction {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttack(GameAvatar caster, List<EntityMonster> monsters) {
|
||||
for (EntityMonster monster : monsters) {
|
||||
monster.addBuff(caster.getAvatarId(), buffId, duration);
|
||||
public void onAttack(GameAvatar caster, List<? extends GameEntity> entities) {
|
||||
for (GameEntity entity : entities) {
|
||||
if (entity instanceof EntityMonster monster) {
|
||||
// Add buff to monster
|
||||
var buff = monster.addBuff(caster.getAvatarId(), buffId, duration);
|
||||
|
||||
// Send packet
|
||||
if (buff != null && this.sendBuffPacket) {
|
||||
caster.getOwner().sendPacket(new PacketSyncEntityBuffChangeListScNotify(entity.getEntityId(), buff));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
package emu.lunarcore.game.battle.skills;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.entity.EntityProp;
|
||||
import emu.lunarcore.game.scene.entity.GameEntity;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
import lombok.Getter;
|
||||
|
||||
@Getter
|
||||
public class MazeSkillHitProp extends MazeSkillAction {
|
||||
|
||||
@Override
|
||||
public void onCast(GameAvatar caster, MotionInfo castPosition) {
|
||||
// Skip
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttack(GameAvatar caster, Battle battle) {
|
||||
// Skip
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttack(GameAvatar caster, List<? extends GameEntity> entities) {
|
||||
for (GameEntity entity : entities) {
|
||||
if (entity instanceof EntityProp prop) {
|
||||
caster.getScene().destroyProp(prop);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -4,7 +4,7 @@ import java.util.List;
|
||||
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.entity.EntityMonster;
|
||||
import emu.lunarcore.game.scene.entity.GameEntity;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
|
||||
public class MazeSkillModifyHP extends MazeSkillAction {
|
||||
@@ -25,7 +25,7 @@ public class MazeSkillModifyHP extends MazeSkillAction {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttack(GameAvatar caster, List<EntityMonster> monsters) {
|
||||
public void onAttack(GameAvatar caster, List<? extends GameEntity> entities) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ import java.util.List;
|
||||
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.entity.EntityMonster;
|
||||
import emu.lunarcore.game.scene.entity.GameEntity;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
|
||||
public class MazeSkillModifySP extends MazeSkillAction {
|
||||
@@ -28,7 +28,7 @@ public class MazeSkillModifySP extends MazeSkillAction {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttack(GameAvatar caster, List<EntityMonster> monsters) {
|
||||
public void onAttack(GameAvatar caster, List<? extends GameEntity> entities) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -2,26 +2,37 @@ package emu.lunarcore.game.battle.skills;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import emu.lunarcore.data.excel.SummonUnitExcel;
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.entity.EntityMonster;
|
||||
import emu.lunarcore.game.scene.entity.GameEntity;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
import emu.lunarcore.util.Position;
|
||||
import lombok.Getter;
|
||||
|
||||
@Getter
|
||||
public class MazeSkillSummonUnit extends MazeSkillAction {
|
||||
private SummonUnitExcel excel;
|
||||
private int duration;
|
||||
|
||||
public MazeSkillSummonUnit(SummonUnitExcel excel, int duration) {
|
||||
this.excel = excel;
|
||||
this.duration = duration;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onCast(GameAvatar caster, MotionInfo castPosition) {
|
||||
// TODO Auto-generated method stub
|
||||
caster.getScene().summonUnit(caster, excel, new Position(castPosition.getPos()), new Position(castPosition.getRot()), duration);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttack(GameAvatar caster, Battle battle) {
|
||||
// TODO Auto-generated method stub
|
||||
// Skip
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttack(GameAvatar caster, List<EntityMonster> monsters) {
|
||||
// TODO Auto-generated method stub
|
||||
public void onAttack(GameAvatar caster, List<? extends GameEntity> entities) {
|
||||
// Skip
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -274,9 +274,16 @@ public class Player {
|
||||
}
|
||||
|
||||
public void setWorldLevel(int level) {
|
||||
if (this.worldLevel == level) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worldLevel = level;
|
||||
this.save();
|
||||
this.sendPacket(new PacketPlayerSyncScNotify(this));
|
||||
|
||||
if (this.isOnline()) {
|
||||
this.save();
|
||||
this.getSession().send(new PacketPlayerSyncScNotify(this));
|
||||
}
|
||||
}
|
||||
|
||||
public int getWorldLevel() {
|
||||
@@ -470,7 +477,12 @@ public class Player {
|
||||
}
|
||||
|
||||
public void setBattle(Battle battle) {
|
||||
// Set battle first
|
||||
this.battle = battle;
|
||||
// Scene handler
|
||||
if (this.getScene() != null) {
|
||||
this.getScene().onBattleStart(battle);
|
||||
}
|
||||
}
|
||||
|
||||
public void forceQuitBattle() {
|
||||
@@ -572,7 +584,7 @@ public class Player {
|
||||
// Finish puzzle
|
||||
prop.setState(PropState.Locked);
|
||||
// Trigger event
|
||||
this.getScene().invokeTrigger(PropTriggerType.PUZZLE_FINISH, prop.getGroupId(), prop.getInstId());
|
||||
this.getScene().invokePropTrigger(PropTriggerType.PUZZLE_FINISH, prop.getGroupId(), prop.getInstId());
|
||||
//
|
||||
return prop;
|
||||
}
|
||||
@@ -711,7 +723,12 @@ public class Player {
|
||||
}
|
||||
|
||||
public void onTick() {
|
||||
// Update stamina
|
||||
this.updateStamina();
|
||||
// Scene update
|
||||
if (this.getScene() != null) {
|
||||
this.getScene().onTick();
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
|
||||
@@ -6,22 +6,27 @@ import java.util.List;
|
||||
import emu.lunarcore.data.GameData;
|
||||
import emu.lunarcore.data.config.*;
|
||||
import emu.lunarcore.data.excel.MazePlaneExcel;
|
||||
import emu.lunarcore.data.excel.SummonUnitExcel;
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.enums.PlaneType;
|
||||
import emu.lunarcore.game.scene.entity.*;
|
||||
import emu.lunarcore.game.scene.triggers.PropTrigger;
|
||||
import emu.lunarcore.game.scene.triggers.PropTriggerType;
|
||||
import emu.lunarcore.game.player.Player;
|
||||
import emu.lunarcore.game.player.lineup.PlayerLineup;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
import emu.lunarcore.proto.SceneEntityGroupInfoOuterClass.SceneEntityGroupInfo;
|
||||
import emu.lunarcore.proto.SceneGroupStateOuterClass.SceneGroupState;
|
||||
import emu.lunarcore.proto.SceneInfoOuterClass.SceneInfo;
|
||||
import emu.lunarcore.server.packet.send.PacketActivateFarmElementScRsp;
|
||||
import emu.lunarcore.server.packet.send.PacketRefreshTriggerByClientScNotify;
|
||||
import emu.lunarcore.server.packet.send.PacketSceneGroupRefreshScNotify;
|
||||
|
||||
import emu.lunarcore.util.Position;
|
||||
import it.unimi.dsi.fastutil.ints.*;
|
||||
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
|
||||
import lombok.Getter;
|
||||
import us.hebi.quickbuf.RepeatedInt;
|
||||
|
||||
@Getter
|
||||
public class Scene {
|
||||
@@ -39,6 +44,7 @@ public class Scene {
|
||||
// Avatar entites
|
||||
private final IntSet avatarEntityIds;
|
||||
private final Int2ObjectMap<GameAvatar> avatars;
|
||||
private EntitySummonUnit playerSummon;
|
||||
|
||||
// Other entities
|
||||
private final Int2ObjectMap<GameEntity> entities;
|
||||
@@ -208,6 +214,64 @@ public class Scene {
|
||||
return true;
|
||||
}
|
||||
|
||||
// Summons
|
||||
|
||||
public synchronized void summonUnit(GameAvatar caster, SummonUnitExcel excel, Position pos, Position rot, int duration) {
|
||||
// Remove previous summon
|
||||
this.removeSummonUnit();
|
||||
|
||||
// Add a new summoned unit to scene
|
||||
var summon = new EntitySummonUnit(this, caster, excel, pos, rot);
|
||||
summon.setDuration(duration);
|
||||
|
||||
this.addEntity(summon, true);
|
||||
}
|
||||
|
||||
public synchronized void removeSummonUnit() {
|
||||
if (this.getPlayerSummon() != null) {
|
||||
this.removeEntity(this.getPlayerSummon());
|
||||
}
|
||||
}
|
||||
|
||||
public void handleSummonUnitTriggers(int entityId, String name, MotionInfo motion, RepeatedInt targetIds) {
|
||||
// Get summon unit
|
||||
EntitySummonUnit summonUnit = null;
|
||||
|
||||
var entity = this.getEntityById(entityId);
|
||||
if (entity instanceof EntitySummonUnit) {
|
||||
summonUnit = (EntitySummonUnit) entity;
|
||||
} else {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get trigger
|
||||
var trigger = summonUnit.getExcel().getInfo().getTriggerByName(name);
|
||||
if (trigger == null) return;
|
||||
|
||||
// Get targets
|
||||
var targets = new ArrayList<GameEntity>();
|
||||
|
||||
for (int targetId : targetIds) {
|
||||
var target = this.getEntityById(targetId);
|
||||
if (target != null) {
|
||||
targets.add(target);
|
||||
}
|
||||
}
|
||||
|
||||
// Handle task actions
|
||||
for (var action : trigger.getActions()) {
|
||||
action.onAttack(summonUnit.getCaster(), targets);
|
||||
}
|
||||
|
||||
// Send packet
|
||||
this.getPlayer().sendPacket(new PacketRefreshTriggerByClientScNotify(entityId, name, targetIds));
|
||||
}
|
||||
|
||||
public void destroyProp(EntityProp prop) {
|
||||
// TODO sanity check prop to make sure it can be destroyed
|
||||
this.removeEntity(prop);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the nearest spring (Space Anchor) to the player in the scene
|
||||
* @return
|
||||
@@ -238,7 +302,7 @@ public class Scene {
|
||||
return spring;
|
||||
}
|
||||
|
||||
public void invokeTrigger(PropTriggerType type, int param1, int param2) {
|
||||
public void invokePropTrigger(PropTriggerType type, int param1, int param2) {
|
||||
for (PropTrigger trigger : this.getTriggers()) {
|
||||
if (trigger.shouldRun(param1, param2)) {
|
||||
trigger.run(this);
|
||||
@@ -286,6 +350,26 @@ public class Scene {
|
||||
}
|
||||
}
|
||||
|
||||
// Player events
|
||||
|
||||
public void onTick() {
|
||||
// Remove summoned unit if it expired
|
||||
if (this.getPlayerSummon() != null) {
|
||||
if (this.getPlayerSummon().isExpired()) {
|
||||
this.removeSummonUnit();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void onBattleStart(Battle battle) {
|
||||
// Remove summoned unit
|
||||
if (this.getPlayerSummon() != null) {
|
||||
this.removeSummonUnit();
|
||||
}
|
||||
}
|
||||
|
||||
// Proto serialization
|
||||
|
||||
public synchronized SceneInfo toProto() {
|
||||
// Set loaded flag
|
||||
this.loaded = true;
|
||||
|
||||
37
src/main/java/emu/lunarcore/game/scene/SceneBuff.java
Normal file
37
src/main/java/emu/lunarcore/game/scene/SceneBuff.java
Normal file
@@ -0,0 +1,37 @@
|
||||
package emu.lunarcore.game.scene;
|
||||
|
||||
import emu.lunarcore.proto.BuffInfoOuterClass.BuffInfo;
|
||||
import lombok.Getter;
|
||||
|
||||
@Getter
|
||||
public class SceneBuff {
|
||||
private int casterAvatarId; // Owner avatar id
|
||||
private int buffId;
|
||||
private int buffLevel;
|
||||
private int duration;
|
||||
private long createTime;
|
||||
private long expiry;
|
||||
|
||||
public SceneBuff(int casterAvatarId, int buffId, int seconds) {
|
||||
this.casterAvatarId = casterAvatarId;
|
||||
this.buffId = buffId;
|
||||
this.buffLevel = 1;
|
||||
this.createTime = System.currentTimeMillis();
|
||||
this.duration = seconds * 1000;
|
||||
this.expiry = this.createTime + duration;
|
||||
}
|
||||
|
||||
// Serialization
|
||||
|
||||
public BuffInfo toProto() {
|
||||
var proto = BuffInfo.newInstance()
|
||||
.setBuffId(this.getBuffId())
|
||||
.setLevel(this.getBuffLevel())
|
||||
.setBaseAvatarId(this.getCasterAvatarId())
|
||||
.setAddTimeMs(this.getCreateTime())
|
||||
.setLifeTime(this.getDuration() / 10)
|
||||
.setCount(1);
|
||||
|
||||
return proto;
|
||||
}
|
||||
}
|
||||
@@ -1,16 +0,0 @@
|
||||
package emu.lunarcore.game.scene;
|
||||
|
||||
import lombok.Getter;
|
||||
|
||||
@Getter
|
||||
public class SceneEntityBuff {
|
||||
private int owner; // Owner avatar id
|
||||
private int id;
|
||||
private long expiry;
|
||||
|
||||
public SceneEntityBuff(int owner, int id, long duration) {
|
||||
this.owner = owner;
|
||||
this.id = id;
|
||||
this.expiry = System.currentTimeMillis() + (duration * 1000);
|
||||
}
|
||||
}
|
||||
@@ -5,7 +5,7 @@ import emu.lunarcore.data.config.MonsterInfo;
|
||||
import emu.lunarcore.data.excel.NpcMonsterExcel;
|
||||
import emu.lunarcore.game.battle.Battle;
|
||||
import emu.lunarcore.game.scene.Scene;
|
||||
import emu.lunarcore.game.scene.SceneEntityBuff;
|
||||
import emu.lunarcore.game.scene.SceneBuff;
|
||||
import emu.lunarcore.game.scene.triggers.PropTriggerType;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
import emu.lunarcore.proto.SceneEntityInfoOuterClass.SceneEntityInfo;
|
||||
@@ -29,7 +29,7 @@ public class EntityMonster implements GameEntity {
|
||||
private final Position pos;
|
||||
private final Position rot;
|
||||
|
||||
private Int2ObjectMap<SceneEntityBuff> buffs;
|
||||
private Int2ObjectMap<SceneBuff> buffs;
|
||||
private int farmElementId;
|
||||
@Setter private int overrideStageId;
|
||||
@Setter private int overrideLevel;
|
||||
@@ -56,12 +56,17 @@ public class EntityMonster implements GameEntity {
|
||||
}
|
||||
}
|
||||
|
||||
public void addBuff(int caster, int buffId, int duration) {
|
||||
public SceneBuff addBuff(int caster, int buffId, int duration) {
|
||||
if (this.buffs == null) {
|
||||
this.buffs = new Int2ObjectOpenHashMap<>();
|
||||
}
|
||||
|
||||
this.buffs.put(buffId, new SceneEntityBuff(caster, buffId, duration));
|
||||
// Create buff
|
||||
var buff = new SceneBuff(caster, buffId, duration);
|
||||
|
||||
// Add to buff map
|
||||
this.buffs.put(buffId, buff);
|
||||
return buff;
|
||||
}
|
||||
|
||||
public void applyBuffs(Battle battle) {
|
||||
@@ -79,7 +84,7 @@ public class EntityMonster implements GameEntity {
|
||||
}
|
||||
|
||||
// Get owner index
|
||||
int ownerIndex = battle.getLineup().indexOf(entry.getValue().getOwner());
|
||||
int ownerIndex = battle.getLineup().indexOf(entry.getValue().getCasterAvatarId());
|
||||
|
||||
// Add buff to battle if owner exists
|
||||
if (ownerIndex != -1) {
|
||||
@@ -92,7 +97,7 @@ public class EntityMonster implements GameEntity {
|
||||
@Override
|
||||
public void onRemove() {
|
||||
// Try to fire any triggers
|
||||
getScene().invokeTrigger(PropTriggerType.MONSTER_DIE, this.getGroupId(), this.getInstId());
|
||||
getScene().invokePropTrigger(PropTriggerType.MONSTER_DIE, this.getGroupId(), this.getInstId());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -0,0 +1,72 @@
|
||||
package emu.lunarcore.game.scene.entity;
|
||||
|
||||
import emu.lunarcore.data.excel.SummonUnitExcel;
|
||||
import emu.lunarcore.game.avatar.GameAvatar;
|
||||
import emu.lunarcore.game.scene.Scene;
|
||||
import emu.lunarcore.proto.MotionInfoOuterClass.MotionInfo;
|
||||
import emu.lunarcore.proto.SceneEntityInfoOuterClass.SceneEntityInfo;
|
||||
import emu.lunarcore.proto.SceneSummonUnitInfoOuterClass.SceneSummonUnitInfo;
|
||||
import emu.lunarcore.util.Position;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
|
||||
@Getter
|
||||
public class EntitySummonUnit implements GameEntity {
|
||||
@Setter private int entityId;
|
||||
private final GameAvatar caster;
|
||||
private final SummonUnitExcel excel;
|
||||
|
||||
private final Scene scene;
|
||||
private final Position pos;
|
||||
private final Position rot;
|
||||
private final long createTime;
|
||||
|
||||
private int attachedEntityId;
|
||||
private int duration;
|
||||
private long expiry;
|
||||
|
||||
public EntitySummonUnit(Scene scene, GameAvatar caster, SummonUnitExcel excel, Position pos, Position rot) {
|
||||
this.scene = scene;
|
||||
this.caster = caster;
|
||||
this.excel = excel;
|
||||
this.pos = pos;
|
||||
this.rot = rot;
|
||||
this.createTime = System.currentTimeMillis();
|
||||
|
||||
// Attach summon unit to an entity
|
||||
String attachPoint = excel.getInfo().getAttachPoint();
|
||||
if (attachPoint != null && attachPoint.equals("Origin")) {
|
||||
this.attachedEntityId = caster.getEntityId();
|
||||
}
|
||||
}
|
||||
|
||||
public void setDuration(int seconds) {
|
||||
this.duration = seconds * 1000;
|
||||
this.expiry = this.createTime + duration;
|
||||
}
|
||||
|
||||
public boolean isExpired() {
|
||||
return System.currentTimeMillis() > this.expiry;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SceneEntityInfo toSceneEntityProto() {
|
||||
var summon = SceneSummonUnitInfo.newInstance()
|
||||
.setLifeTimeMs(this.getDuration())
|
||||
.setCreateTimeMs(this.getCreateTime())
|
||||
.setCasterEntityId(this.getCaster().getEntityId())
|
||||
.setAttachEntityId(this.getAttachedEntityId())
|
||||
.setSummonUnitId(this.getExcel().getId());
|
||||
|
||||
for (var trigger : this.getExcel().getInfo().getCustomTriggers()) {
|
||||
summon.addCustomTriggers(trigger.getTriggerName());
|
||||
}
|
||||
|
||||
var proto = SceneEntityInfo.newInstance()
|
||||
.setEntityId(this.getEntityId())
|
||||
.setMotion(MotionInfo.newInstance().setPos(getPos().toProto()).setRot(getRot().toProto()))
|
||||
.setSummonUnit(summon);
|
||||
|
||||
return proto;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
package emu.lunarcore.server.packet.recv;
|
||||
|
||||
import emu.lunarcore.proto.RefreshTriggerByClientCsReqOuterClass.RefreshTriggerByClientCsReq;
|
||||
import emu.lunarcore.server.game.GameSession;
|
||||
import emu.lunarcore.server.packet.CmdId;
|
||||
import emu.lunarcore.server.packet.Opcodes;
|
||||
import emu.lunarcore.server.packet.PacketHandler;
|
||||
import emu.lunarcore.server.packet.send.PacketRefreshTriggerByClientScRsp;
|
||||
|
||||
@Opcodes(CmdId.RefreshTriggerByClientCsReq)
|
||||
public class HandlerRefreshTriggerByClientCsReq extends PacketHandler {
|
||||
|
||||
@Override
|
||||
public void handle(GameSession session, byte[] data) throws Exception {
|
||||
var req = RefreshTriggerByClientCsReq.parseFrom(data);
|
||||
|
||||
if (session.getPlayer().getScene() != null) {
|
||||
session.getPlayer().getScene().handleSummonUnitTriggers(
|
||||
req.getTriggerEntityId(),
|
||||
req.getTriggerName(),
|
||||
req.getTriggerMotion(),
|
||||
req.getTriggerTargetIdList()
|
||||
);
|
||||
}
|
||||
|
||||
session.send(new PacketRefreshTriggerByClientScRsp(req));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
package emu.lunarcore.server.packet.send;
|
||||
|
||||
import emu.lunarcore.proto.RefreshTriggerByClientScNotifyOuterClass.RefreshTriggerByClientScNotify;
|
||||
import emu.lunarcore.server.packet.BasePacket;
|
||||
import emu.lunarcore.server.packet.CmdId;
|
||||
import us.hebi.quickbuf.RepeatedInt;
|
||||
|
||||
public class PacketRefreshTriggerByClientScNotify extends BasePacket {
|
||||
|
||||
public PacketRefreshTriggerByClientScNotify(int triggerEntityId, String name, RepeatedInt targetIds) {
|
||||
super(CmdId.RefreshTriggerByClientScNotify);
|
||||
|
||||
var data = RefreshTriggerByClientScNotify.newInstance()
|
||||
.setTriggerName(name)
|
||||
.setTriggerEntityId(triggerEntityId);
|
||||
|
||||
for (int id : targetIds) {
|
||||
data.addTriggerTargetIdList(id);
|
||||
}
|
||||
|
||||
this.setData(data);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
package emu.lunarcore.server.packet.send;
|
||||
|
||||
import emu.lunarcore.proto.RefreshTriggerByClientCsReqOuterClass.RefreshTriggerByClientCsReq;
|
||||
import emu.lunarcore.proto.RefreshTriggerByClientScRspOuterClass.RefreshTriggerByClientScRsp;
|
||||
import emu.lunarcore.server.packet.BasePacket;
|
||||
import emu.lunarcore.server.packet.CmdId;
|
||||
|
||||
public class PacketRefreshTriggerByClientScRsp extends BasePacket {
|
||||
|
||||
public PacketRefreshTriggerByClientScRsp(RefreshTriggerByClientCsReq req) {
|
||||
super(CmdId.RefreshTriggerByClientScRsp);
|
||||
|
||||
var data = RefreshTriggerByClientScRsp.newInstance()
|
||||
.setTriggerEntityId(req.getTriggerEntityId())
|
||||
.setTriggerName(req.getTriggerName())
|
||||
.setRefreshTrigger(true);
|
||||
|
||||
this.setData(data);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
package emu.lunarcore.server.packet.send;
|
||||
|
||||
import emu.lunarcore.game.scene.SceneBuff;
|
||||
import emu.lunarcore.proto.EntityBuffChangeInfoOuterClass.EntityBuffChangeInfo;
|
||||
import emu.lunarcore.proto.SyncEntityBuffChangeListScNotifyOuterClass.SyncEntityBuffChangeListScNotify;
|
||||
import emu.lunarcore.server.packet.BasePacket;
|
||||
import emu.lunarcore.server.packet.CmdId;
|
||||
|
||||
public class PacketSyncEntityBuffChangeListScNotify extends BasePacket {
|
||||
|
||||
public PacketSyncEntityBuffChangeListScNotify(int entityId, SceneBuff buff) {
|
||||
super(CmdId.SyncEntityBuffChangeListScNotify);
|
||||
|
||||
var buffChange = EntityBuffChangeInfo.newInstance().setEntityId(entityId)
|
||||
.setBuffChangeInfo(buff.toProto())
|
||||
.setEntityId(entityId);
|
||||
|
||||
var data = SyncEntityBuffChangeListScNotify.newInstance()
|
||||
.addEntityBuffInfoList(buffChange);
|
||||
|
||||
this.setData(data);
|
||||
}
|
||||
}
|
||||
@@ -24,6 +24,12 @@ public class Position {
|
||||
this.y = position.getY();
|
||||
this.z = position.getZ();
|
||||
}
|
||||
|
||||
public Position(Vector vector) {
|
||||
this.x = vector.getX();
|
||||
this.y = vector.getY();
|
||||
this.z = vector.getZ();
|
||||
}
|
||||
|
||||
public int getX() {
|
||||
return x;
|
||||
|
||||
Reference in New Issue
Block a user