173 lines
5.3 KiB
GDScript
173 lines
5.3 KiB
GDScript
extends Node2D
|
|
|
|
var spaceState:World2D
|
|
var query : PhysicsPointQueryParameters2D
|
|
var CastResult : Array
|
|
|
|
var hoveredColliders : Array
|
|
var hoveredCollider:CollisionObject2D
|
|
var hoveredStickerNode:Sticker
|
|
var grabbedStickerNode:Sticker
|
|
var grabbedStickerOffset:Vector2
|
|
|
|
enum CURSOR_STATE {DEFAULT, CLICK, GRAB, GRABBED}
|
|
var currentCursorState:CURSOR_STATE = CURSOR_STATE.DEFAULT
|
|
var oldCursorState:CURSOR_STATE = CURSOR_STATE.DEFAULT
|
|
var cursorPlaying:bool
|
|
|
|
# Called when the node enters the scene tree for the first time.
|
|
func _ready():
|
|
if not OS.is_debug_build():
|
|
Input.set_mouse_mode(Input.MOUSE_MODE_CONFINED_HIDDEN)
|
|
query = PhysicsPointQueryParameters2D.new()
|
|
spaceState = get_world_2d()
|
|
|
|
# Called every frame. 'delta' is the elapsed time since the previous frame.
|
|
func _process(_delta):
|
|
#region Cursor Position
|
|
position = get_global_mouse_position()
|
|
#endregion
|
|
pointcast()
|
|
cursor_look()
|
|
if (grabbedStickerNode != null):
|
|
grabbedStickerNode.get_parent().position = grabbedStickerOffset+get_global_mouse_position()
|
|
|
|
|
|
func pointcast():
|
|
resetCast()
|
|
query.collide_with_areas = true
|
|
query.collide_with_bodies = false
|
|
query.position = get_global_mouse_position()
|
|
CastResult = spaceState.direct_space_state.intersect_point(query)
|
|
# CastResult is not reliable. Objects are added randomly in the array
|
|
# so we need to filter/sort the trace result
|
|
if ( CastResult.size() > 0 and (grabbedStickerNode == null)):
|
|
|
|
#region Fill hoveredColliders
|
|
for _object in CastResult:
|
|
if(_object.collider.input_pickable == true):
|
|
hoveredColliders.append(_object.collider)
|
|
#endregion
|
|
if (hoveredColliders.size() > 0):
|
|
if (hoveredColliders.size() >= 2):
|
|
hoveredColliders = sortByPosY(hoveredColliders,false)
|
|
if (hoveredColliders[0] != hoveredCollider):
|
|
$GrabTimer.stop()
|
|
if (hoveredCollider and hoveredCollider.has_method("on_unhover")):
|
|
hoveredCollider.on_unhover()
|
|
hoveredCollider = hoveredColliders[0]
|
|
if (hoveredCollider and hoveredCollider.has_method("on_hover")):
|
|
hoveredCollider.on_hover()
|
|
print("Current hovered object :", hoveredCollider)
|
|
if (Global.isSticker(hoveredCollider)):
|
|
hoveredStickerNode = hoveredCollider
|
|
print("Current hovered sticker :", hoveredStickerNode)
|
|
else:
|
|
hoveredStickerNode = null
|
|
else:
|
|
resetCast(true)
|
|
else:
|
|
resetCast(true)
|
|
|
|
func resetCast(bFull = false):
|
|
CastResult.clear()
|
|
hoveredColliders.clear()
|
|
if bFull:
|
|
if (hoveredCollider != null and hoveredCollider.has_method("on_unhover") and (hoveredCollider != grabbedStickerNode)):
|
|
hoveredCollider.on_unhover()
|
|
hoveredCollider = null
|
|
hoveredStickerNode = null
|
|
|
|
## Sort objects by parent's Y position
|
|
func sortByPosY(objects: Array, ascending_order: bool = true):
|
|
var _tempArray :Array
|
|
var _tempStickerArray :Array
|
|
_tempArray = objects
|
|
#filter stickers
|
|
for _collider in _tempArray:
|
|
if _collider is Sticker:
|
|
_tempStickerArray.append(_collider)
|
|
if _tempStickerArray.size() > 0:
|
|
_tempArray = _tempStickerArray
|
|
_tempArray.sort_custom(comparePosY)
|
|
# Reverse if descending order is required
|
|
if not ascending_order:
|
|
_tempArray.reverse()
|
|
return _tempArray
|
|
|
|
func comparePosY(a, b):
|
|
#print("Compare ",a," at ",a.position.y, " and ",b," at ",b.position.y )
|
|
return a.get_parent().position.y < b.get_parent().position.y #Sticker are always at 0, so we need parent position
|
|
|
|
|
|
func _input(rawInputEvent:InputEvent):
|
|
if (rawInputEvent.is_action_pressed("select")):
|
|
cursorClick()
|
|
$GrabTimer.start()
|
|
if (rawInputEvent.is_action_released("select")):
|
|
$GrabTimer.stop()
|
|
if (grabbedStickerNode != null):
|
|
grab_end()
|
|
|
|
func grab_start():
|
|
if (hoveredStickerNode and grabbedStickerNode == null):
|
|
grabbedStickerNode = hoveredStickerNode
|
|
|
|
print("Grabbed ", grabbedStickerNode)
|
|
grabbedStickerOffset = grabbedStickerNode.get_parent().position - get_global_mouse_position()
|
|
print("offset =", grabbedStickerOffset, " Stickpos:",grabbedStickerNode.get_parent().position,"-",get_global_mouse_position() )
|
|
if (grabbedStickerNode.has_method("on_grab")):
|
|
grabbedStickerNode.on_grab(grabbedStickerOffset)
|
|
|
|
func grab_end():
|
|
if (grabbedStickerNode.has_method("on_released")):
|
|
grabbedStickerNode.on_unhover()
|
|
grabbedStickerNode.on_released()
|
|
|
|
|
|
print("stopg grabbin at ",query.position )
|
|
DebugDraw.points.append(query.position)
|
|
DebugDraw.drawPoints()
|
|
|
|
grabbedStickerNode = null
|
|
|
|
func cursorClick():
|
|
if (hoveredCollider and hoveredCollider.has_method("on_click")):
|
|
hoveredCollider.on_click()
|
|
|
|
func cursor_look():
|
|
if (grabbedStickerNode ):
|
|
currentCursorState = CURSOR_STATE.GRABBED
|
|
elif (hoveredStickerNode):
|
|
if ($GrabTimer and !($GrabTimer.is_stopped())):
|
|
currentCursorState = CURSOR_STATE.GRABBED
|
|
else:
|
|
currentCursorState = CURSOR_STATE.GRAB
|
|
elif ($GrabTimer and !($GrabTimer.is_stopped())):
|
|
currentCursorState = CURSOR_STATE.CLICK
|
|
else:
|
|
currentCursorState = CURSOR_STATE.DEFAULT
|
|
|
|
if (currentCursorState != oldCursorState):
|
|
oldCursorState = currentCursorState
|
|
match oldCursorState:
|
|
CURSOR_STATE.DEFAULT:
|
|
$AnimatedSprite2D.play("default")
|
|
CURSOR_STATE.CLICK:
|
|
$AnimatedSprite2D.play("click")
|
|
CURSOR_STATE.GRAB:
|
|
$AnimatedSprite2D.play("grab_intro")
|
|
CURSOR_STATE.GRABBED:
|
|
$AnimatedSprite2D.play("grab")
|
|
|
|
|
|
func _on_grab_timer_timeout():
|
|
grab_start()
|
|
|
|
|
|
func _on_animated_sprite_2d_animation_changed():
|
|
cursorPlaying = true
|
|
|
|
|
|
func _on_animated_sprite_2d_animation_finished():
|
|
cursorPlaying = false
|