diff options
| author | dam <dam@gudinoff> | 2022-01-01 04:56:58 +0000 |
|---|---|---|
| committer | dam <dam@gudinoff> | 2022-01-01 04:56:58 +0000 |
| commit | c59f89e99c90c0e756cdf780bcbf04d782eb3e6f (patch) | |
| tree | afeea78d9d5f68092f61d573dff2f677b1c40aa8 /pointer_input_sensor.gd | |
| parent | 7f0580b6b49a9dbafc54a0190bf573503c54417a (diff) | |
| download | surgery-log-c59f89e99c90c0e756cdf780bcbf04d782eb3e6f.tar.zst surgery-log-c59f89e99c90c0e756cdf780bcbf04d782eb3e6f.zip | |
Change touch scroll detection to pointer-input-sensor approach using signals/events.
Diffstat (limited to 'pointer_input_sensor.gd')
| -rw-r--r-- | pointer_input_sensor.gd | 84 |
1 files changed, 84 insertions, 0 deletions
diff --git a/pointer_input_sensor.gd b/pointer_input_sensor.gd new file mode 100644 index 0000000..95e1b4b --- /dev/null +++ b/pointer_input_sensor.gd @@ -0,0 +1,84 @@ +extends Control +class_name PointerInputSensor + +export var drag_threshold_cm: float = 0.250 + +signal on_press +signal on_release +#signal on_release_outside +signal on_click +signal on_enter +signal on_exit +#signal on_exit_app_window +signal on_begin_drag +signal on_drag +signal on_end_drag + +class PointerInputData: + var target: PointerInputSensor + var index := -1 + var initial_position := Vector2.ZERO + var current_position := Vector2.ZERO + var relative_position = Vector2.ZERO + var velocity := Vector2.ZERO + var was_dragged := false + var is_pressed := false + +var pointer: PointerInputData +var screen_dpcm: float +var on_process: FuncRef + + +func _ready(): + screen_dpcm = float(OS.get_screen_dpi()) / 2.54 + pointer = PointerInputData.new() + pointer.target = self + connect("mouse_entered", self, "_on_enter_exit", [true]) + connect("mouse_entered", self, "_on_enter_exit", [false]) + + +func _process(delta: float): + if on_process != null && on_process.is_valid(): + on_process.call_func(delta, self) + + +func _on_enter_exit(is_inside: bool): + emit_signal("on_enter" if is_inside else "on_exit", pointer) + + +func _gui_input(event: InputEvent): + + # @DAM A bug on GODOT-3.X makes events from non-mouse-emulated pointers (index > 0) unreliable. + if event is InputEventScreenTouch || event is InputEventScreenDrag: + if event.index != 0: + return + + if event is InputEventScreenTouch && (pointer.is_pressed == false || pointer.index == event.index): + var touch := event as InputEventScreenTouch + pointer.is_pressed = event.pressed + pointer.current_position = get_global_mouse_position() + if pointer.is_pressed: + pointer.index = touch.index + pointer.initial_position = get_global_mouse_position() + emit_signal("on_press", pointer) + else: + emit_signal("on_release", pointer) + if pointer.was_dragged == false: + emit_signal("on_click", pointer) + else: + emit_signal("on_end_drag", pointer) + pointer.index = -1 + pointer.was_dragged = false + + if event is InputEventScreenDrag && event.index == pointer.index: + var drag := event as InputEventScreenDrag + pointer.current_position = get_global_mouse_position() + pointer.velocity = drag.speed + pointer.relative_position = drag.relative + # @DAM Instead of constantly converting the pointer distance to cm... just conver the drag_threshold_cm to pixels + if pointer.was_dragged == false && pointer.current_position.distance_to(pointer.initial_position) / screen_dpcm > drag_threshold_cm: + pointer.was_dragged = true + emit_signal("on_begin_drag", pointer) + emit_signal("on_drag", pointer) + + |
