Search in sources :

Example 16 with Tuple

use of games.strategy.util.Tuple in project triplea by triplea-game.

the class AbstractEndTurnDelegate method changeUnitOwnership.

private static void changeUnitOwnership(final IDelegateBridge bridge) {
    final PlayerID player = bridge.getPlayerId();
    final PlayerAttachment pa = PlayerAttachment.get(player);
    final Collection<PlayerID> possibleNewOwners = pa.getGiveUnitControl();
    final Collection<Territory> territories = bridge.getData().getMap().getTerritories();
    final CompositeChange change = new CompositeChange();
    final Collection<Tuple<Territory, Collection<Unit>>> changeList = new ArrayList<>();
    for (final Territory currTerritory : territories) {
        final TerritoryAttachment ta = TerritoryAttachment.get(currTerritory);
        // if ownership should change in this territory
        if (ta != null && ta.getChangeUnitOwners() != null && !ta.getChangeUnitOwners().isEmpty()) {
            final Collection<PlayerID> terrNewOwners = ta.getChangeUnitOwners();
            for (final PlayerID terrNewOwner : terrNewOwners) {
                if (possibleNewOwners.contains(terrNewOwner)) {
                    // PlayerOwnerChange
                    final Collection<Unit> units = currTerritory.getUnits().getMatches(Matches.unitOwnedBy(player).and(Matches.unitCanBeGivenByTerritoryTo(terrNewOwner)));
                    if (!units.isEmpty()) {
                        change.add(ChangeFactory.changeOwner(units, terrNewOwner, currTerritory));
                        changeList.add(Tuple.of(currTerritory, units));
                    }
                }
            }
        }
    }
    if (!change.isEmpty() && !changeList.isEmpty()) {
        if (changeList.size() == 1) {
            final Tuple<Territory, Collection<Unit>> tuple = changeList.iterator().next();
            bridge.getHistoryWriter().startEvent("Some Units in " + tuple.getFirst().getName() + " change ownership: " + MyFormatter.unitsToTextNoOwner(tuple.getSecond()), tuple.getSecond());
        } else {
            bridge.getHistoryWriter().startEvent("Units Change Ownership");
            for (final Tuple<Territory, Collection<Unit>> tuple : changeList) {
                bridge.getHistoryWriter().addChildToEvent("Some Units in " + tuple.getFirst().getName() + " change ownership: " + MyFormatter.unitsToTextNoOwner(tuple.getSecond()), tuple.getSecond());
            }
        }
        bridge.addChange(change);
    }
}
Also used : PlayerID(games.strategy.engine.data.PlayerID) Territory(games.strategy.engine.data.Territory) TerritoryAttachment(games.strategy.triplea.attachments.TerritoryAttachment) ArrayList(java.util.ArrayList) Unit(games.strategy.engine.data.Unit) PlayerAttachment(games.strategy.triplea.attachments.PlayerAttachment) Collection(java.util.Collection) CompositeChange(games.strategy.engine.data.CompositeChange) Tuple(games.strategy.util.Tuple)

Example 17 with Tuple

use of games.strategy.util.Tuple in project triplea by triplea-game.

the class AbstractEndTurnDelegate method getBlockadeProductionLoss.

// finds losses due to blockades, positive value returned.
private int getBlockadeProductionLoss(final PlayerID player, final GameData data, final IDelegateBridge bridge, final StringBuilder endTurnReport) {
    final PlayerAttachment playerRules = PlayerAttachment.get(player);
    if (playerRules != null && playerRules.getImmuneToBlockade()) {
        return 0;
    }
    final GameMap map = data.getMap();
    final Collection<Territory> blockable = CollectionUtils.getMatches(map.getTerritories(), Matches.territoryIsBlockadeZone());
    if (blockable.isEmpty()) {
        return 0;
    }
    final Predicate<Unit> enemyUnits = Matches.enemyUnit(player, data);
    int totalLoss = 0;
    final boolean rollDiceForBlockadeDamage = Properties.getConvoyBlockadesRollDiceForCost(data);
    final Collection<String> transcripts = new ArrayList<>();
    final HashMap<Territory, Tuple<Integer, List<Territory>>> damagePerBlockadeZone = new HashMap<>();
    boolean rolledDice = false;
    for (final Territory b : blockable) {
        // match will check for land, convoy zones, and also contested territories
        final List<Territory> viableNeighbors = CollectionUtils.getMatches(map.getNeighbors(b), Matches.isTerritoryOwnedBy(player).and(Matches.territoryCanCollectIncomeFrom(player, data)));
        final int maxLoss = getProduction(viableNeighbors);
        if (maxLoss <= 0) {
            continue;
        }
        final Collection<Unit> enemies = CollectionUtils.getMatches(b.getUnits().getUnits(), enemyUnits);
        if (enemies.isEmpty()) {
            continue;
        }
        int loss = 0;
        if (rollDiceForBlockadeDamage) {
            int numberOfDice = 0;
            for (final Unit u : enemies) {
                numberOfDice += UnitAttachment.get(u.getType()).getBlockade();
            }
            if (numberOfDice > 0) {
                // there is an issue with maps that have lots of rolls without any pause between them: they are causing the
                // cypted random source
                // (ie: live and pbem games) to lock up or error out
                // so we need to slow them down a bit, until we come up with a better solution (like aggregating all the
                // chances together, then
                // getting a ton of random numbers at once instead of one at a time)
                Interruptibles.sleep(100);
                final String transcript = "Rolling for Convoy Blockade Damage in " + b.getName();
                final int[] dice = bridge.getRandom(CONVOY_BLOCKADE_DICE_SIDES, numberOfDice, enemies.iterator().next().getOwner(), DiceType.BOMBING, transcript);
                transcripts.add(transcript + ". Rolls: " + MyFormatter.asDice(dice));
                rolledDice = true;
                for (final int d : dice) {
                    // we are zero based
                    final int roll = d + 1;
                    loss += (roll <= 3 ? roll : 0);
                }
            }
        } else {
            for (final Unit u : enemies) {
                loss += UnitAttachment.get(u.getType()).getBlockade();
            }
        }
        if (loss <= 0) {
            continue;
        }
        final int lossForBlockade = Math.min(maxLoss, loss);
        damagePerBlockadeZone.put(b, Tuple.of(lossForBlockade, viableNeighbors));
        totalLoss += lossForBlockade;
    }
    if (totalLoss <= 0 && !rolledDice) {
        return 0;
    }
    // now we need to make sure that we didn't deal more damage than the territories are worth, in the case of having
    // multiple sea zones
    // touching the same land zone.
    final List<Territory> blockadeZonesSorted = new ArrayList<>(damagePerBlockadeZone.keySet());
    blockadeZonesSorted.sort(getSingleBlockadeThenHighestToLowestBlockadeDamage(damagePerBlockadeZone));
    // we want to match highest damage to largest producer first, that is why we sort twice
    final IntegerMap<Territory> totalDamageTracker = new IntegerMap<>();
    for (final Territory b : blockadeZonesSorted) {
        final Tuple<Integer, List<Territory>> tuple = damagePerBlockadeZone.get(b);
        int damageForZone = tuple.getFirst();
        final List<Territory> terrsLosingIncome = new ArrayList<>(tuple.getSecond());
        terrsLosingIncome.sort(getSingleNeighborBlockadesThenHighestToLowestProduction(blockadeZonesSorted, map));
        final Iterator<Territory> iter = terrsLosingIncome.iterator();
        while (damageForZone > 0 && iter.hasNext()) {
            final Territory t = iter.next();
            final int maxProductionLessPreviousDamage = TerritoryAttachment.getProduction(t) - totalDamageTracker.getInt(t);
            final int damageToTerr = Math.min(damageForZone, maxProductionLessPreviousDamage);
            damageForZone -= damageToTerr;
            totalDamageTracker.put(t, damageToTerr + totalDamageTracker.getInt(t));
        }
    }
    final int realTotalLoss = Math.max(0, totalDamageTracker.totalValues());
    if (rollDiceForBlockadeDamage && (realTotalLoss > 0 || (rolledDice && !transcripts.isEmpty()))) {
        final String mainline = "Total Cost from Convoy Blockades: " + realTotalLoss;
        bridge.getHistoryWriter().startEvent(mainline);
        endTurnReport.append(mainline).append("<br />");
        for (final String t : transcripts) {
            bridge.getHistoryWriter().addChildToEvent(t);
            endTurnReport.append("* ").append(t).append("<br />");
        }
        endTurnReport.append("<br />");
    }
    return realTotalLoss;
}
Also used : IntegerMap(games.strategy.util.IntegerMap) Territory(games.strategy.engine.data.Territory) GameMap(games.strategy.engine.data.GameMap) HashMap(java.util.HashMap) ArrayList(java.util.ArrayList) Unit(games.strategy.engine.data.Unit) PlayerAttachment(games.strategy.triplea.attachments.PlayerAttachment) ArrayList(java.util.ArrayList) List(java.util.List) Tuple(games.strategy.util.Tuple)

Example 18 with Tuple

use of games.strategy.util.Tuple in project triplea by triplea-game.

the class ProScrambleAi method scrambleUnitsQuery.

HashMap<Territory, Collection<Unit>> scrambleUnitsQuery(final Territory scrambleTo, final Map<Territory, Tuple<Collection<Unit>, Collection<Unit>>> possibleScramblers) {
    // Get battle data
    final GameData data = ProData.getData();
    final PlayerID player = ProData.getPlayer();
    final BattleDelegate delegate = DelegateFinder.battleDelegate(data);
    final IBattle battle = delegate.getBattleTracker().getPendingBattle(scrambleTo, false, BattleType.NORMAL);
    // Check if defense already wins
    final List<Unit> attackers = (List<Unit>) battle.getAttackingUnits();
    final List<Unit> defenders = (List<Unit>) battle.getDefendingUnits();
    final Set<Unit> bombardingUnits = new HashSet<>(battle.getBombardingUnits());
    final ProBattleResult minResult = calc.calculateBattleResults(scrambleTo, attackers, defenders, bombardingUnits);
    ProLogger.debug(scrambleTo + ", minTUVSwing=" + minResult.getTuvSwing() + ", minWin%=" + minResult.getWinPercentage());
    if (minResult.getTuvSwing() <= 0 && minResult.getWinPercentage() < (100 - ProData.minWinPercentage)) {
        return null;
    }
    // Check if max defense is worse
    final Set<Unit> allScramblers = new HashSet<>();
    final Map<Territory, List<Unit>> possibleMaxScramblerMap = new HashMap<>();
    for (final Territory t : possibleScramblers.keySet()) {
        final int maxCanScramble = BattleDelegate.getMaxScrambleCount(possibleScramblers.get(t).getFirst());
        List<Unit> canScrambleAir = new ArrayList<>(possibleScramblers.get(t).getSecond());
        if (maxCanScramble < canScrambleAir.size()) {
            canScrambleAir.sort(Comparator.comparingDouble(o -> ProBattleUtils.estimateStrength(scrambleTo, Collections.singletonList(o), new ArrayList<>(), false)));
            canScrambleAir = canScrambleAir.subList(0, maxCanScramble);
        }
        allScramblers.addAll(canScrambleAir);
        possibleMaxScramblerMap.put(t, canScrambleAir);
    }
    defenders.addAll(allScramblers);
    final ProBattleResult maxResult = calc.calculateBattleResults(scrambleTo, attackers, defenders, bombardingUnits);
    ProLogger.debug(scrambleTo + ", maxTUVSwing=" + maxResult.getTuvSwing() + ", maxWin%=" + maxResult.getWinPercentage());
    if (maxResult.getTuvSwing() >= minResult.getTuvSwing()) {
        return null;
    }
    // Loop through all units and determine attack options
    final Map<Unit, Set<Territory>> unitDefendOptions = new HashMap<>();
    for (final Territory t : possibleMaxScramblerMap.keySet()) {
        final Set<Territory> possibleTerritories = data.getMap().getNeighbors(t, ProMatches.territoryCanMoveSeaUnits(player, data, true));
        possibleTerritories.add(t);
        final Set<Territory> battleTerritories = new HashSet<>();
        for (final Territory possibleTerritory : possibleTerritories) {
            final IBattle possibleBattle = delegate.getBattleTracker().getPendingBattle(possibleTerritory, false, BattleType.NORMAL);
            if (possibleBattle != null) {
                battleTerritories.add(possibleTerritory);
            }
        }
        for (final Unit u : possibleMaxScramblerMap.get(t)) {
            unitDefendOptions.put(u, battleTerritories);
        }
    }
    // Sort units by number of defend options and cost
    final Map<Unit, Set<Territory>> sortedUnitDefendOptions = ProSortMoveOptionsUtils.sortUnitMoveOptions(unitDefendOptions);
    // Add one scramble unit at a time and check if final result is better than min result
    final List<Unit> unitsToScramble = new ArrayList<>();
    ProBattleResult result = minResult;
    for (final Unit u : sortedUnitDefendOptions.keySet()) {
        unitsToScramble.add(u);
        final List<Unit> currentDefenders = (List<Unit>) battle.getDefendingUnits();
        currentDefenders.addAll(unitsToScramble);
        result = calc.calculateBattleResults(scrambleTo, attackers, currentDefenders, bombardingUnits);
        ProLogger.debug(scrambleTo + ", TUVSwing=" + result.getTuvSwing() + ", Win%=" + result.getWinPercentage() + ", addedUnit=" + u);
        if (result.getTuvSwing() <= 0 && result.getWinPercentage() < (100 - ProData.minWinPercentage)) {
            break;
        }
    }
    if (result.getTuvSwing() >= minResult.getTuvSwing()) {
        return null;
    }
    // Return units to scramble
    final HashMap<Territory, Collection<Unit>> scrambleMap = new HashMap<>();
    for (final Territory t : possibleScramblers.keySet()) {
        for (final Unit u : possibleScramblers.get(t).getSecond()) {
            if (unitsToScramble.contains(u)) {
                if (scrambleMap.containsKey(t)) {
                    scrambleMap.get(t).add(u);
                } else {
                    final Collection<Unit> units = new ArrayList<>();
                    units.add(u);
                    scrambleMap.put(t, units);
                }
            }
        }
    }
    return scrambleMap;
}
Also used : ProSortMoveOptionsUtils(games.strategy.triplea.ai.pro.util.ProSortMoveOptionsUtils) Unit(games.strategy.engine.data.Unit) ProBattleResult(games.strategy.triplea.ai.pro.data.ProBattleResult) IBattle(games.strategy.triplea.delegate.IBattle) Collection(java.util.Collection) Set(java.util.Set) Territory(games.strategy.engine.data.Territory) HashMap(java.util.HashMap) ProBattleUtils(games.strategy.triplea.ai.pro.util.ProBattleUtils) ArrayList(java.util.ArrayList) ProLogger(games.strategy.triplea.ai.pro.logging.ProLogger) HashSet(java.util.HashSet) GameData(games.strategy.engine.data.GameData) BattleType(games.strategy.triplea.delegate.IBattle.BattleType) List(java.util.List) DelegateFinder(games.strategy.triplea.delegate.DelegateFinder) Tuple(games.strategy.util.Tuple) PlayerID(games.strategy.engine.data.PlayerID) ProMatches(games.strategy.triplea.ai.pro.util.ProMatches) Map(java.util.Map) BattleDelegate(games.strategy.triplea.delegate.BattleDelegate) ProOddsCalculator(games.strategy.triplea.ai.pro.util.ProOddsCalculator) Comparator(java.util.Comparator) Collections(java.util.Collections) PlayerID(games.strategy.engine.data.PlayerID) BattleDelegate(games.strategy.triplea.delegate.BattleDelegate) Territory(games.strategy.engine.data.Territory) GameData(games.strategy.engine.data.GameData) Set(java.util.Set) HashSet(java.util.HashSet) HashMap(java.util.HashMap) ArrayList(java.util.ArrayList) ProBattleResult(games.strategy.triplea.ai.pro.data.ProBattleResult) Unit(games.strategy.engine.data.Unit) IBattle(games.strategy.triplea.delegate.IBattle) Collection(java.util.Collection) ArrayList(java.util.ArrayList) List(java.util.List) HashSet(java.util.HashSet)

Example 19 with Tuple

use of games.strategy.util.Tuple in project triplea by triplea-game.

the class GameParser method setValues.

private ArrayList<Tuple<String, String>> setValues(final IAttachment attachment, final List<Element> values) throws GameParseException {
    final ArrayList<Tuple<String, String>> options = new ArrayList<>();
    for (final Element current : values) {
        // decapitalize the property name for backwards compatibility
        final String name = decapitalize(current.getAttribute("name"));
        if (name.isEmpty()) {
            throw newGameParseException("Option name with zero length");
        }
        final String value = current.getAttribute("value");
        final String count = current.getAttribute("count");
        final String itemValues = (count.length() > 0 ? count + ":" : "") + value;
        try {
            attachment.getProperty(name).orElseThrow(() -> newGameParseException(String.format("Missing property definition for option '%s' in attachment '%s'", name, attachment.getName()))).setValue(itemValues);
        } catch (final GameParseException e) {
            throw e;
        } catch (final Exception e) {
            throw newGameParseException("Unexpected Exception while setting values for attachment" + attachment, e);
        }
        options.add(Tuple.of(name, itemValues));
    }
    return options;
}
Also used : Element(org.w3c.dom.Element) ArrayList(java.util.ArrayList) Tuple(games.strategy.util.Tuple) SAXException(org.xml.sax.SAXException) IOException(java.io.IOException) SAXParseException(org.xml.sax.SAXParseException) ParserConfigurationException(javax.xml.parsers.ParserConfigurationException)

Example 20 with Tuple

use of games.strategy.util.Tuple in project triplea by triplea-game.

the class TabbedProductionPanel method getDefaultRuleLists.

private List<Tuple<String, List<Rule>>> getDefaultRuleLists() {
    final List<Tuple<String, List<Rule>>> ruleLists = new ArrayList<>();
    final ArrayList<Rule> allRules = new ArrayList<>();
    final ArrayList<Rule> landRules = new ArrayList<>();
    final ArrayList<Rule> airRules = new ArrayList<>();
    final ArrayList<Rule> seaRules = new ArrayList<>();
    final ArrayList<Rule> constructRules = new ArrayList<>();
    final ArrayList<Rule> upgradeConsumesRules = new ArrayList<>();
    final ArrayList<Rule> resourceRules = new ArrayList<>();
    for (final Rule rule : rules) {
        allRules.add(rule);
        final NamedAttachable resourceOrUnit = rule.getProductionRule().getResults().keySet().iterator().next();
        if (resourceOrUnit instanceof UnitType) {
            final UnitType type = (UnitType) resourceOrUnit;
            final UnitAttachment attach = UnitAttachment.get(type);
            if (attach.getConsumesUnits() != null && attach.getConsumesUnits().totalValues() >= 1) {
                upgradeConsumesRules.add(rule);
            }
            // anywhere (placed without needing a factory).
            if (attach.getIsConstruction()) {
                constructRules.add(rule);
            } else if (attach.getIsSea()) {
                seaRules.add(rule);
            } else if (attach.getIsAir()) {
                airRules.add(rule);
            } else {
                landRules.add(rule);
            }
        } else if (resourceOrUnit instanceof Resource) {
            resourceRules.add(rule);
        }
    }
    ruleLists.add(Tuple.of("All", allRules));
    ruleLists.add(Tuple.of("Land", landRules));
    ruleLists.add(Tuple.of("Air", airRules));
    ruleLists.add(Tuple.of("Sea", seaRules));
    ruleLists.add(Tuple.of("Construction", constructRules));
    ruleLists.add(Tuple.of("Upgrades/Consumes", upgradeConsumesRules));
    ruleLists.add(Tuple.of("Resources", resourceRules));
    return ruleLists;
}
Also used : UnitAttachment(games.strategy.triplea.attachments.UnitAttachment) NamedAttachable(games.strategy.engine.data.NamedAttachable) UnitType(games.strategy.engine.data.UnitType) ArrayList(java.util.ArrayList) Resource(games.strategy.engine.data.Resource) ProductionRule(games.strategy.engine.data.ProductionRule) Tuple(games.strategy.util.Tuple)

Aggregations

Tuple (games.strategy.util.Tuple)24 ArrayList (java.util.ArrayList)20 Unit (games.strategy.engine.data.Unit)18 Territory (games.strategy.engine.data.Territory)11 HashSet (java.util.HashSet)11 UnitType (games.strategy.engine.data.UnitType)10 IntegerMap (games.strategy.util.IntegerMap)10 HashMap (java.util.HashMap)9 GameData (games.strategy.engine.data.GameData)8 PlayerID (games.strategy.engine.data.PlayerID)8 TripleAUnit (games.strategy.triplea.TripleAUnit)8 UnitAttachment (games.strategy.triplea.attachments.UnitAttachment)7 Collection (java.util.Collection)7 List (java.util.List)7 Set (java.util.Set)7 CompositeChange (games.strategy.engine.data.CompositeChange)6 Change (games.strategy.engine.data.Change)5 ProductionRule (games.strategy.engine.data.ProductionRule)4 ResourceCollection (games.strategy.engine.data.ResourceCollection)4 GridBagConstraints (java.awt.GridBagConstraints)4