1
0
Fork 0
mirror of https://github.com/correl/mage.git synced 2025-04-03 17:00:16 -09:00

Potential game freeze fix

This commit is contained in:
Oleg Agafonov 2020-07-02 01:27:53 +04:00
parent 126898f70a
commit f409f56c05

View file

@ -1,10 +1,6 @@
package mage.players; package mage.players;
import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableMap;
import java.io.Serializable;
import java.util.*;
import java.util.Map.Entry;
import java.util.stream.Collectors;
import mage.ConditionalMana; import mage.ConditionalMana;
import mage.MageObject; import mage.MageObject;
import mage.MageObjectReference; import mage.MageObjectReference;
@ -70,6 +66,11 @@ import mage.util.GameLog;
import mage.util.RandomUtil; import mage.util.RandomUtil;
import org.apache.log4j.Logger; import org.apache.log4j.Logger;
import java.io.Serializable;
import java.util.*;
import java.util.Map.Entry;
import java.util.stream.Collectors;
public abstract class PlayerImpl implements Player, Serializable { public abstract class PlayerImpl implements Player, Serializable {
private static final Logger logger = Logger.getLogger(PlayerImpl.class); private static final Logger logger = Logger.getLogger(PlayerImpl.class);
@ -131,7 +132,7 @@ public abstract class PlayerImpl implements Player, Serializable {
protected boolean idleTimeout; protected boolean idleTimeout;
protected RangeOfInfluence range; protected RangeOfInfluence range;
protected Set<UUID> inRange = new HashSet<>(); protected Set<UUID> inRange = new HashSet<>(); // players list in current range of influence (updates each turn)
protected boolean isTestMode = false; protected boolean isTestMode = false;
protected boolean canGainLife = true; protected boolean canGainLife = true;
@ -460,7 +461,7 @@ public abstract class PlayerImpl implements Player, Serializable {
@Override @Override
public void beginTurn(Game game) { public void beginTurn(Game game) {
this.landsPlayed = 0; this.landsPlayed = 0;
findRange(game); updateRangeOfInfluence(game);
} }
@Override @Override
@ -468,44 +469,34 @@ public abstract class PlayerImpl implements Player, Serializable {
return range; return range;
} }
protected void findRange(Game game) { protected void updateRangeOfInfluence(Game game) {
// 20100423 - 801.2c // 20100423 - 801.2c
// 801.2c The particular players within each players range of influence are determined as each turn begins.
inRange.clear(); inRange.clear();
if (range == RangeOfInfluence.ALL) { inRange.add(this.playerId);
for (Player player : game.getPlayers().values()) { inRange.addAll(getAllNearPlayers(game, true));
if (!player.hasLeft()) { inRange.addAll(getAllNearPlayers(game, false));
inRange.add(player.getId());
}
}
} else if ((range.getRange() * 2) + 1 >= game.getPlayers().size()) {
for (Player player : game.getPlayers().values()) {
if (!player.hasLeft()) {
inRange.add(player.getId());
}
}
} else {
inRange.add(playerId);
PlayerList players = game.getState().getPlayerList(playerId);
for (int i = 0; i < range.getRange(); i++) {
Player player = players.getNext(game, false);
if (player != null) {
while (player.hasLeft()) { // can freeze?
player = players.getNext(game, false);
}
inRange.add(player.getId());
}
}
players = game.getState().getPlayerList(playerId);
for (int i = 0; i < range.getRange(); i++) {
Player player = players.getPrevious(game);
if (player != null) {
while (player.hasLeft()) { // can freeze?
player = players.getPrevious(game);
}
inRange.add(player.getId());
} }
private Set<UUID> getAllNearPlayers(Game game, boolean needPrevious) {
// find all near players (search from current player position)
Set<UUID> foundedList = new HashSet<>();
PlayerList players = game.getState().getPlayerList(this.playerId);
int needAmount = this.getRange().getRange(); // distance to search (0 - ALL range)
int foundedAmount = 0;
while (needAmount == 0 || foundedAmount < needAmount) {
Player foundedPlayer = needPrevious ? players.getPrevious(game) : players.getNext(game, false);
// PlayerList is inifine, so stops on repeats
if (foundedPlayer == null || foundedPlayer.getId().equals(this.playerId) || foundedList.contains(foundedPlayer.getId())) {
break;
} }
// skip leaved player (no needs cause next/previous code already checks it)
foundedList.add(foundedPlayer.getId());
foundedAmount++;
} }
return foundedList;
} }
@Override @Override