Fix bug where only net_pickable could disable XRToolPickables
This commit is contained in:
@@ -35,6 +35,9 @@ properties/1/replication_mode = 1
|
||||
properties/2/path = NodePath("NetPickable:net_held_by")
|
||||
properties/2/spawn = true
|
||||
properties/2/replication_mode = 1
|
||||
properties/3/path = NodePath(".:enabled")
|
||||
properties/3/spawn = false
|
||||
properties/3/replication_mode = 1
|
||||
|
||||
[sub_resource type="Gradient" id="Gradient_s6exe"]
|
||||
interpolation_mode = 2
|
||||
|
||||
+22
-4
@@ -24,6 +24,12 @@ var _original_freeze_mode: RigidBody3D.FreezeMode
|
||||
# branch of apply_held_state() clears while someone else is holding the item.
|
||||
var _original_enabled: bool
|
||||
|
||||
# Intent set by external game logic (e.g. a station enabling/disabling a tool),
|
||||
# independent of hold state. apply_held_state() is the sole writer of the
|
||||
# pickable's actual `enabled` property, so this is how other systems express
|
||||
# "should be enabled" without fighting that reconciliation every tick.
|
||||
var _tool_enabled: bool = true
|
||||
|
||||
# Whether the "our own hand still holds this" guard has already been logged for
|
||||
# the current grab. apply_held_state() runs every network tick, so without this
|
||||
# the guard message repeats for as long as you hold the item.
|
||||
@@ -47,6 +53,17 @@ func _ready() -> void:
|
||||
apply_held_state.call_deferred()
|
||||
|
||||
|
||||
## Called by external game logic (e.g. Counter._enable_tool/_disable_tool) to
|
||||
## express whether this item should be usable right now, independent of hold
|
||||
## state. Reapplies immediately so the change takes effect without waiting for
|
||||
## the next net_held_by tick.
|
||||
func set_tool_enabled(value: bool) -> void:
|
||||
if _tool_enabled == value:
|
||||
return
|
||||
_tool_enabled = value
|
||||
apply_held_state()
|
||||
|
||||
|
||||
func _set_net_held_by(value: int) -> void:
|
||||
var old := net_held_by
|
||||
net_held_by = value
|
||||
@@ -95,10 +112,11 @@ func apply_held_state() -> void:
|
||||
# e.g. a plate still got marked dirty) while pick_up() bailed out on
|
||||
# the disabled item, leaving the zone holding an item with no grab
|
||||
# driver that then fell out of the station.
|
||||
if _pickable.enabled != _original_enabled:
|
||||
var want_enabled_authority := _original_enabled and _tool_enabled
|
||||
if _pickable.enabled != want_enabled_authority:
|
||||
if NetworkManager.is_online():
|
||||
SweetLogger.debug("{0}: reclaiming ownership, restoring enabled {1}->{2}", [_pickable.name, _pickable.enabled, _original_enabled])
|
||||
_pickable.enabled = _original_enabled
|
||||
SweetLogger.debug("{0}: reclaiming ownership, restoring enabled {1}->{2}", [_pickable.name, _pickable.enabled, want_enabled_authority])
|
||||
_pickable.enabled = want_enabled_authority
|
||||
return
|
||||
# A net_held_by/position sync update can race ahead of the
|
||||
# authority-handoff RPC that's about to confirm a grab we just made
|
||||
@@ -125,7 +143,7 @@ func apply_held_state() -> void:
|
||||
# physics-property writes per item per tick. The comparison also means we
|
||||
# still re-apply if something else perturbs the state (e.g. let_go()
|
||||
# restoring the collision mask after a force-drop).
|
||||
var want_enabled := (net_held_by == 0)
|
||||
var want_enabled := (net_held_by == 0) and _tool_enabled
|
||||
if _pickable.freeze \
|
||||
and _pickable.freeze_mode == RigidBody3D.FREEZE_MODE_KINEMATIC \
|
||||
and _pickable.collision_mask == 0 \
|
||||
|
||||
+16
-9
@@ -18,7 +18,7 @@ func _ready() -> void:
|
||||
SweetLogger.warning("{0} missing chop_audio reference", [name])
|
||||
if not knife:
|
||||
SweetLogger.warning("{0} missing knife reference", [name])
|
||||
_hide_all_tools()
|
||||
_disable_all_tools()
|
||||
|
||||
|
||||
func _start_chopping(id: String, work: float) -> void:
|
||||
@@ -33,12 +33,20 @@ func _process(delta: float) -> void:
|
||||
super.process(delta)
|
||||
|
||||
|
||||
|
||||
func _hide_all_tools():
|
||||
knife.visible = false
|
||||
knife.enabled = false
|
||||
func _enable_tool(_item: XRToolsPickable):
|
||||
SweetLogger.debug("Enable tool {0} on {1}", [_item.name, name])
|
||||
_item.visible = true
|
||||
_item.get_node("NetPickable").set_tool_enabled(true)
|
||||
|
||||
|
||||
func _disable_tool(_item: XRToolsPickable):
|
||||
SweetLogger.debug("Disable tool {0} on {1}", [_item.name, name])
|
||||
_item.visible = false
|
||||
_item.get_node("NetPickable").set_tool_enabled(false)
|
||||
|
||||
func _disable_all_tools():
|
||||
SweetLogger.debug("Disable all tools on {0}", [name])
|
||||
_disable_tool(knife)
|
||||
|
||||
|
||||
func _on_gesture_area_body_entered(body: Node3D) -> void:
|
||||
@@ -84,20 +92,19 @@ func on_food_item_picked_up(food_item: FoodItem) -> void:
|
||||
SweetLogger.debug("Held a FoodItem that is not choppable, id: {0} result: {1}", [food_item.id, result])
|
||||
return
|
||||
|
||||
knife.visible = true
|
||||
knife.enabled = true
|
||||
_enable_tool(knife)
|
||||
_start_chopping(result, RecipeManager.get_chopping_work(food_item.id))
|
||||
|
||||
|
||||
# Called from Station base class
|
||||
func on_object_dropped(_item: Node3D) -> void:
|
||||
SweetLogger.debug("->[]")
|
||||
_hide_all_tools()
|
||||
_disable_all_tools()
|
||||
reset()
|
||||
|
||||
|
||||
# Called from Station base class
|
||||
func on_work_complete():
|
||||
SweetLogger.debug("->[]")
|
||||
_hide_all_tools()
|
||||
_disable_all_tools()
|
||||
convert_item()
|
||||
|
||||
Reference in New Issue
Block a user