extends GutTest func test_core_boar_reuses_wolf_behavior_and_spawns_from_data() -> void: SimulationEnemies.invalidate_cache() var wolf := SimulationEnemies.get_enemy(&"enemy_wolf") var boar := SimulationEnemies.get_enemy(&"enemy_boar") assert_not_null(wolf) assert_not_null(boar) assert_eq(boar.behavior_profile_id, wolf.behavior_profile_id) assert_eq(boar.behavior_profile_id, EnemyDefinition.BEHAVIOR_PROFILE_WOLF_HUNT) assert_eq(boar.combatant_id_prefix, "boar") var factory := CombatantFactory.new() var combatant := factory.create_enemy(boar.enemy_id, Vector3(1.0, 2.0, 3.0)) assert_not_null(combatant) assert_eq(combatant.get_combatant_id(), &"boar_0") assert_eq(combatant.get_enemy_definition_id(), boar.enemy_id) assert_eq(combatant.get_kind(), boar.kind) assert_eq(combatant.get_faction_id(), boar.faction_id) assert_eq(combatant.get_weapon_id(), boar.weapon_id) assert_eq(combatant.get_max_health(), boar.health) assert_eq(combatant.is_hostile(), boar.hostile) func test_factory_accepts_a_definition_without_enemy_specific_code() -> void: var definition := EnemyDefinition.new() definition.enemy_id = &"enemy_test_hound" definition.display_name = "Test Hound" definition.kind = SimulationIds.COMBATANT_KIND_WOLF definition.behavior_profile_id = EnemyDefinition.BEHAVIOR_PROFILE_WOLF_HUNT definition.combatant_id_prefix = "test_hound" definition.faction_id = SimulationIds.FACTION_TRIBE definition.hostile = true definition.weapon_id = SimulationIds.ITEM_CLAW definition.health = 37.0 var factory := CombatantFactory.new() assert_true(definition.validate().is_empty()) var combatant := factory.create_from_definition(definition, Vector3.ZERO) assert_not_null(combatant) assert_eq(combatant.get_combatant_id(), &"test_hound_0") assert_eq(combatant.get_enemy_definition_id(), definition.enemy_id) assert_eq(combatant.get_max_health(), 37.0) func test_enemy_definition_id_round_trips_and_v1_infers_legacy_ids() -> void: var current := CombatantStateRecord.create( &"boar_7", SimulationIds.COMBATANT_KIND_WOLF, SimulationIds.FACTION_TRIBE, "Wild Boar", Vector3.ZERO, 55.0, SimulationIds.ITEM_CLAW, CombatantStateRecord.NO_NPC_ID, true, &"enemy_boar" ) var restored := CombatantStateRecord.from_dictionary(current.to_dictionary()) assert_not_null(restored) assert_eq(restored.get_enemy_definition_id(), &"enemy_boar") var legacy_data := current.to_dictionary() legacy_data["schema_version"] = CombatantStateRecord.LEGACY_SCHEMA_VERSION legacy_data.erase("enemy_definition_id") var migrated := CombatantStateRecord.from_dictionary(legacy_data) assert_not_null(migrated) assert_eq(migrated.get_enemy_definition_id(), &"enemy_wolf") assert_eq(int(migrated.to_dictionary()["schema_version"]), CombatantStateRecord.SCHEMA_VERSION) func test_conflict_restore_rebuilds_collision_free_definition_allocators() -> void: var records: Array[CombatantStateRecord] = [ _enemy_record(&"wolf_0", &"enemy_wolf"), _enemy_record(&"wolf_4", &"enemy_wolf"), _enemy_record(&"boar_2", &"enemy_boar"), ] var no_factions: Array[FactionStateRecord] = [] var conflict := ConflictSystem.new() conflict.restore_state_records(records, no_factions, 12) var wolf_id := conflict.spawn_wolf(Vector3.ZERO) var boar_id := conflict.spawn_enemy(&"enemy_boar", Vector3.ONE) assert_eq(wolf_id, &"wolf_5") assert_eq(boar_id, &"boar_3") assert_eq(conflict.get_combatant(wolf_id).get_enemy_definition_id(), &"enemy_wolf") assert_eq(conflict.get_combatant(boar_id).get_enemy_definition_id(), &"enemy_boar") assert_eq(conflict.get_all_combatants().size(), 6) func _enemy_record( combatant_id: StringName, enemy_definition_id: StringName ) -> CombatantStateRecord: var definition := SimulationEnemies.get_enemy(enemy_definition_id) return CombatantStateRecord.create( combatant_id, definition.kind, definition.faction_id, definition.display_name, Vector3.ZERO, definition.health, definition.weapon_id, CombatantStateRecord.NO_NPC_ID, definition.hostile, definition.enemy_id )