import mock
import unittest

from MTG.test.test_game import TestGameBase
from MTG.exceptions import *

class TestPlayer(TestGameBase):
    def test_optional_trigger_on_lifegain(self):
        """ Ajani's Pridemate: on life gain, put +1/+1 counter. """
        with mock.patch('builtins.input', side_effect=[
                '__self.battlefield.add("Ajani\'s Pridemate")',
                '__self.gain_life(3)',
                '', '', 'yes',  # resolving trigger
                '__self.tmp = self.battlefield[0].power == 3',
                '__self.gain_life(2)',
                '', '', '',  # resolving trigger, saying 'no'
                '__self.tmp = self.tmp and self.battlefield[0].power == 3',
                '__self.gain_life(1)',
                '', '', 'yes',  # resolving trigger
                '__self.tmp = self.tmp and self.battlefield[0].toughness == 4',
                '', '',
                '', '__self.gain_life(1)', '',  # opponent gains life
                '__self.tmp = self.tmp and not self.stack',  # no trigger
                's upkeep',
                's upkeep']):  # no attack

            self.GAME.handle_turn()
            self.assertTrue(self.player.tmp)

    def test_pt_modifiers(self):
        """Testing casting +4/+4 and -3/-3 until eot effects (plus +1/+1 counters)"""
        with mock.patch('builtins.input', side_effect=[
                '__self.battlefield.add("Ajani\'s Pridemate")',
                '__self.gain_life(1)',
                '', '', 'yes',  # resolving trigger
                '__self.tmp = self.battlefield[0].power == 3',
                '__self.gain_life(1)',
                '', '', 'yes',
                '__self.tmp = self.tmp and self.battlefield[0].power == 4',
                '__self.add_card_to_hand("Ulcerate")',
                '__self.add_card_to_hand("Titanic Growth")',
                '__self.mana.add("BGG")',
                'p Ulcerate', 'b 0',  # target
                '', '',
                '__self.tmp = self.tmp and self.battlefield[0].toughness == 1',
                'p Titanic Growth', 'b 0', '', # target
                '', '',
                '__self.tmp = self.tmp and self.battlefield[0].toughness == 5',
                's upkeep',
                's upkeep']):

            self.GAME.handle_turn()
            self.assertTrue(self.player.tmp)
            # both ulcerate and titanic growth should have fallen off
            self.assertEqual(self.player.battlefield[0].power, 4)

    def test_activated_ability_no_target(self):
        """Zof shade: self buff until eot """
        with mock.patch('builtins.input', side_effect=[
                '__self.battlefield.add("Zof Shade")',
                '__self.mana.add(mana.Mana.BLACK, 9)',
                'a 0', '', '',
                '__self.tmp = self.battlefield[0].power == 4',
                'a 0', 'a 0', '', '',
                '__self.tmp = self.tmp and self.battlefield[0].power == 6',
                '', '',
                '__self.tmp = self.tmp and self.battlefield[0].power == 8',
                's end', 's end',
                # should still keep the power at beginning of end step
                '__self.tmp = self.tmp and self.battlefield[0].power == 8',
                's upkeep',
                's upkeep']):

            self.GAME.handle_turn()
            self.assertTrue(self.player.tmp)
            # buffs should off
            self.assertEqual(self.player.battlefield[0].power, 2)

    def test_phase_based_conditional_trigger(self):
        """Testing trigger on each upkeep -- if lost life last turn, create token"""
        with mock.patch('builtins.input', side_effect=[
                '__self.battlefield.add("First Response")',
                '__self.lose_life(3)',
                's upkeep', 's upkeep', '', '',
                's upkeep',  # player 1's turn
                # player 0 verifying token
                '__self.tmp = self.battlefield[1].power == 1'
            ' and self.battlefield[1].is_color(["W"])', 's upkeep',
                '', '', 's upkeep', 's upkeep',  # player 0's turn again
                '0'  # attacking with token
        ]):

            self.player.autoDiscard = True
            self.opponent.autoDiscard = True
            self.GAME.handle_turn()
            self.GAME.handle_turn()
            self.GAME.handle_turn()
            self.assertTrue(self.player.tmp)
            # buffs should off
            self.assertEqual(self.player.opponent.life, 19)


    def test_activated_ability_targeting(self):
        """Testing Grindclock: mill based on # counters"""
        with mock.patch('builtins.input', side_effect=[
                '', '',
                '__self.battlefield.add("Grindclock")',
                'a 0_1', 'p',  # mill myself; the amount should be checked on RESOLUTION
                '__self.battlefield[0].untap()',
                'a 0_0',
                '__self.battlefield[0].untap()',
                'a 0_0',  # put 2 charge counters; activated in respond, so they should resolve first
                's upkeep', 's upkeep'
        ]):
            self.GAME.handle_turn()
            self.assertEqual(len(self.player.graveyard), 2)  # mill 2 cards


    def test_triggered_ability_targeting(self):
        """Testing Kinsbaile Skirmisher"""
        with mock.patch('builtins.input', side_effect=[
                's main', 's main',
                '__self.battlefield.add("Soulmender")',
                '__self.add_card_to_hand("Kinsbaile Skirmisher")',
                '__self.add_card_to_hand("Kinsbaile Skirmisher")',