extends SceneTree const BattleService = preload("res://p10_3/deep_channels_battle_service.gd") const Controller = preload("res://p10_3/runtime_controller.gd") const Fixture = preload("res://tests/p10_3/deep_channels_fixture.gd") const VIEWPORT := Vector2i(844, 390) var experience var failures: Array[String] = [] var parsed_drags := 0 var parsed_touches := 0 func _initialize() -> void: call_deferred("run_test") func run_test() -> void: root.size = VIEWPORT root.content_scale_mode = Window.CONTENT_SCALE_MODE_CANVAS_ITEMS root.content_scale_aspect = Window.CONTENT_SCALE_ASPECT_EXPAND root.content_scale_size = VIEWPORT experience = Controller.new() experience.persistence_enabled = false experience.locale = "zh_CN" experience.size = Vector2(VIEWPORT) experience.configure_entry(Fixture.new().migrated_snapshot()) root.add_child(experience) await settle_frames(12) var equipment_id := String(experience.region_market.state.current_run.market_board.equipment_offers[0].offer_id) await tap("P102EquipmentTarget_%s" % equipment_id) expect(experience.region_focused_equipment == equipment_id, "parsed equipment touch opens its exact consequence preview") var order: Array = Array(experience.region_market.state.current_run.deployed_recruit_ids).duplicate() if order.size() >= 2: await drag("P102CompanyTarget_%s" % String(order[-1]), "P102CompanyTarget_%s" % String(order[0])) expect(experience.region_market.state.current_run.deployed_recruit_ids != order, "parsed ScreenDrag changes the deployed order") await play_round(5, 0, "channel_thread_adjacent") await play_round(6, 1, "safe_index_advanced") expect(experience.screen == Controller.P103_SCREEN_ARTIFACT, "parsed flow reaches the Artifact shrine") await tap("P103ArtifactTarget_AR-012") expect(experience.screen == Controller.P103_SCREEN_PROMOTION, "parsed Artifact choice reaches the promotion anvil") await tap("P103PromotionTarget_PF-A13") expect(experience.screen == Controller.P103_SCREEN_MARKET, "parsed promotion choice returns to Market 7") await play_round(7, 2, "fieldmender_patient_repositioned") expect(experience.screen == Controller.P103_SCREEN_MARKET_8, "parsed flow reaches stable Market 8") expect(experience.region_market.state.current_run.active_artifact_ids == ["AR-012"], "parsed Artifact choice persists") expect(experience.input_touch_count == parsed_touches, "controller counts every parsed ScreenTouch press") expect(experience.input_drag_count == parsed_drags, "controller counts every parsed ScreenDrag and no direct drag") experience.queue_free() await settle_frames(45) if failures.is_empty(): print("ABG_P10_3_RUNTIME_TOUCH_FLOW_OK markets=5,6,7,8 rounds=3 equipment=inspect order=drag routes=3 artifact=AR-012 promotion=PF-A13 touch=%d drag=%d fallback=0 direct=0" % [parsed_touches, parsed_drags]) quit(0) else: for failure in failures: push_error(failure) quit(1) func play_round(market_index: int, risk: int, decisive_kind: String) -> void: var route: Dictionary = experience.region_market.state.current_run.market_board.battle_offers[risk] var plan_id := String(BattleService.PREFERRED_PLAN[String(route.route_id)]) await tap("P102RouteTarget_%s" % String(route.offer_id)) await tap("P102PrepareRouteButton") expect(experience.screen == Controller.P103_SCREEN_PLAN, "Round %d parsed route opens plan choice" % market_index) await tap("P102PlanTarget_%s" % plan_id) expect(experience.screen == Controller.P103_SCREEN_BATTLE, "Round %d parsed plan starts battle" % market_index) await tap("P101SpeedButton") var frames := 0 while not experience.region_battle_complete and frames < 720: await process_frame frames += 1 expect(experience.region_battle_complete, "Round %d automatic playback terminates" % market_index) expect(int(experience.region_event_counts.get(decisive_kind, 0)) == 1, "Round %d presents %s once" % [market_index, decisive_kind]) await tap("P101SettleButton") expect(int(experience.region_market.state.current_run.market_index) == market_index + 1, "Round %d settlement opens the next Market" % market_index) func tap(node_name: String) -> void: var control := experience.find_child(node_name, true, false) as Control expect(control != null, "%s exists before parsed touch" % node_name) if control == null: return var point := root.get_final_transform() * control.get_global_rect().get_center() var down := InputEventScreenTouch.new() down.index = 0 down.position = point down.pressed = true Input.parse_input_event(down) parsed_touches += 1 await process_frame var up := InputEventScreenTouch.new() up.index = 0 up.position = point up.pressed = false Input.parse_input_event(up) await settle_frames() func drag(source_name: String, target_name: String) -> void: var source := experience.find_child(source_name, true, false) as Control var target := experience.find_child(target_name, true, false) as Control expect(source != null and target != null, "Line drag targets exist") if source == null or target == null: return var start := root.get_final_transform() * source.get_global_rect().get_center() var finish := root.get_final_transform() * target.get_global_rect().get_center() var down := InputEventScreenTouch.new() down.index = 1 down.position = start down.pressed = true Input.parse_input_event(down) parsed_touches += 1 await process_frame var motion := InputEventScreenDrag.new() motion.index = 1 motion.position = finish motion.relative = finish - start Input.parse_input_event(motion) parsed_drags += 1 await process_frame var up := InputEventScreenTouch.new() up.index = 1 up.position = finish up.pressed = false Input.parse_input_event(up) await settle_frames() func settle_frames(count := 5) -> void: for _index in count: await process_frame func expect(condition: bool, message: String) -> void: if not condition: failures.append("P10.3 runtime touch: %s" % message)