From 5a09c22aa1987641f15c6ca728bf554b518f9eec Mon Sep 17 00:00:00 2001 From: Melledy <52122272+Melledy@users.noreply.github.com> Date: Wed, 20 Apr 2022 03:42:59 -0700 Subject: [PATCH] Fix character abilities not showing for others in co-op/lasting too long --- .../emu/grasscutter/game/GenshinPlayer.java | 7 +++++ .../HandlerClientAbilityInitFinishNotify.java | 26 +++++++++++++++++ .../HandlerSetEntityClientDataNotify.java | 11 ++++++- .../PacketClientAbilityInitFinishNotify.java | 29 +++++++++++++++++++ 4 files changed, 72 insertions(+), 1 deletion(-) create mode 100644 src/main/java/emu/grasscutter/server/packet/recv/HandlerClientAbilityInitFinishNotify.java create mode 100644 src/main/java/emu/grasscutter/server/packet/send/PacketClientAbilityInitFinishNotify.java diff --git a/src/main/java/emu/grasscutter/game/GenshinPlayer.java b/src/main/java/emu/grasscutter/game/GenshinPlayer.java index 70fea04f0..1d8650e54 100644 --- a/src/main/java/emu/grasscutter/game/GenshinPlayer.java +++ b/src/main/java/emu/grasscutter/game/GenshinPlayer.java @@ -38,6 +38,7 @@ import emu.grasscutter.server.packet.send.PacketAvatarAddNotify; import emu.grasscutter.server.packet.send.PacketAvatarDataNotify; import emu.grasscutter.server.packet.send.PacketAvatarGainCostumeNotify; import emu.grasscutter.server.packet.send.PacketAvatarGainFlycloakNotify; +import emu.grasscutter.server.packet.send.PacketClientAbilityInitFinishNotify; import emu.grasscutter.server.packet.send.PacketCombatInvocationsNotify; import emu.grasscutter.server.packet.send.PacketGadgetInteractRsp; import emu.grasscutter.server.packet.send.PacketItemAddHintNotify; @@ -104,6 +105,7 @@ public class GenshinPlayer { @Transient private final Int2ObjectMap coopRequests; @Transient private final InvokeHandler combatInvokeHandler; @Transient private final InvokeHandler abilityInvokeHandler; + @Transient private final InvokeHandler clientAbilityInitFinishHandler; @Deprecated @SuppressWarnings({ "rawtypes", "unchecked" }) // Morphia only! public GenshinPlayer() { @@ -126,6 +128,7 @@ public class GenshinPlayer { this.coopRequests = new Int2ObjectOpenHashMap<>(); this.combatInvokeHandler = new InvokeHandler(PacketCombatInvocationsNotify.class); this.abilityInvokeHandler = new InvokeHandler(PacketAbilityInvocationsNotify.class); + this.clientAbilityInitFinishHandler = new InvokeHandler(PacketClientAbilityInitFinishNotify.class); } // On player creation @@ -389,6 +392,10 @@ public class GenshinPlayer { return this.abilityInvokeHandler; } + public InvokeHandler getClientAbilityInitFinishHandler() { + return clientAbilityInitFinishHandler; + } + public void setMpSetting(MpSettingType mpSetting) { this.mpSetting = mpSetting; } diff --git a/src/main/java/emu/grasscutter/server/packet/recv/HandlerClientAbilityInitFinishNotify.java b/src/main/java/emu/grasscutter/server/packet/recv/HandlerClientAbilityInitFinishNotify.java new file mode 100644 index 000000000..cfe697b91 --- /dev/null +++ b/src/main/java/emu/grasscutter/server/packet/recv/HandlerClientAbilityInitFinishNotify.java @@ -0,0 +1,26 @@ +package emu.grasscutter.server.packet.recv; + +import emu.grasscutter.net.packet.Opcodes; +import emu.grasscutter.net.packet.PacketOpcodes; +import emu.grasscutter.net.proto.AbilityInvokeEntryOuterClass.AbilityInvokeEntry; +import emu.grasscutter.net.proto.ClientAbilityInitFinishNotifyOuterClass.ClientAbilityInitFinishNotify; +import emu.grasscutter.net.packet.PacketHandler; +import emu.grasscutter.server.game.GameSession; + +@Opcodes(PacketOpcodes.ClientAbilityInitFinishNotify) +public class HandlerClientAbilityInitFinishNotify extends PacketHandler { + + @Override + public void handle(GameSession session, byte[] header, byte[] payload) throws Exception { + ClientAbilityInitFinishNotify notif = ClientAbilityInitFinishNotify.parseFrom(payload); + + for (AbilityInvokeEntry entry : notif.getInvokesList()) { + session.getPlayer().getClientAbilityInitFinishHandler().addEntry(entry.getForwardType(), entry); + } + + if (notif.getInvokesList().size() > 0) { + session.getPlayer().getClientAbilityInitFinishHandler().update(session.getPlayer()); + } + } + +} diff --git a/src/main/java/emu/grasscutter/server/packet/recv/HandlerSetEntityClientDataNotify.java b/src/main/java/emu/grasscutter/server/packet/recv/HandlerSetEntityClientDataNotify.java index accbd253d..1a60f677b 100644 --- a/src/main/java/emu/grasscutter/server/packet/recv/HandlerSetEntityClientDataNotify.java +++ b/src/main/java/emu/grasscutter/server/packet/recv/HandlerSetEntityClientDataNotify.java @@ -1,5 +1,6 @@ package emu.grasscutter.server.packet.recv; +import emu.grasscutter.net.packet.GenshinPacket; import emu.grasscutter.net.packet.Opcodes; import emu.grasscutter.net.packet.PacketOpcodes; import emu.grasscutter.net.packet.PacketHandler; @@ -10,7 +11,15 @@ public class HandlerSetEntityClientDataNotify extends PacketHandler { @Override public void handle(GameSession session, byte[] header, byte[] payload) throws Exception { - // Auto template + // Skip if there is no one to broadcast it too + if (session.getPlayer().getScene().getPlayerCount() <= 1) { + return; + } + + GenshinPacket packet = new GenshinPacket(PacketOpcodes.SetEntityClientDataNotify, true); + packet.setData(payload); + + session.getPlayer().getScene().broadcastPacketToOthers(session.getPlayer(), packet); } } diff --git a/src/main/java/emu/grasscutter/server/packet/send/PacketClientAbilityInitFinishNotify.java b/src/main/java/emu/grasscutter/server/packet/send/PacketClientAbilityInitFinishNotify.java new file mode 100644 index 000000000..dc676c4d1 --- /dev/null +++ b/src/main/java/emu/grasscutter/server/packet/send/PacketClientAbilityInitFinishNotify.java @@ -0,0 +1,29 @@ +package emu.grasscutter.server.packet.send; + +import java.util.List; + +import emu.grasscutter.net.packet.GenshinPacket; +import emu.grasscutter.net.packet.PacketOpcodes; +import emu.grasscutter.net.proto.AbilityInvokeEntryOuterClass.AbilityInvokeEntry; +import emu.grasscutter.net.proto.ClientAbilityInitFinishNotifyOuterClass.ClientAbilityInitFinishNotify; + +public class PacketClientAbilityInitFinishNotify extends GenshinPacket { + + public PacketClientAbilityInitFinishNotify(List entries) { + super(PacketOpcodes.ClientAbilityInitFinishNotify, true); + + int entityId = 0; + + if (entries.size() > 0) { + AbilityInvokeEntry entry = entries.get(0); + entityId = entry.getEntityId(); + } + + ClientAbilityInitFinishNotify proto = ClientAbilityInitFinishNotify.newBuilder() + .setEntityId(entityId) + .addAllInvokes(entries) + .build(); + + this.setData(proto); + } +}