@tool extends Line2D @export_group("Targets") @export var target_a: Node2D @export var target_b: Node2D @export_group("Cable Settings") @export var segment_count: int = 20 @export var rope_length: float = 300.0 @export var gravity: Vector2 = Vector2(0, 9.8) @export var iterations: int = 5 var points_pos: Array[Vector2] = [] var points_prev: Array[Vector2] = [] var segment_dist: float func _ready(): segment_dist = rope_length / segment_count var start_pos = target_a.global_position if target_a else global_position for i in range(segment_count): points_pos.append(start_pos) points_prev.append(start_pos) points = PackedVector2Array(points_pos) func _physics_process(delta: float): if not target_a or not target_b: return _update_points(delta) for i in range(iterations): _apply_constraints() var local_points = PackedVector2Array() for p in points_pos: local_points.append(to_local(p)) points = local_points func _update_points(delta: float): for i in range(segment_count): var velocity = points_pos[i] - points_prev[i] points_prev[i] = points_pos[i] points_pos[i] += velocity + gravity * delta * 50.0 func _apply_constraints(): points_pos[0] = target_a.global_position points_pos[segment_count - 1] = target_b.global_position for i in range(segment_count - 1): var p1 = points_pos[i] var p2 = points_pos[i+1] var diff = p1 - p2 var distance = diff.length() var error = distance - segment_dist var percent = error / distance var offset = diff * percent * 0.5 if i != 0: points_pos[i] -= offset if i + 1 != segment_count - 1: points_pos[i+1] += offset