#!/usr/bin/env python3 """ 测试回合制行动限制 - 刚部署单位不能行动(除非有Blitz) - 单位一回合只能移动或攻击二选一(除非有Tank) - 单位一回合最多攻击一次(除非有Fury) """ import sys import os # 添加项目路径 sys.path.insert(0, os.path.join(os.path.dirname(__file__), '..')) from kards_battle.core.battle_engine import BattleEngine from kards_battle.units.unit_loader import load_unit from interactive.command_parser import CommandParser def test_newly_deployed_unit_cannot_act(): """测试刚部署的单位不能行动""" print("=== 测试刚部署单位不能行动 ===") engine = BattleEngine("Germany", "USA", debug_mode=True) parser = CommandParser(engine) # 部署一个普通单位(没有BLITZ) grenadier = load_unit('ger_infantry_grenadier') engine.deploy_unit_to_support(grenadier, 0) engine.debug_set_kredits(0, kredits=5) print(f"单位关键词: {grenadier.keywords}") print(f"单位状态: deployed_this_turn={grenadier.deployed_this_turn}") print(f" can_operate_immediately={grenadier.can_operate_immediately}") # 尝试移动刚部署的单位 print("\n尝试移动刚部署的单位:") success, message = parser.parse("move 1 0") print(f"移动结果: {success} - {message}") assert not success, "刚部署的单位应该不能移动" assert "deployed this turn" in message, f"错误信息应该提到部署限制: {message}" # 尝试攻击 print("\n尝试攻击:") # 需要有目标,先部署敌军 marine = load_unit('usa_infantry_marine') engine.deploy_unit_to_support(marine, 1) success, message = parser.parse("attack S1 S0") print(f"攻击结果: {success} - {message}") assert not success, "刚部署的单位应该不能攻击" assert "deployed this turn" in message, f"错误信息应该提到部署限制: {message}" def test_blitz_unit_can_act_immediately(): """测试有Blitz关键词的单位可以立即行动""" print("\n=== 测试Blitz单位立即行动 ===") engine = BattleEngine("Germany", "USA", debug_mode=True) parser = CommandParser(engine) # 部署一个有Blitz的单位 stormtrooper = load_unit('ger_infantry_stormtrooper') # 应该有BLITZ关键词 engine.deploy_unit_to_support(stormtrooper, 0) engine.debug_set_kredits(0, kredits=5) print(f"单位关键词: {stormtrooper.keywords}") print(f"can_operate_immediately: {stormtrooper.can_operate_immediately}") if stormtrooper.has_keyword("BLITZ"): # 尝试移动Blitz单位 print("\n尝试移动Blitz单位:") success, message = parser.parse("move 1 0") print(f"移动结果: {success} - {message}") assert success, f"Blitz单位应该能立即移动: {message}" else: print("注意: Stormtrooper没有BLITZ关键词,跳过此测试") def test_move_or_attack_restriction(): """测试移动或攻击二选一限制""" print("\n=== 测试移动攻击二选一 ===") engine = BattleEngine("Germany", "USA", debug_mode=True) parser = CommandParser(engine) # 部署单位并让其可以行动 panzer = load_unit('ger_tank_panzer_iv') # Tank有BLITZ和移动攻击能力 engine.deploy_unit_to_support(panzer, 0) engine.debug_set_kredits(0, kredits=10) # 结束回合让单位状态重置 engine.end_turn() # 切换到美军 engine.end_turn() # 切换回德军,新回合开始 engine.debug_set_kredits(0, kredits=10) print(f"单位状态: deployed_this_turn={panzer.deployed_this_turn}") print(f" can_move_and_attack={panzer.can_move_and_attack}") # 先移动 print("\n1. 移动单位:") success, message = parser.parse("move 1 0") print(f"移动结果: {success} - {message}") if success: print(f"移动后状态: has_moved_this_turn={panzer.has_moved_this_turn}") # 再尝试攻击 print("\n2. 移动后尝试攻击:") # 部署目标 marine = load_unit('usa_infantry_marine') engine.deploy_unit_to_support(marine, 1) success, message = parser.parse("attack F0 S0") print(f"攻击结果: {success} - {message}") if panzer.can_move_and_attack: print("Tank单位应该可以移动后攻击") else: assert not success, "普通单位移动后应该不能攻击" assert "has moved" in message, f"错误信息应该提到移动限制: {message}" def test_multiple_attack_restriction(): """测试多次攻击限制""" print("\n=== 测试攻击次数限制 ===") engine = BattleEngine("Germany", "USA", debug_mode=True) parser = CommandParser(engine) # 部署攻击单位 grenadier = load_unit('ger_infantry_grenadier') engine.deploy_unit_to_support(grenadier, 0) engine.debug_set_kredits(0, kredits=20) # 部署多个目标 for i in range(3): marine = load_unit('usa_infantry_marine') engine.deploy_unit_to_support(marine, 1) # 结束回合让单位可以行动 engine.end_turn() # 切换到美军 engine.end_turn() # 切换回德军,新回合开始 engine.debug_set_kredits(0, kredits=20) print(f"最大攻击次数: {grenadier.max_attacks_per_turn}") # 第一次攻击 print("\n1. 第一次攻击:") success, message = parser.parse("attack S1 S0") print(f"攻击结果: {success} - {message}") if success: print(f"攻击次数: {grenadier.attacks_this_turn}") # 第二次攻击 print("\n2. 第二次攻击:") success, message = parser.parse("attack S1 S1") print(f"攻击结果: {success} - {message}") if grenadier.can_attack_multiple_times: print("有Fury等能力的单位可以多次攻击") else: assert not success, "普通单位应该不能攻击两次" assert "maximum attacks" in message, f"错误信息应该提到攻击次数限制: {message}" def test_tank_abilities(): """测试Tank类单位的特殊能力""" print("\n=== 测试Tank单位特殊能力 ===") engine = BattleEngine("Germany", "USA", debug_mode=True) parser = CommandParser(engine) # 部署Tank单位 panzer = load_unit('ger_tank_panzer_iv') engine.deploy_unit_to_support(panzer, 0) engine.debug_set_kredits(0, kredits=20) # 部署目标 marine = load_unit('usa_infantry_marine') engine.deploy_unit_to_support(marine, 1) # 结束回合让单位可以行动 engine.end_turn() # 切换到美军 engine.end_turn() # 切换回德军,新回合开始 engine.debug_set_kredits(0, kredits=20) print(f"Tank能力: can_move_and_attack={panzer.can_move_and_attack}") print(f"单位类型: {panzer.unit_type}") if panzer.can_move_and_attack: # Tank应该可以移动后攻击 print("\n1. Tank移动:") success, message = parser.parse("move 1 0") print(f"移动结果: {success} - {message}") if success: print("\n2. Tank移动后攻击:") success, message = parser.parse("attack F0 S0") print(f"攻击结果: {success} - {message}") assert success, f"Tank应该能移动后攻击: {message}" if __name__ == "__main__": print("开始回合制限制测试\n") tests = [ test_newly_deployed_unit_cannot_act, test_blitz_unit_can_act_immediately, test_move_or_attack_restriction, test_multiple_attack_restriction, test_tank_abilities, ] for test in tests: try: test() print("✅ 测试通过") except AssertionError as e: print(f"❌ 测试失败: {e}") except Exception as e: print(f"❌ 测试异常: {e}") print("-" * 50) print("\n回合制限制测试完成")