Use static typing in all demos (#1063)

This leads to code that is easier to understand and runs
faster thanks to GDScript's typed instructions.

The untyped declaration warning is now enabled on all projects
where type hints were added. All projects currently run without
any untyped declration warnings.

Dodge the Creeps and Squash the Creeps demos intentionally don't
use type hints to match the documentation, where type hints haven't
been adopted yet (given its beginner focus).
This commit is contained in:
Hugo Locurcio
2024-06-01 12:12:18 +02:00
committed by GitHub
parent 8e9c180278
commit bac1e69164
498 changed files with 5218 additions and 4776 deletions

View File

@@ -1,15 +1,16 @@
@tool
extends Node3D
@export_range(0, 1, 0.1) var fade = 0.0:
@export_range(0, 1, 0.1) var fade := 0.0:
set(value):
fade = value
if is_inside_tree():
_update_fade()
var material : ShaderMaterial
var material: ShaderMaterial
func _update_fade():
func _update_fade() -> void:
if fade == 0.0:
$MeshInstance3D.visible = false
else:
@@ -17,7 +18,7 @@ func _update_fade():
material.set_shader_parameter("albedo", Color(0.0, 0.0, 0.0, fade))
$MeshInstance3D.visible = true
# Called when the node enters the scene tree for the first time.
func _ready():
func _ready() -> void:
material = $MeshInstance3D.material_override
_update_fade()

View File

@@ -1,75 +1,77 @@
extends CharacterBody3D
# Settings to control the character
@export var rotation_speed : float = 1.0
@export var movement_speed : float = 5.0
@export var movement_acceleration : float = 5.0
# Settings to control the character.
@export var rotation_speed := 1.0
@export var movement_speed := 5.0
@export var movement_acceleration := 5.0
# Get the gravity from the project settings to be synced with RigidBody nodes.
var gravity = ProjectSettings.get_setting("physics/3d/default_gravity")
var gravity := float(ProjectSettings.get_setting("physics/3d/default_gravity"))
# Helper variables to keep our code readable
@onready var origin_node : XROrigin3D = $XROrigin3D
@onready var camera_node : XRCamera3D = $XROrigin3D/XRCamera3D
@onready var neck_position_node : Node3D = $XROrigin3D/XRCamera3D/Neck
@onready var black_out : Node3D = $XROrigin3D/XRCamera3D/BlackOut
# Helper variables to keep our code readable.
@onready var origin_node: XROrigin3D = $XROrigin3D
@onready var camera_node: XRCamera3D = $XROrigin3D/XRCamera3D
@onready var neck_position_node: Node3D = $XROrigin3D/XRCamera3D/Neck
@onready var black_out: Node3D = $XROrigin3D/XRCamera3D/BlackOut
# `recenter` is called when the user has requested their view to be recentered.
# The code here assumes the player has walked into an area they shouldn't be
# and we return the player back to the character body.
# But other strategies can be applied here as well such as returning the player
# to a starting position or a checkpoint.
func recenter():
# Calculate where our camera should be, we start with our global transform
## Called when the user has requested their view to be recentered.
func recenter() -> void:
# The code here assumes the player has walked into an area they shouldn't be
# and we return the player back to the character body.
# But other strategies can be applied here as well such as returning the player
# to a starting position or a checkpoint.
# Calculate where our camera should be, we start with our global transform.
var new_camera_transform : Transform3D = global_transform
# Set to the height of our neck joint
# Set to the height of our neck joint.
new_camera_transform.origin.y = neck_position_node.global_position.y
# Apply transform our our next position to get our desired camera transform
# Apply transform our our next position to get our desired camera transform.
new_camera_transform = new_camera_transform * neck_position_node.transform.inverse()
# Remove tilt from camera transform
# Remove tilt from camera transform.
var camera_transform : Transform3D = camera_node.transform
var forward_dir : Vector3 = camera_transform.basis.z
forward_dir.y = 0.0
camera_transform = camera_transform.looking_at(camera_transform.origin + forward_dir.normalized(), Vector3.UP, true)
# Update our XR location
# Update our XR location.
origin_node.global_transform = new_camera_transform * camera_transform.inverse()
# `_get_movement_input` returns our move input by querying the move action on each controller
# Returns our move input by querying the move action on each controller.
func _get_movement_input() -> Vector2:
var movement : Vector2 = Vector2()
var movement := Vector2()
# If move is not bound to one of our controllers,
# that controller will return a Vector2(0.0, 0.0)
# that controller will return `Vector2.ZERO`.
movement += $XROrigin3D/LeftHand.get_vector2("move")
movement += $XROrigin3D/RightHand.get_vector2("move")
return movement
# `_process_on_physical_movement` handles the physical movement of the player
# `_process_on_physical_movement()` handles the physical movement of the player
# adjusting our character body position to "catch up to" the player.
# If the character body encounters an obstruction our view will black out
# and we will stop further character movement until the player physically
# moves back.
func _process_on_physical_movement(delta) -> bool:
# Remember our current velocity, we'll apply that later
var current_velocity = velocity
func _process_on_physical_movement(delta: float) -> bool:
# Remember our current velocity, as we'll apply that later.
var current_velocity := velocity
# Start by rotating the player to face the same way our real player is
# Start by rotating the player to face the same way our real player is.
var camera_basis: Basis = origin_node.transform.basis * camera_node.transform.basis
var forward: Vector2 = Vector2(camera_basis.z.x, camera_basis.z.z)
var angle: float = forward.angle_to(Vector2(0.0, 1.0))
# Rotate our character body
# Rotate our character body.
transform.basis = transform.basis.rotated(Vector3.UP, angle)
# Reverse this rotation our origin node
# Reverse this rotation our origin node.
origin_node.transform = Transform3D().rotated(Vector3.UP, -angle) * origin_node.transform
# Now apply movement, first move our player body to the right location
# Now apply movement, first move our player body to the right location.
var org_player_body: Vector3 = global_transform.origin
var player_body_location: Vector3 = origin_node.transform * camera_node.transform * neck_position_node.transform.origin
player_body_location.y = 0.0
@@ -78,34 +80,33 @@ func _process_on_physical_movement(delta) -> bool:
velocity = (player_body_location - org_player_body) / delta
move_and_slide()
# Now move our XROrigin back
var delta_movement = global_transform.origin - org_player_body
# Now move our XROrigin back.
var delta_movement := global_transform.origin - org_player_body
origin_node.global_transform.origin -= delta_movement
# Negate any height change in local space due to player hitting ramps etc.
# Negate any height change in local space due to player hitting ramps, etc.
origin_node.transform.origin.y = 0.0
# Return our value
# Return our value.
velocity = current_velocity
# Check if we managed to move where we wanted to
var location_offset = (player_body_location - global_transform.origin).length()
# Check if we managed to move where we wanted to.
var location_offset := (player_body_location - global_transform.origin).length()
if location_offset > 0.1:
# We couldn't go where we wanted to, black out our screen
black_out.fade = clamp((location_offset - 0.1) / 0.1, 0.0, 1.0)
# We couldn't go where we wanted to, black out our screen.
black_out.fade = clampf((location_offset - 0.1) / 0.1, 0.0, 1.0)
return true
else:
black_out.fade = 0.0
return false
# `_process_movement_on_input` handles movement through controller input.
# `_process_movement_on_input()` handles movement through controller input.
# We first handle rotating the player and then apply movement.
# We also apply the effects of gravity at this point.
func _process_movement_on_input(is_colliding, delta):
if !is_colliding:
func _process_movement_on_input(is_colliding: bool, delta: float) -> void:
if not is_colliding:
# Only handle input if we've not physically moved somewhere we shouldn't.
var movement_input = _get_movement_input()
var movement_input := _get_movement_input()
# First handle rotation, to keep this example simple we are implementing
# "smooth" rotation here. This can lead to motion sickness.
@@ -117,7 +118,7 @@ func _process_movement_on_input(is_colliding, delta):
# Straffing can be added by using the movement_input.x input
# and using a different input for rotational control.
# Straffing is more prone to motion sickness.
var direction = global_transform.basis * Vector3(0.0, 0.0, -movement_input.y) * movement_speed
var direction := global_transform.basis * Vector3(0.0, 0.0, -movement_input.y) * movement_speed
if direction:
velocity.x = move_toward(velocity.x, direction.x, delta * movement_acceleration)
velocity.z = move_toward(velocity.z, direction.z, delta * movement_acceleration)
@@ -130,7 +131,7 @@ func _process_movement_on_input(is_colliding, delta):
move_and_slide()
# _physics_process handles our player movement.
func _physics_process(delta):
var is_colliding = _process_on_physical_movement(delta)
# `_physics_process()` handles our player movement.
func _physics_process(delta: float) -> void:
var is_colliding := _process_on_physical_movement(delta)
_process_movement_on_input(is_colliding, delta)

View File

@@ -11,10 +11,14 @@ config_version=5
[application]
config/name="OpenXR Character Centric Movement"
config/tags=PackedStringArray("demo", "official", "xr")
run/main_scene="res://main.tscn"
config/features=PackedStringArray("4.2", "GL Compatibility")
config/icon="res://icon.svg"
config/tags=PackedStringArray("demo", "official", "xr")
[debug]
gdscript/warnings/untyped_declaration=1
[rendering]

View File

@@ -7,29 +7,28 @@ signal pose_recentered
@export var maximum_refresh_rate : int = 90
var xr_interface : OpenXRInterface
var xr_is_focussed = false
var xr_is_focused := false
# Called when the node enters the scene tree for the first time.
func _ready():
func _ready() -> void:
xr_interface = XRServer.find_interface("OpenXR")
if xr_interface and xr_interface.is_initialized():
print("OpenXR instantiated successfully.")
var vp : Viewport = get_viewport()
# Enable XR on our viewport
# Enable XR on our viewport.
vp.use_xr = true
# Make sure v-sync is off, v-sync is handled by OpenXR
# Make sure V-Sync is off, as V-Sync is handled by OpenXR.
DisplayServer.window_set_vsync_mode(DisplayServer.VSYNC_DISABLED)
# Enable VRS
# Enable variable rate shading.
if RenderingServer.get_rendering_device():
vp.vrs_mode = Viewport.VRS_XR
elif int(ProjectSettings.get_setting("xr/openxr/foveation_level")) == 0:
push_warning("OpenXR: Recommend setting Foveation level to High in Project Settings")
# Connect the OpenXR events
# Connect the OpenXR events.
xr_interface.session_begun.connect(_on_openxr_session_begun)
xr_interface.session_visible.connect(_on_openxr_visible_state)
xr_interface.session_focussed.connect(_on_openxr_focused_state)
@@ -41,22 +40,22 @@ func _ready():
get_tree().quit()
# Handle OpenXR session ready
# Handle OpenXR session ready.
func _on_openxr_session_begun() -> void:
# Get the reported refresh rate
var current_refresh_rate = xr_interface.get_display_refresh_rate()
# Get the reported refresh rate.
var current_refresh_rate := xr_interface.get_display_refresh_rate()
if current_refresh_rate > 0:
print("OpenXR: Refresh rate reported as ", str(current_refresh_rate))
else:
print("OpenXR: No refresh rate given by XR runtime")
# See if we have a better refresh rate available
var new_rate = current_refresh_rate
var available_rates : Array = xr_interface.get_available_display_refresh_rates()
if available_rates.size() == 0:
# See if we have a better refresh rate available.
var new_rate := current_refresh_rate
var available_rates: Array[float] = xr_interface.get_available_display_refresh_rates()
if available_rates.is_empty():
print("OpenXR: Target does not support refresh rate extension")
elif available_rates.size() == 1:
# Only one available, so use it
# Only one available, so use it.
new_rate = available_rates[0]
else:
for rate in available_rates:
@@ -69,20 +68,21 @@ func _on_openxr_session_begun() -> void:
xr_interface.set_display_refresh_rate(new_rate)
current_refresh_rate = new_rate
# Now match our physics rate
Engine.physics_ticks_per_second = current_refresh_rate
# Now match our physics rate. This is currently needed to avoid jittering,
# due to physics interpolation not being used.
Engine.physics_ticks_per_second = roundi(current_refresh_rate)
# Handle OpenXR visible state
# Handle OpenXR visible state.
func _on_openxr_visible_state() -> void:
# We always pass this state at startup,
# but the second time we get this it means our player took off their headset
if xr_is_focussed:
# but the second time we get this, it means our player took off their headset.
if xr_is_focused:
print("OpenXR lost focus")
xr_is_focussed = false
xr_is_focused = false
# pause our game
# Pause our game.
process_mode = Node.PROCESS_MODE_DISABLED
focus_lost.emit()
@@ -91,19 +91,21 @@ func _on_openxr_visible_state() -> void:
# Handle OpenXR focused state
func _on_openxr_focused_state() -> void:
print("OpenXR gained focus")
xr_is_focussed = true
xr_is_focused = true
# unpause our game
# Unpause our game.
process_mode = Node.PROCESS_MODE_INHERIT
focus_gained.emit()
# Handle OpenXR stopping state
# Handle OpenXR stopping state.
func _on_openxr_stopping() -> void:
# Our session is being stopped.
print("OpenXR is stopping")
# Handle OpenXR pose recentered signal
# Handle OpenXR pose recentered signal.
func _on_openxr_pose_recentered() -> void:
# User recentered view, we have to react to this by recentering the view.
# This is game implementation dependent.

View File

@@ -1,15 +1,15 @@
@tool
extends Node3D
@export_range(0, 1, 0.1) var fade = 0.0:
@export_range(0, 1, 0.1) var fade := 0.0:
set(value):
fade = value
if is_inside_tree():
_update_fade()
var material : ShaderMaterial
var material: ShaderMaterial
func _update_fade():
func _update_fade() -> void:
if fade == 0.0:
$MeshInstance3D.visible = false
else:
@@ -17,7 +17,7 @@ func _update_fade():
material.set_shader_parameter("albedo", Color(0.0, 0.0, 0.0, fade))
$MeshInstance3D.visible = true
# Called when the node enters the scene tree for the first time.
func _ready():
func _ready() -> void:
material = $MeshInstance3D.material_override
_update_fade()

View File

@@ -1,53 +1,53 @@
extends XROrigin3D
# Settings to control the character
@export var rotation_speed : float = 1.0
@export var movement_speed : float = 5.0
@export var movement_acceleration : float = 5.0
# Settings to control the character.
@export var rotation_speed := 1.0
@export var movement_speed := 5.0
@export var movement_acceleration := 5.0
# Get the gravity from the project settings to be synced with RigidBody nodes.
var gravity = ProjectSettings.get_setting("physics/3d/default_gravity")
var gravity := float(ProjectSettings.get_setting("physics/3d/default_gravity"))
# Helper variables to keep our code readable
# Helper variables to keep our code readable.
@onready var character_body : CharacterBody3D = $CharacterBody3D
@onready var camera_node : XRCamera3D = $XRCamera3D
@onready var neck_position_node : Node3D = $XRCamera3D/Neck
@onready var black_out : Node3D = $XRCamera3D/BlackOut
# `recenter` is called when the user has requested their view to be recentered.
# The code here assumes the player has walked into an area they shouldn't be
# and we return the player back to the character body.
# But other strategies can be applied here as well such as returning the player
# to a starting position or a checkpoint.
func recenter():
# Calculate where our camera should be, we start with our global transform
var new_camera_transform : Transform3D = character_body.global_transform
## Called when the user has requested their view to be recentered.
func recenter() -> void:
# The code here assumes the player has walked into an area they shouldn't be
# and we return the player back to the character body.
# But other strategies can be applied here as well such as returning the player
# to a starting position or a checkpoint.
# Set to the height of our neck joint
# Calculate where our camera should be, we start with our global transform.
var new_camera_transform: Transform3D = character_body.global_transform
# Set to the height of our neck joint.
new_camera_transform.origin.y = neck_position_node.global_position.y
# Apply transform our our next position to get our desired camera transform
# Apply transform our our next position to get our desired camera transform.
new_camera_transform = new_camera_transform * neck_position_node.transform.inverse()
# Remove tilt from camera transform
var camera_transform : Transform3D = camera_node.transform
var forward_dir : Vector3 = camera_transform.basis.z
# Remove tilt from camera transform.
var camera_transform: Transform3D = camera_node.transform
var forward_dir: Vector3 = camera_transform.basis.z
forward_dir.y = 0.0
camera_transform = camera_transform.looking_at(camera_transform.origin + forward_dir.normalized(), Vector3.UP, true)
# Update our XR location
# Update our XR location.
global_transform = new_camera_transform * camera_transform.inverse()
# Recenter character body
# Recenter character body.
character_body.transform = Transform3D()
# `_get_movement_input` returns our move input by querying the move action on each controller
# `_get_movement_input()` returns our move input by querying the move action on each controller.
func _get_movement_input() -> Vector2:
var movement : Vector2 = Vector2()
# If move is not bound to one of our controllers,
# that controller will return a Vector2(0.0, 0.0)
# that controller will return `Vector2.ZERO`.
movement += $LeftHand.get_vector2("move")
movement += $RightHand.get_vector2("move")
@@ -58,33 +58,33 @@ func _get_movement_input() -> Vector2:
# If the character body encounters an obstruction our view will black out
# and we will stop further character movement until the player physically
# moves back.
func _process_on_physical_movement(delta) -> bool:
# Remember our current velocity, we'll apply that later
var current_velocity = character_body.velocity
func _process_on_physical_movement(delta: float) -> bool:
# Remember our current velocity, as we'll apply that later.
var current_velocity := character_body.velocity
# Remember where our player body currently is
# Remember where our player body currently is.
var org_player_body: Vector3 = character_body.global_transform.origin
# Determine where our player body should be
# Determine where our player body should be.
var player_body_location: Vector3 = camera_node.transform * neck_position_node.transform.origin
player_body_location.y = 0.0
player_body_location = global_transform * player_body_location
# Attempt to move our character
# Attempt to move our character.
character_body.velocity = (player_body_location - org_player_body) / delta
character_body.move_and_slide()
# Set back to our current value
# Set back to our current value.
character_body.velocity = current_velocity
# Check if we managed to move all the way, ignoring height change
var movement_left = player_body_location - character_body.global_transform.origin
# Check if we managed to move all the way, ignoring height change.
var movement_left := player_body_location - character_body.global_transform.origin
movement_left.y = 0.0
# Check if we managed to move where we wanted to
var location_offset = movement_left.length()
# Check if we managed to move where we wanted to.
var location_offset := movement_left.length()
if location_offset > 0.1:
# We couldn't go where we wanted to, black out our screen
# We couldn't go where we wanted to, black out our screen.
black_out.fade = clamp((location_offset - 0.1) / 0.1, 0.0, 1.0)
return true
@@ -92,23 +92,25 @@ func _process_on_physical_movement(delta) -> bool:
black_out.fade = 0.0
return false
func _copy_player_rotation_to_character_body():
# We only copy our forward direction to our character body, we ignore tilt
var camera_forward: Vector3 = -camera_node.global_transform.basis.z
var body_forward: Vector3 = Vector3(camera_forward.x, 0.0, camera_forward.z)
func _copy_player_rotation_to_character_body() -> void:
# We only copy our forward direction to our character body, we ignore tilt.
var camera_forward := -camera_node.global_transform.basis.z
var body_forward := Vector3(camera_forward.x, 0.0, camera_forward.z)
character_body.global_transform.basis = Basis.looking_at(body_forward, Vector3.UP)
# `_process_movement_on_input` handles movement through controller input.
# We first handle rotating the player and then apply movement.
# We also apply the effects of gravity at this point.
func _process_movement_on_input(is_colliding, delta):
# Remember where our player body currently is
func _process_movement_on_input(is_colliding: bool, delta: float) -> void:
# Remember where our player body currently is.
var org_player_body: Vector3 = character_body.global_transform.origin
if !is_colliding:
if not is_colliding:
# Only handle input if we've not physically moved somewhere we shouldn't.
var movement_input = _get_movement_input()
var movement_input := _get_movement_input()
# First handle rotation, to keep this example simple we are implementing
# "smooth" rotation here. This can lead to motion sickness.
@@ -119,15 +121,15 @@ func _process_movement_on_input(is_colliding, delta):
var t2 := Transform3D()
var rot := Transform3D()
# We are going to rotate the origin around the player
var player_position = character_body.global_transform.origin - global_transform.origin
# We are going to rotate the origin around the player.
var player_position := character_body.global_transform.origin - global_transform.origin
t1.origin = -player_position
t2.origin = player_position
rot = rot.rotated(Vector3(0.0, 1.0, 0.0), -movement_input.x * delta * rotation_speed)
global_transform = (global_transform * t2 * rot * t1).orthonormalized()
# Now ensure our player body is facing the correct way as well
# Now ensure our player body is facing the correct way as well.
_copy_player_rotation_to_character_body()
# Now handle forward/backwards movement.
@@ -142,16 +144,17 @@ func _process_movement_on_input(is_colliding, delta):
character_body.velocity.x = move_toward(character_body.velocity.x, 0, delta * movement_acceleration)
character_body.velocity.z = move_toward(character_body.velocity.z, 0, delta * movement_acceleration)
# Always handle gravity
# Always handle gravity.
character_body.velocity.y -= gravity * delta
# Attempt to move our player
# Attempt to move our player.
character_body.move_and_slide()
# And now apply the actual movement to our origin
# And now apply the actual movement to our origin.
global_transform.origin += character_body.global_transform.origin - org_player_body
# _physics_process handles our player movement.
func _physics_process(delta):
var is_colliding = _process_on_physical_movement(delta)
func _physics_process(delta: float) -> void:
var is_colliding := _process_on_physical_movement(delta)
_process_movement_on_input(is_colliding, delta)

View File

@@ -11,10 +11,14 @@ config_version=5
[application]
config/name="OpenXR Origin Centric Movement"
config/tags=PackedStringArray("demo", "official", "xr")
run/main_scene="res://main.tscn"
config/features=PackedStringArray("4.2", "GL Compatibility")
config/icon="res://icon.svg"
config/tags=PackedStringArray("demo", "official", "xr")
[debug]
gdscript/warnings/untyped_declaration=1
[rendering]

View File

@@ -4,32 +4,31 @@ signal focus_lost
signal focus_gained
signal pose_recentered
@export var maximum_refresh_rate : int = 90
@export var maximum_refresh_rate: int = 90
var xr_interface : OpenXRInterface
var xr_is_focussed = false
var xr_interface: OpenXRInterface
var xr_is_focused := false
# Called when the node enters the scene tree for the first time.
func _ready():
func _ready() -> void:
xr_interface = XRServer.find_interface("OpenXR")
if xr_interface and xr_interface.is_initialized():
print("OpenXR instantiated successfully.")
var vp : Viewport = get_viewport()
var vp: Viewport = get_viewport()
# Enable XR on our viewport
# Enable XR on our viewport.
vp.use_xr = true
# Make sure v-sync is off, v-sync is handled by OpenXR
# Make sure V-Sync is off, as V-Sync is handled by OpenXR.
DisplayServer.window_set_vsync_mode(DisplayServer.VSYNC_DISABLED)
# Enable VRS
# Enable variable rate shading.
if RenderingServer.get_rendering_device():
vp.vrs_mode = Viewport.VRS_XR
elif int(ProjectSettings.get_setting("xr/openxr/foveation_level")) == 0:
push_warning("OpenXR: Recommend setting Foveation level to High in Project Settings")
# Connect the OpenXR events
# Connect the OpenXR events.
xr_interface.session_begun.connect(_on_openxr_session_begun)
xr_interface.session_visible.connect(_on_openxr_visible_state)
xr_interface.session_focussed.connect(_on_openxr_focused_state)
@@ -41,22 +40,22 @@ func _ready():
get_tree().quit()
# Handle OpenXR session ready
# Handle OpenXR session ready.
func _on_openxr_session_begun() -> void:
# Get the reported refresh rate
var current_refresh_rate = xr_interface.get_display_refresh_rate()
# Get the reported refresh rate.
var current_refresh_rate := xr_interface.get_display_refresh_rate()
if current_refresh_rate > 0:
print("OpenXR: Refresh rate reported as ", str(current_refresh_rate))
else:
print("OpenXR: No refresh rate given by XR runtime")
# See if we have a better refresh rate available
var new_rate = current_refresh_rate
var available_rates : Array = xr_interface.get_available_display_refresh_rates()
if available_rates.size() == 0:
# See if we have a better refresh rate available.
var new_rate := current_refresh_rate
var available_rates: Array[float] = xr_interface.get_available_display_refresh_rates()
if available_rates.is_empty():
print("OpenXR: Target does not support refresh rate extension")
elif available_rates.size() == 1:
# Only one available, so use it
# Only one available, so use it.
new_rate = available_rates[0]
else:
for rate in available_rates:
@@ -69,20 +68,21 @@ func _on_openxr_session_begun() -> void:
xr_interface.set_display_refresh_rate(new_rate)
current_refresh_rate = new_rate
# Now match our physics rate
Engine.physics_ticks_per_second = current_refresh_rate
# Now match our physics rate. This is currently needed to avoid jittering,
# due to physics interpolation not being used.
Engine.physics_ticks_per_second = roundi(current_refresh_rate)
# Handle OpenXR visible state
func _on_openxr_visible_state() -> void:
# We always pass this state at startup,
# but the second time we get this it means our player took off their headset
if xr_is_focussed:
# but the second time we get this, it means our player took off their headset.
if xr_is_focused:
print("OpenXR lost focus")
xr_is_focussed = false
xr_is_focused = false
# pause our game
# Pause our game.
process_mode = Node.PROCESS_MODE_DISABLED
focus_lost.emit()
@@ -91,19 +91,19 @@ func _on_openxr_visible_state() -> void:
# Handle OpenXR focused state
func _on_openxr_focused_state() -> void:
print("OpenXR gained focus")
xr_is_focussed = true
xr_is_focused = true
# unpause our game
# Unpause our game.
process_mode = Node.PROCESS_MODE_INHERIT
focus_gained.emit()
# Handle OpenXR stopping state
# Handle OpenXR stopping state.
func _on_openxr_stopping() -> void:
# Our session is being stopped.
print("OpenXR is stopping")
# Handle OpenXR pose recentered signal
# Handle OpenXR pose recentered signal.
func _on_openxr_pose_recentered() -> void:
# User recentered view, we have to react to this by recentering the view.
# This is game implementation dependent.