This commit is contained in:
Tim203 2019-10-04 19:25:08 +02:00
parent ee97585036
commit 89550a5ecb
9 changed files with 154 additions and 79 deletions

View file

@ -297,7 +297,7 @@ public class GeyserSession implements Player {
startGamePacket.setCurrentTick(0); startGamePacket.setCurrentTick(0);
startGamePacket.setEnchantmentSeed(0); startGamePacket.setEnchantmentSeed(0);
startGamePacket.setMultiplayerCorrelationId(""); startGamePacket.setMultiplayerCorrelationId("");
startGamePacket.setCachedPalette(Toolbox.CACHED_PALLETE.copy()); startGamePacket.setCachedPalette(Toolbox.CACHED_PALLETE.retainedDuplicate());
startGamePacket.setItemEntries(Toolbox.ITEMS); startGamePacket.setItemEntries(Toolbox.ITEMS);
upstream.sendPacket(startGamePacket); upstream.sendPacket(startGamePacket);

View file

@ -43,12 +43,16 @@ public class JavaChatTranslator extends PacketTranslator<ServerChatPacket> {
switch (packet.getType()) { switch (packet.getType()) {
case CHAT: case CHAT:
textPacket.setType(TextPacket.Type.CHAT); textPacket.setType(TextPacket.Type.CHAT);
break;
case SYSTEM: case SYSTEM:
textPacket.setType(TextPacket.Type.SYSTEM); textPacket.setType(TextPacket.Type.SYSTEM);
break;
case NOTIFICATION: case NOTIFICATION:
textPacket.setType(TextPacket.Type.TIP); textPacket.setType(TextPacket.Type.TIP);
break;
default: default:
textPacket.setType(TextPacket.Type.RAW); textPacket.setType(TextPacket.Type.RAW);
break;
} }
if (packet.getMessage() instanceof TranslationMessage) { if (packet.getMessage() instanceof TranslationMessage) {

View file

@ -22,7 +22,7 @@ public class JavaPlayerListEntryTranslator extends PacketTranslator<ServerPlayer
PlayerListPacket.Entry entry1 = new PlayerListPacket.Entry(entry.getProfile().getId()); PlayerListPacket.Entry entry1 = new PlayerListPacket.Entry(entry.getProfile().getId());
if (packet.getAction() == PlayerListEntryAction.ADD_PLAYER) { if (packet.getAction() == PlayerListEntryAction.ADD_PLAYER) {
boolean self = session.getPlayerEntity().getUuid().equals(entry.getProfile().getId()); boolean self = entry.getProfile().getId().equals(session.getPlayerEntity().getUuid());
PlayerEntity playerEntity = session.getPlayerEntity(); PlayerEntity playerEntity = session.getPlayerEntity();
if (!self) { if (!self) {

View file

@ -25,45 +25,39 @@
package org.geysermc.connector.network.translators.java.scoreboard; package org.geysermc.connector.network.translators.java.scoreboard;
import com.github.steveice10.mc.protocol.data.game.scoreboard.ObjectiveAction;
import com.github.steveice10.mc.protocol.packet.ingame.server.scoreboard.ServerScoreboardObjectivePacket; import com.github.steveice10.mc.protocol.packet.ingame.server.scoreboard.ServerScoreboardObjectivePacket;
import org.geysermc.connector.network.session.GeyserSession; import org.geysermc.connector.network.session.GeyserSession;
import org.geysermc.connector.network.session.cache.ScoreboardCache; import org.geysermc.connector.network.session.cache.ScoreboardCache;
import org.geysermc.connector.network.translators.PacketTranslator; import org.geysermc.connector.network.translators.PacketTranslator;
import org.geysermc.connector.scoreboard.Scoreboard;
import org.geysermc.connector.scoreboard.Objective; import org.geysermc.connector.scoreboard.Objective;
import org.geysermc.connector.scoreboard.Scoreboard;
import org.geysermc.connector.utils.MessageUtils; import org.geysermc.connector.utils.MessageUtils;
public class JavaScoreboardObjectiveTranslator extends PacketTranslator<ServerScoreboardObjectivePacket> { public class JavaScoreboardObjectiveTranslator extends PacketTranslator<ServerScoreboardObjectivePacket> {
@Override @Override
public void translate(ServerScoreboardObjectivePacket packet, GeyserSession session) { public void translate(ServerScoreboardObjectivePacket packet, GeyserSession session) {
try {
ScoreboardCache cache = session.getScoreboardCache(); ScoreboardCache cache = session.getScoreboardCache();
Scoreboard scoreboard = cache.getScoreboard(); Scoreboard scoreboard = cache.getScoreboard();
if (scoreboard.getObjective(packet.getName()) == null) { Objective objective = scoreboard.getObjective(packet.getName());
// whoops sent objective to early, ignore it
return; if (objective == null && packet.getAction() != ObjectiveAction.REMOVE) {
objective = scoreboard.registerNewObjective(packet.getName(), true);
} }
switch (packet.getAction()) { switch (packet.getAction()) {
case ADD: case ADD:
Objective objective = scoreboard.getObjective(packet.getName()); case UPDATE:
objective.setDisplayName(MessageUtils.getBedrockMessage(packet.getDisplayName())); objective.setDisplayName(MessageUtils.getBedrockMessage(packet.getDisplayName()));
objective.setType(packet.getType().ordinal()); objective.setType(packet.getType().ordinal());
break; break;
case UPDATE:
Objective updateObj = scoreboard.getObjective(packet.getName());
updateObj.setDisplayName(MessageUtils.getBedrockMessage(packet.getDisplayName()));
break;
case REMOVE: case REMOVE:
scoreboard.unregisterObjective(packet.getName()); scoreboard.unregisterObjective(packet.getName());
break; break;
} }
scoreboard.onUpdate(); if (objective != null && !objective.isTemp()) scoreboard.onUpdate();
} catch (Exception ex) {
ex.printStackTrace();
}
} }
} }

View file

@ -25,12 +25,13 @@
package org.geysermc.connector.network.translators.java.scoreboard; package org.geysermc.connector.network.translators.java.scoreboard;
import com.github.steveice10.mc.protocol.data.game.scoreboard.ScoreboardAction;
import com.github.steveice10.mc.protocol.packet.ingame.server.scoreboard.ServerUpdateScorePacket; import com.github.steveice10.mc.protocol.packet.ingame.server.scoreboard.ServerUpdateScorePacket;
import org.geysermc.api.Geyser; import org.geysermc.api.Geyser;
import org.geysermc.connector.network.session.GeyserSession; import org.geysermc.connector.network.session.GeyserSession;
import org.geysermc.connector.network.translators.PacketTranslator; import org.geysermc.connector.network.translators.PacketTranslator;
import org.geysermc.connector.scoreboard.Scoreboard;
import org.geysermc.connector.scoreboard.Objective; import org.geysermc.connector.scoreboard.Objective;
import org.geysermc.connector.scoreboard.Scoreboard;
public class JavaUpdateScoreTranslator extends PacketTranslator<ServerUpdateScorePacket> { public class JavaUpdateScoreTranslator extends PacketTranslator<ServerUpdateScorePacket> {
@ -40,18 +41,24 @@ public class JavaUpdateScoreTranslator extends PacketTranslator<ServerUpdateScor
Scoreboard scoreboard = session.getScoreboardCache().getScoreboard(); Scoreboard scoreboard = session.getScoreboardCache().getScoreboard();
Objective objective = scoreboard.getObjective(packet.getObjective()); Objective objective = scoreboard.getObjective(packet.getObjective());
if (objective == null) { if (objective == null && packet.getAction() != ScoreboardAction.REMOVE) {
Geyser.getLogger().info("Tried to update score without the existence of its requested objective"); Geyser.getLogger().info("Tried to update score without the existence of its requested objective '" + packet.getObjective() + '\'');
return; return;
} }
switch (packet.getAction()) { switch (packet.getAction()) {
case REMOVE:
objective.resetScore(packet.getEntry());
break;
case ADD_OR_UPDATE: case ADD_OR_UPDATE:
objective.setScore(packet.getEntry(), packet.getValue()); objective.setScore(packet.getEntry(), packet.getValue());
break; break;
case REMOVE:
if (objective != null) {
objective.resetScore(packet.getEntry());
} else {
for (Objective objective1 : scoreboard.getObjectives().values()) {
objective1.resetScore(packet.getEntry());
}
}
break;
} }
scoreboard.onUpdate(); scoreboard.onUpdate();
} catch (Exception ex) { } catch (Exception ex) {

View file

@ -36,23 +36,37 @@ import java.util.Map;
public class Objective { public class Objective {
private Scoreboard scoreboard; private Scoreboard scoreboard;
private long id; private long id;
private boolean temp;
@Setter @Setter
private UpdateType updateType = UpdateType.ADD; private UpdateType updateType = UpdateType.ADD;
private String objectiveName; private String objectiveName;
private String displaySlot; private String displaySlot;
private String displayName; private String displayName = "unknown";
private int type; // 0 = integer, 1 = heart private int type = 0; // 0 = integer, 1 = heart
private Map<String, Score> scores = new HashMap<>(); private Map<String, Score> scores = new HashMap<>();
private Objective(Scoreboard scoreboard) {
this.id = scoreboard.getNextId().getAndIncrement();
this.scoreboard = scoreboard;
}
/**
* /!\ This method is made for temporary objectives until the real objective is received
*/
public Objective(Scoreboard scoreboard, String objectiveName) {
this(scoreboard);
this.objectiveName = objectiveName;
this.temp = true;
}
public Objective(Scoreboard scoreboard, String objectiveName, ScoreboardPosition displaySlot, String displayName, int type) { public Objective(Scoreboard scoreboard, String objectiveName, ScoreboardPosition displaySlot, String displayName, int type) {
this(scoreboard, objectiveName, displaySlot.name().toLowerCase(), displayName, type); this(scoreboard, objectiveName, displaySlot.name().toLowerCase(), displayName, type);
} }
public Objective(Scoreboard scoreboard, String objectiveName, String displaySlot, String displayName, int type) { public Objective(Scoreboard scoreboard, String objectiveName, String displaySlot, String displayName, int type) {
this.scoreboard = scoreboard; this(scoreboard);
this.id = scoreboard.getNextId().getAndIncrement();
this.objectiveName = objectiveName; this.objectiveName = objectiveName;
this.displaySlot = displaySlot; this.displaySlot = displaySlot;
this.displayName = displayName; this.displayName = displayName;
@ -61,9 +75,9 @@ public class Objective {
public void registerScore(String id, int score) { public void registerScore(String id, int score) {
if (!scores.containsKey(id)) { if (!scores.containsKey(id)) {
Score score1 = new Score(this, id).setScore(score); Score score1 = new Score(this, id)
Team team = scoreboard.getTeamFor(id); .setScore(score)
if (team != null) score1.setTeam(team); .setTeam(scoreboard.getTeamFor(id));
scores.put(id, score1); scores.put(id, score1);
} }
} }
@ -80,9 +94,9 @@ public class Objective {
if (!scores.containsKey(oldText) || oldText.equals(newText)) return; if (!scores.containsKey(oldText) || oldText.equals(newText)) return;
Score oldScore = scores.get(oldText); Score oldScore = scores.get(oldText);
Score newScore = new Score(this, newText).setScore(oldScore.getScore()); Score newScore = new Score(this, newText)
Team team = scoreboard.getTeamFor(newText); .setScore(oldScore.getScore())
if (team != null) newScore.setTeam(team); .setTeam(scoreboard.getTeamFor(newText));
scores.put(newText, newScore); scores.put(newText, newScore);
oldScore.setUpdateType(UpdateType.REMOVE); oldScore.setUpdateType(UpdateType.REMOVE);
@ -123,4 +137,11 @@ public class Objective {
if (updateType == UpdateType.NOTHING) updateType = UpdateType.UPDATE; if (updateType == UpdateType.NOTHING) updateType = UpdateType.UPDATE;
return this; return this;
} }
public void removeTemp(ScoreboardPosition displaySlot) {
if (temp) {
temp = false;
this.displaySlot = displaySlot.name().toLowerCase();
}
}
} }

View file

@ -39,7 +39,7 @@ public class Score {
private String name; private String name;
private Team team; private Team team;
private int score; private int score;
private int oldScore = Integer.MIN_VALUE;
public Score(Objective objective, String name) { public Score(Objective objective, String name) {
this.id = objective.getScoreboard().getNextId().getAndIncrement(); this.id = objective.getScoreboard().getNextId().getAndIncrement();
@ -48,9 +48,17 @@ public class Score {
} }
public String getDisplayName() { public String getDisplayName() {
if (team != null) { if (team != null && team.getUpdateType() != UpdateType.REMOVE) {
return team.getPrefix() + name + team.getSuffix(); return team.getPrefix() + name + team.getSuffix();
} }
return name; return name;
} }
public Score setScore(int score) {
if (oldScore == Integer.MIN_VALUE) {
this.oldScore = score;
}
this.score = score;
return this;
}
} }

View file

@ -32,7 +32,6 @@ import com.nukkitx.protocol.bedrock.packet.SetDisplayObjectivePacket;
import com.nukkitx.protocol.bedrock.packet.SetScorePacket; import com.nukkitx.protocol.bedrock.packet.SetScorePacket;
import lombok.Getter; import lombok.Getter;
import org.geysermc.api.Geyser; import org.geysermc.api.Geyser;
import org.geysermc.connector.console.GeyserLogger;
import org.geysermc.connector.network.session.GeyserSession; import org.geysermc.connector.network.session.GeyserSession;
import java.util.*; import java.util.*;
@ -52,13 +51,30 @@ public class Scoreboard {
this.session = session; this.session = session;
} }
public Objective registerNewObjective(String objectiveId, ScoreboardPosition displaySlot) { public Objective registerNewObjective(String objectiveId, boolean temp) {
Objective objective = new Objective(this, objectiveId, displaySlot, "unknown", 0); if (!temp || objectives.containsKey(objectiveId)) return objectives.get(objectiveId);
if (objectives.containsKey(objectiveId)) despawnObjective(objectives.get(objectiveId)); Objective objective = new Objective(this, objectiveId);
objectives.put(objectiveId, objective); objectives.put(objectiveId, objective);
return objective; return objective;
} }
public Objective registerNewObjective(String objectiveId, ScoreboardPosition displaySlot) {
Objective objective = null;
if (objectives.containsKey(objectiveId)) {
objective = objectives.get(objectiveId);
if (objective.isTemp()) objective.removeTemp(displaySlot);
else {
despawnObjective(objective);
objective = null;
}
}
if (objective == null) {
objective = new Objective(this, objectiveId, displaySlot, "unknown", 0);
objectives.put(objectiveId, objective);
}
return objective;
}
public Team registerNewTeam(String teamName, Set<String> players) { public Team registerNewTeam(String teamName, Set<String> players) {
if (teams.containsKey(teamName)) { if (teams.containsKey(teamName)) {
Geyser.getLogger().info("Ignoring team " + teamName + ". It overrides without removing old team."); Geyser.getLogger().info("Ignoring team " + teamName + ". It overrides without removing old team.");
@ -71,7 +87,7 @@ public class Scoreboard {
for (Objective objective : objectives.values()) { for (Objective objective : objectives.values()) {
for (Score score : objective.getScores().values()) { for (Score score : objective.getScores().values()) {
if (players.contains(score.getName())) { if (players.contains(score.getName())) {
score.setTeam(team).setUpdateType(ADD); score.setTeam(team);
} }
} }
} }
@ -92,15 +108,8 @@ public class Scoreboard {
} }
public void removeTeam(String teamName) { public void removeTeam(String teamName) {
if (teams.remove(teamName) != null) { Team remove = teams.remove(teamName);
for (Objective objective : objectives.values()) { if (remove != null) remove.setUpdateType(REMOVE);
for (Score score : objective.getScores().values()) {
if (score.getName().equals(teamName)) {
score.setTeam(null).setUpdateType(ADD);
}
}
}
}
} }
public void onUpdate() { public void onUpdate() {
@ -110,23 +119,64 @@ public class Scoreboard {
for (String objectiveId : new ArrayList<>(objectives.keySet())) { for (String objectiveId : new ArrayList<>(objectives.keySet())) {
Objective objective = objectives.get(objectiveId); Objective objective = objectives.get(objectiveId);
if (objective.isTemp()) {
Geyser.getLogger().debug("Ignoring temp Scoreboard Objective '"+ objectiveId +'\'');
continue;
}
if (objective.getUpdateType() != NOTHING) changedObjectives.add(objective); if (objective.getUpdateType() != NOTHING) changedObjectives.add(objective);
boolean globalUpdate = objective.getUpdateType() == UPDATE;
boolean globalAdd = objective.getUpdateType() == ADD || globalUpdate;
boolean globalRemove = objective.getUpdateType() == REMOVE || globalUpdate;
boolean hasUpdate = globalUpdate;
List<Score> handledScores = new ArrayList<>();
for (String identifier : new HashSet<>(objective.getScores().keySet())) { for (String identifier : new HashSet<>(objective.getScores().keySet())) {
Score score = objective.getScores().get(identifier); Score score = objective.getScores().get(identifier);
Team team = score.getTeam();
boolean add = (objective.getUpdateType() != NOTHING && objective.getUpdateType() != REMOVE) && score.getUpdateType() != REMOVE || score.getUpdateType() == ADD; boolean inTeam = team != null && team.getEntities().contains(score.getName());
boolean remove = (add && score.getUpdateType() != ADD && objective.getUpdateType() != ADD) || objective.getUpdateType() == REMOVE || score.getUpdateType() == REMOVE;
ScoreInfo info = new ScoreInfo(score.getId(), score.getObjective().getObjectiveName(), score.getScore(), score.getDisplayName()); boolean teamAdd = team != null && (team.getUpdateType() == ADD || team.getUpdateType() == UPDATE);
if (add || (score.getTeam() != null && (score.getTeam().getUpdateType() == ADD || score.getTeam().getUpdateType() == UPDATE))) addScores.add(info); boolean teamRemove = team != null && (team.getUpdateType() == REMOVE || team.getUpdateType() == UPDATE);
if (remove || (score.getTeam() != null && score.getTeam().getUpdateType() != NOTHING)) removeScores.add(info);
if (team != null && (team.getUpdateType() == REMOVE || inTeam)) score.setTeam(null);
boolean add = (hasUpdate || globalAdd || teamAdd || teamRemove || score.getUpdateType() == ADD || score.getUpdateType() == UPDATE) && (score.getUpdateType() != REMOVE);
boolean remove = hasUpdate || globalRemove || teamAdd || teamRemove || score.getUpdateType() == REMOVE || score.getUpdateType() == UPDATE;
boolean updated = false;
if (!hasUpdate) {
updated = hasUpdate = add;
}
if (updated) {
for (Score score1 : handledScores) {
ScoreInfo scoreInfo = new ScoreInfo(score1.getId(), score1.getObjective().getObjectiveName(), score1.getScore(), score1.getDisplayName());
addScores.add(scoreInfo);
removeScores.add(scoreInfo);
}
}
if (add) {
addScores.add(new ScoreInfo(score.getId(), score.getObjective().getObjectiveName(), score.getScore(), score.getDisplayName()));
}
if (remove) {
removeScores.add(new ScoreInfo(score.getId(), score.getObjective().getObjectiveName(), score.getOldScore(), score.getDisplayName()));
}
score.setOldScore(score.getScore());
if (score.getUpdateType() == REMOVE) { if (score.getUpdateType() == REMOVE) {
objective.removeScore(score.getName()); objective.removeScore(score.getName());
} }
if (addScores.contains(info) || removeScores.contains(info)) changedObjectives.add(objective); if (add || remove) {
changedObjectives.add(objective);
} else { // stays the same like before
handledScores.add(score);
}
score.setUpdateType(NOTHING); score.setUpdateType(NOTHING);
} }
} }

View file

@ -36,29 +36,20 @@ public class Team {
added.add(name); added.add(name);
} }
} }
setUpdateType(UpdateType.UPDATE);
for (Objective objective : scoreboard.getObjectives().values()) { for (Objective objective : scoreboard.getObjectives().values()) {
for (Score score : objective.getScores().values()) { for (Score score : objective.getScores().values()) {
if (added.contains(score.getName())) { if (added.contains(score.getName())) {
score.setTeam(this).setUpdateType(UpdateType.ADD); score.setTeam(this);
} }
} }
} }
} }
public void removeEntities(String... names) { public void removeEntities(String... names) {
List<String> removed = new ArrayList<>();
for (String name : names) { for (String name : names) {
if (entities.contains(name)) {
entities.remove(name); entities.remove(name);
removed.add(name);
}
}
for (Objective objective : scoreboard.getObjectives().values()) {
for (Score score : objective.getScores().values()) {
if (removed.contains(score.getName())) {
score.setTeam(null).setUpdateType(UpdateType.ADD);
}
}
} }
setUpdateType(UpdateType.UPDATE);
} }
} }