diff --git a/forge-core/src/main/java/forge/card/MagicColor.java b/forge-core/src/main/java/forge/card/MagicColor.java index d5665ee03af..759ac729509 100644 --- a/forge-core/src/main/java/forge/card/MagicColor.java +++ b/forge-core/src/main/java/forge/card/MagicColor.java @@ -85,6 +85,14 @@ public class MagicColor { } } + public static int getIndexOfFirstColor(byte color){ + for(int i = 0; i < NUMBER_OR_COLORS; i++) { + if ((color & WUBRG[i]) != 0) + return i; + } + return -1; // colorless + } + /** * The Interface Color. */ diff --git a/forge-game/src/main/java/forge/game/mana/ManaPool.java b/forge-game/src/main/java/forge/game/mana/ManaPool.java index e9c6ed05394..b8969317308 100644 --- a/forge-game/src/main/java/forge/game/mana/ManaPool.java +++ b/forge-game/src/main/java/forge/game/mana/ManaPool.java @@ -65,6 +65,7 @@ public class ManaPool { */ public ManaPool(final Player player) { owner = player; + restoreColorReplacements(); } public final int getAmountOfColor(final byte color) { @@ -416,8 +417,25 @@ public class ManaPool { p.getGame().fireEvent(new GameEventZone(ZoneType.Battlefield, p, EventValueChangeType.ComplexUpdate, null)); } + + private byte[] colorConversionMatrix = new byte[6]; + + private static final byte[] identityMatrix = { MagicColor.WHITE, MagicColor.BLUE, MagicColor.BLACK, MagicColor.RED, MagicColor.GREEN, 0 }; + + public void restoreColorReplacements() { + for(int i = 0; i < colorConversionMatrix.length; i++) + colorConversionMatrix[i] = identityMatrix[i]; + } + public boolean canPayForShardWithColor(ManaCostShard shard, byte color) { - // add color changing manipulations here - return shard.canBePaidWithManaOfColor(color); + int rowIdx = MagicColor.getIndexOfFirstColor(color); + byte line = colorConversionMatrix[rowIdx < 0 ? identityMatrix.length - 1 : rowIdx]; + for(int i = 0; i < MagicColor.NUMBER_OR_COLORS; i++) + { + byte outColor = MagicColor.WUBRG[i]; + if (( line & outColor) != 0 && shard.canBePaidWithManaOfColor(outColor)) + return true; + } + return shard.canBePaidWithManaOfColor((byte)0); } } diff --git a/forge-gui/src/main/java/forge/gui/input/InputPayMana.java b/forge-gui/src/main/java/forge/gui/input/InputPayMana.java index 9d3f622cfcf..2ae6f7d0040 100644 --- a/forge-gui/src/main/java/forge/gui/input/InputPayMana.java +++ b/forge-gui/src/main/java/forge/gui/input/InputPayMana.java @@ -110,8 +110,12 @@ public abstract class InputPayMana extends InputSyncronizedBase { if (manaCost.isAnyPartPayableWith(color, player.getManaPool())) { colorCanUse |= color; } if (manaCost.needsColor(color, player.getManaPool())) { colorNeeded |= color; } } - boolean canUseColorless = manaCost.isAnyPartPayableWith((byte)0, player.getManaPool()); + if (manaCost.isAnyPartPayableWith(MagicColor.COLORLESS, player.getManaPool())) + colorCanUse |= MagicColor.COLORLESS; + if ( 0 == colorCanUse ) // no mana cost or something + return; + List abilities = new ArrayList(); // you can't remove unneeded abilities inside a for (am:abilities) loop :( @@ -125,10 +129,10 @@ public abstract class InputPayMana extends InputSyncronizedBase { ma.setActivatingPlayer(player); AbilityManaPart m = ma.getManaPartRecursive(); - if (m == null || !ma.canPlay()) { continue; } - if (!canUseColorless && !abilityProducesManaColor(ma, m, colorCanUse)) { continue; } - if (ma.isAbility() && ma.getRestrictions().isInstantSpeed()) { continue; } - if (!m.meetsManaRestrictions(saPaidFor)) { continue; } + if (m == null || !ma.canPlay()) { continue; } + if (!abilityProducesManaColor(ma, m, colorCanUse)) { continue; } + if (ma.isAbility() && ma.getRestrictions().isInstantSpeed()) { continue; } + if (!m.meetsManaRestrictions(saPaidFor)) { continue; } abilities.add(ma); @@ -216,7 +220,7 @@ public abstract class InputPayMana extends InputSyncronizedBase { * @return a boolean. */ private static boolean abilityProducesManaColor(final SpellAbility am, AbilityManaPart m, final byte neededColor) { - if (neededColor == 0) { + if (0 != (neededColor & MagicColor.COLORLESS)) { return true; }