extends LimboState

@onready var root: Normal = %Normal

@export_category("Hook Pull Release")
@export var release_distance: float = 12.0
@export var release_dot_threshold: float = 0.0
@export var min_pull_timer: float = 0.08

var _pull_timer := 0.0
var _anchor

var _tween: Tween


func _setup() -> void:
	self.add_event_handler(&"trigger_jump",_handle_trigger_jump)

func _enter() -> void:
	var tween := get_tree().create_tween()
	tween.set_ignore_time_scale(true)

	tween.tween_property(Engine, "time_scale", .25, .03)
	tween.tween_interval(.1)
	tween.tween_property(Engine, "time_scale", 1.0, .05)
	
	var hook_inst: Hook = agent.spawn_hook_comp.get_current_hook_inst()
	if hook_inst: 
		var i = hook_inst.get_direction_id()
	
		#if i >= 0:
			#if i == 0 or i == 4:
				#CameraSystem.get_cached_camera().emit_hook_touch_shock(0)
			#elif i == 1 or i == 5:
				#CameraSystem.get_cached_camera().emit_hook_touch_shock(1)
			#elif i == 2 or i == 6:
				#CameraSystem.get_cached_camera().emit_hook_touch_shock(2)
			#elif i == 3 or i == 7:
				#CameraSystem.get_cached_camera().emit_hook_touch_shock(3)
	
	if root.grap_hook_state._jump_grace_timer > 0:
		_hook_to_jump()
	
	_pull_timer = 0.0
	_anchor = agent.spawn_hook_comp.get_current_hook_anchor()

	if _anchor and is_instance_valid(_anchor):
		agent.locomotion_comp._custom_move_to(_anchor)

func _update(delta: float) -> void:
	_pull_timer += delta

	if _pull_timer < min_pull_timer:
		return
	
	if not _anchor or not is_instance_valid(_anchor):
		_force_release()
		return

	var character : CharacterBody2D = agent
	var pos: Vector2 = character.global_position
	var target_pos: Vector2 = _anchor.global_position

	var to_target := target_pos - pos
	var distance := to_target.length()

	if distance <= release_distance:
		_force_release()
		return

	if distance > 0.001:
		var dir := to_target / distance
		if character.velocity.dot(dir) <= release_dot_threshold:
			_force_release()
			return

func _exit() -> void:
	agent.locomotion_comp.stop_custom_move(false)
	_anchor = null
	
	agent.spawn_hook_comp.release_cached_hook()

func _handle_trigger_jump() -> bool:
	_hook_to_jump()
	return false

func _hook_to_jump() -> void:
	get_root().blackboard.set_var(&"want_to_jump",true)
	self.dispatch(&"hook_to_jump")

func _force_release() -> void:
	agent.locomotion_comp.stop_custom_move(false)
	
	if agent.spawn_hook_comp.has_method("release_hook"):
		agent.spawn_hook_comp.release_hook()
	
	##解除hook
	if agent.is_on_floor():
		self.dispatch(&"exit_on_ground")
	else:
		self.dispatch(&"exit_on_air")
	return
