mirror of
https://github.com/CrispyPin/ovr-utils.git
synced 2025-04-16 00:58:30 +02:00
Compare commits
28 commits
Author | SHA1 | Date | |
---|---|---|---|
b1098a13ec | |||
7edd005bb7 | |||
9f0b811d24 | |||
f892d4892b | |||
e6e003ca51 | |||
d83deb8721 | |||
8725763124 | |||
be9ceeef9c | |||
24ad04e262 | |||
899a3dce3d | |||
710b418970 | |||
23b37778b1 | |||
aaeed533da | |||
ef744db9ae | |||
2bac6afcdc | |||
08cb7dc283 | |||
9eea2a7c28 | |||
97fd916a87 | |||
e1944bcc25 | |||
20bf94d7ab | |||
dc6a9929b7 | |||
a073c19e9c | |||
b673410e70 | |||
f081a963a4 | |||
43d3ce3e16 | |||
a284c87792 | |||
b1eb8eb9d8 | |||
|
588f361f52 |
188 changed files with 1554 additions and 2606 deletions
README.md
docs
ovr-utils
Main.tscn
addons
godot-openvr
meshes
README.mdblinn1.materialblinn2.materialhands_albedo.png.importhands_normal.pnghands_normal.png.importmodels_hands_vr_glove_vmat.materialvr_glove_left_model_slim.glbvr_glove_left_model_slim.glb.importvr_glove_right_model_slim.glbvr_glove_right_model_slim.glb.import
scenes
openvr_overlay
src
Main.tscnOverlayManager.tscnOverlaySettingsSync.tscndefault_env.tresexport_presets.cfg
addons
gdvk
godot-openvr
CHANGES.mdEditorPlugin.gdLICENSEOpenVRAction.gdnsOpenVRConfig.gdnsOpenVRController.gdnsOpenVRExportPlugin.gdOpenVRHaptics.gdnsOpenVROverlay.gdnsOpenVRPose.gdnsOpenVRRenderModel.gdnsOpenVRSkeleton.gdns
actions
actions.jsonbindings_gamepad.jsonbindings_generic.jsonbindings_holographic_controller.jsonbindings_index_controller.jsonbindings_oculus_touch.jsonbindings_vive_controller.json
bin
godot_openvr.gdnlibicon.pngicon.png.importplugin.cfgscenes
openvr_overlay
MissingOverlay.tscnOverlayInstance.tscnOverlayInteraction.tscnOverlayInteractionRoot.tscn
interaction
openvr_overlay.gdoverlay_init.gdoverlay_instance.gdplugin.cfgovr_utils
settings-manager
fonts
|
@ -14,4 +14,3 @@ A cross-platform SteamVR overlay application that aims to have many useful tools
|
||||||
## Usage
|
## Usage
|
||||||
At the moment all interacions are done with the trigger buttons, this will use steamvr actions and be configurable in the future.
|
At the moment all interacions are done with the trigger buttons, this will use steamvr actions and be configurable in the future.
|
||||||
|
|
||||||
To load in images with the `ImageViewer` overlay, they have to be in the user folder; that is `%Appdata%\Roaming\ovr-utils\` on windows or `~/.local/share/ovr-utils/` on linux.
|
|
||||||
|
|
35
docs/README.md
Normal file
35
docs/README.md
Normal file
|
@ -0,0 +1,35 @@
|
||||||
|
# WIP documentation
|
||||||
|
|
||||||
|
## Hierarchy
|
||||||
|
|
||||||
|
```
|
||||||
|
OverlayManager
|
||||||
|
- MyOverlayInstance
|
||||||
|
- [...]
|
||||||
|
- OverlayViewport
|
||||||
|
- Container
|
||||||
|
- MyOverlay
|
||||||
|
- [...]
|
||||||
|
- OverlayInteraction
|
||||||
|
- VR
|
||||||
|
- [colliders for vr trackers etc]
|
||||||
|
- Grabbable
|
||||||
|
- Clickable
|
||||||
|
- Touchable
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
|
## overlay interaction types
|
||||||
|
Each overlay instance has a OverlayInteraction node, which spawns the different interaction modules depending on what is defined in the OVERLAY_PROPERTIES.
|
||||||
|
|
||||||
|
The modules/interaction types are:
|
||||||
|
- Grabbable
|
||||||
|
- Touchable
|
||||||
|
- Clickable
|
||||||
|
|
||||||
|
These modules connect signals from different places to the interaction manager (`OverlayInteraction`)
|
||||||
|
Touchable connects collision signals to mouse inputs (potentially logic between to help prevent double presses)
|
||||||
|
Clickable connects vr button signals to mouse inputs
|
||||||
|
Grabbable connects vr button signals to grab logic, while telling the interaction manager to pause normal interaction
|
||||||
|
|
|
@ -1,3 +0,0 @@
|
||||||
[gd_scene format=2]
|
|
||||||
|
|
||||||
[node name="Main" type="Node"]
|
|
|
@ -1,5 +0,0 @@
|
||||||
The resources here are taken from: `Steam\steamapps\common\SteamVR\resources\rendermodels\vr_glove\`
|
|
||||||
|
|
||||||
To save space in the repository only the slim models are included while the texture maps have been taken from the full versions.
|
|
||||||
|
|
||||||
See `../scenes/ovr_left_hand.tscn` and `../scenes/ovr_right_hand.tscn` for implementation details
|
|
Binary file not shown.
Binary file not shown.
|
@ -1,36 +0,0 @@
|
||||||
[remap]
|
|
||||||
|
|
||||||
importer="texture"
|
|
||||||
type="StreamTexture"
|
|
||||||
path.s3tc="res://.import/hands_albedo.png-149a10baba7906560a9f9eab8fadf1d8.s3tc.stex"
|
|
||||||
path.etc2="res://.import/hands_albedo.png-149a10baba7906560a9f9eab8fadf1d8.etc2.stex"
|
|
||||||
metadata={
|
|
||||||
"imported_formats": [ "s3tc", "etc2" ],
|
|
||||||
"vram_texture": true
|
|
||||||
}
|
|
||||||
|
|
||||||
[deps]
|
|
||||||
|
|
||||||
source_file="res://addons/godot-openvr/meshes/hands_albedo.png"
|
|
||||||
dest_files=[ "res://.import/hands_albedo.png-149a10baba7906560a9f9eab8fadf1d8.s3tc.stex", "res://.import/hands_albedo.png-149a10baba7906560a9f9eab8fadf1d8.etc2.stex" ]
|
|
||||||
|
|
||||||
[params]
|
|
||||||
|
|
||||||
compress/mode=2
|
|
||||||
compress/lossy_quality=0.7
|
|
||||||
compress/hdr_mode=0
|
|
||||||
compress/bptc_ldr=0
|
|
||||||
compress/normal_map=0
|
|
||||||
flags/repeat=true
|
|
||||||
flags/filter=true
|
|
||||||
flags/mipmaps=true
|
|
||||||
flags/anisotropic=false
|
|
||||||
flags/srgb=1
|
|
||||||
process/fix_alpha_border=true
|
|
||||||
process/premult_alpha=false
|
|
||||||
process/HDR_as_SRGB=false
|
|
||||||
process/invert_color=false
|
|
||||||
stream=false
|
|
||||||
size_limit=0
|
|
||||||
detect_3d=false
|
|
||||||
svg/scale=1.0
|
|
Binary file not shown.
Before ![]() (image error) Size: 29 MiB |
|
@ -1,36 +0,0 @@
|
||||||
[remap]
|
|
||||||
|
|
||||||
importer="texture"
|
|
||||||
type="StreamTexture"
|
|
||||||
path.s3tc="res://.import/hands_normal.png-eab7a86e959f13e1294e8f67904a8873.s3tc.stex"
|
|
||||||
path.etc2="res://.import/hands_normal.png-eab7a86e959f13e1294e8f67904a8873.etc2.stex"
|
|
||||||
metadata={
|
|
||||||
"imported_formats": [ "s3tc", "etc2" ],
|
|
||||||
"vram_texture": true
|
|
||||||
}
|
|
||||||
|
|
||||||
[deps]
|
|
||||||
|
|
||||||
source_file="res://addons/godot-openvr/meshes/hands_normal.png"
|
|
||||||
dest_files=[ "res://.import/hands_normal.png-eab7a86e959f13e1294e8f67904a8873.s3tc.stex", "res://.import/hands_normal.png-eab7a86e959f13e1294e8f67904a8873.etc2.stex" ]
|
|
||||||
|
|
||||||
[params]
|
|
||||||
|
|
||||||
compress/mode=2
|
|
||||||
compress/lossy_quality=0.7
|
|
||||||
compress/hdr_mode=0
|
|
||||||
compress/bptc_ldr=0
|
|
||||||
compress/normal_map=1
|
|
||||||
flags/repeat=true
|
|
||||||
flags/filter=true
|
|
||||||
flags/mipmaps=true
|
|
||||||
flags/anisotropic=false
|
|
||||||
flags/srgb=2
|
|
||||||
process/fix_alpha_border=true
|
|
||||||
process/premult_alpha=false
|
|
||||||
process/HDR_as_SRGB=false
|
|
||||||
process/invert_color=false
|
|
||||||
stream=false
|
|
||||||
size_limit=0
|
|
||||||
detect_3d=false
|
|
||||||
svg/scale=1.0
|
|
Binary file not shown.
Binary file not shown.
File diff suppressed because it is too large
Load diff
Binary file not shown.
File diff suppressed because it is too large
Load diff
|
@ -1,42 +0,0 @@
|
||||||
[gd_scene load_steps=5 format=2]
|
|
||||||
|
|
||||||
[ext_resource path="res://addons/godot-openvr/meshes/vr_glove_left_model_slim.glb" type="PackedScene" id=1]
|
|
||||||
[ext_resource path="res://addons/godot-openvr/meshes/models_hands_vr_glove_vmat.material" type="Material" id=2]
|
|
||||||
[ext_resource path="res://addons/godot-openvr/OpenVRPose.gdns" type="Script" id=3]
|
|
||||||
[ext_resource path="res://addons/godot-openvr/OpenVRSkeleton.gdns" type="Script" id=4]
|
|
||||||
|
|
||||||
[node name="ovr_left_hand" instance=ExtResource( 1 )]
|
|
||||||
script = ExtResource( 3 )
|
|
||||||
action = "/actions/godot/in/left_hand"
|
|
||||||
|
|
||||||
[node name="Skeleton" parent="RootNode" index="0"]
|
|
||||||
bones/5/bound_children = [ NodePath("Thumb") ]
|
|
||||||
bones/10/bound_children = [ NodePath("Index") ]
|
|
||||||
bones/15/bound_children = [ NodePath("Middle") ]
|
|
||||||
bones/20/bound_children = [ NodePath("Ring") ]
|
|
||||||
bones/25/bound_children = [ NodePath("Pinky") ]
|
|
||||||
script = ExtResource( 4 )
|
|
||||||
action = "/actions/godot/in/left_hand"
|
|
||||||
|
|
||||||
[node name="vr_glove_left_slim" parent="RootNode/Skeleton" index="0"]
|
|
||||||
material/0 = ExtResource( 2 )
|
|
||||||
|
|
||||||
[node name="Thumb" type="BoneAttachment" parent="RootNode/Skeleton" index="1"]
|
|
||||||
transform = Transform( -0.347509, 0.0284256, 0.937246, -0.13095, -0.991217, -0.0184906, 0.928488, -0.129158, 0.348178, -0.0498674, 0.056092, 0.112777 )
|
|
||||||
bone_name = "finger_thumb_l_end"
|
|
||||||
|
|
||||||
[node name="Index" type="BoneAttachment" parent="RootNode/Skeleton" index="2"]
|
|
||||||
transform = Transform( -0.717079, -0.669965, 0.19221, -0.076153, -0.19881, -0.977075, 0.69282, -0.715277, 0.0915429, -0.0345977, 0.0355404, 0.164767 )
|
|
||||||
bone_name = "finger_index_l_end"
|
|
||||||
|
|
||||||
[node name="Middle" type="BoneAttachment" parent="RootNode/Skeleton" index="3"]
|
|
||||||
transform = Transform( -0.755126, -0.650532, 0.0812012, -0.0513261, -0.064817, -0.996576, 0.653568, -0.756708, 0.0155557, -0.0321126, 0.00654218, 0.171613 )
|
|
||||||
bone_name = "finger_middle_l_end"
|
|
||||||
|
|
||||||
[node name="Ring" type="BoneAttachment" parent="RootNode/Skeleton" index="4"]
|
|
||||||
transform = Transform( -0.749612, -0.661178, -0.0304372, -0.0961052, 0.154228, -0.98335, 0.654864, -0.734206, -0.179154, -0.0346831, -0.0253934, 0.156924 )
|
|
||||||
bone_name = "finger_ring_l_end"
|
|
||||||
|
|
||||||
[node name="Pinky" type="BoneAttachment" parent="RootNode/Skeleton" index="5"]
|
|
||||||
transform = Transform( -0.615435, -0.749373, -0.244295, -0.0354297, 0.335934, -0.941219, 0.787391, -0.570604, -0.233296, -0.0270969, -0.0462902, 0.133467 )
|
|
||||||
bone_name = "finger_pinky_l_end"
|
|
|
@ -1,42 +0,0 @@
|
||||||
[gd_scene load_steps=5 format=2]
|
|
||||||
|
|
||||||
[ext_resource path="res://addons/godot-openvr/meshes/vr_glove_right_model_slim.glb" type="PackedScene" id=1]
|
|
||||||
[ext_resource path="res://addons/godot-openvr/meshes/models_hands_vr_glove_vmat.material" type="Material" id=2]
|
|
||||||
[ext_resource path="res://addons/godot-openvr/OpenVRPose.gdns" type="Script" id=3]
|
|
||||||
[ext_resource path="res://addons/godot-openvr/OpenVRSkeleton.gdns" type="Script" id=4]
|
|
||||||
|
|
||||||
[node name="ovr_right_hand" instance=ExtResource( 1 )]
|
|
||||||
script = ExtResource( 3 )
|
|
||||||
action = "/actions/godot/in/right_hand"
|
|
||||||
|
|
||||||
[node name="Skeleton" parent="RootNode" index="0"]
|
|
||||||
bones/5/bound_children = [ NodePath("Thumb") ]
|
|
||||||
bones/10/bound_children = [ NodePath("Index") ]
|
|
||||||
bones/15/bound_children = [ NodePath("Middle") ]
|
|
||||||
bones/20/bound_children = [ NodePath("Ring") ]
|
|
||||||
bones/25/bound_children = [ NodePath("Pinky") ]
|
|
||||||
script = ExtResource( 4 )
|
|
||||||
action = "/actions/godot/in/right_hand"
|
|
||||||
|
|
||||||
[node name="vr_glove_right_slim" parent="RootNode/Skeleton" index="0"]
|
|
||||||
material/0 = ExtResource( 2 )
|
|
||||||
|
|
||||||
[node name="Thumb" type="BoneAttachment" parent="RootNode/Skeleton" index="1"]
|
|
||||||
transform = Transform( -0.347509, 0.0284256, 0.937246, 0.130949, 0.991217, 0.0184906, -0.928488, 0.129158, -0.348179, 0.0498674, 0.0560921, 0.112777 )
|
|
||||||
bone_name = "finger_thumb_r_end"
|
|
||||||
|
|
||||||
[node name="Index" type="BoneAttachment" parent="RootNode/Skeleton" index="2"]
|
|
||||||
transform = Transform( -0.717079, -0.669965, 0.19221, 0.0761528, 0.19881, 0.977075, -0.69282, 0.715277, -0.0915429, 0.0345977, 0.0355405, 0.164767 )
|
|
||||||
bone_name = "finger_index_r_end"
|
|
||||||
|
|
||||||
[node name="Middle" type="BoneAttachment" parent="RootNode/Skeleton" index="3"]
|
|
||||||
transform = Transform( -0.755126, -0.650532, 0.0812013, 0.0513261, 0.064817, 0.996577, -0.653568, 0.756708, -0.0155557, 0.0321126, 0.00654219, 0.171613 )
|
|
||||||
bone_name = "finger_middle_r_end"
|
|
||||||
|
|
||||||
[node name="Ring" type="BoneAttachment" parent="RootNode/Skeleton" index="4"]
|
|
||||||
transform = Transform( -0.749612, -0.661178, -0.0304372, 0.0961052, -0.154228, 0.98335, -0.654864, 0.734206, 0.179154, 0.0346831, -0.0253934, 0.156924 )
|
|
||||||
bone_name = "finger_ring_r_end"
|
|
||||||
|
|
||||||
[node name="Pinky" type="BoneAttachment" parent="RootNode/Skeleton" index="5"]
|
|
||||||
transform = Transform( -0.615435, -0.749373, -0.244295, 0.0354297, -0.335934, 0.941219, -0.787391, 0.570604, 0.233296, 0.0270969, -0.0462902, 0.133467 )
|
|
||||||
bone_name = "finger_pinky_r_end"
|
|
|
@ -1,6 +0,0 @@
|
||||||
[gd_scene load_steps=2 format=2]
|
|
||||||
|
|
||||||
[ext_resource path="res://addons/openvr_overlay/interaction/overlay_cursor.gd" type="Script" id=1]
|
|
||||||
|
|
||||||
[node name="OverlayCursor" type="Node"]
|
|
||||||
script = ExtResource( 1 )
|
|
|
@ -1,6 +0,0 @@
|
||||||
[gd_scene load_steps=2 format=2]
|
|
||||||
|
|
||||||
[ext_resource path="res://addons/openvr_overlay/interaction/overlay_grab.gd" type="Script" id=1]
|
|
||||||
|
|
||||||
[node name="OverlayGrab" type="Node"]
|
|
||||||
script = ExtResource( 1 )
|
|
|
@ -1,10 +0,0 @@
|
||||||
[gd_scene load_steps=2 format=2]
|
|
||||||
|
|
||||||
[sub_resource type="BoxShape" id=1]
|
|
||||||
resource_local_to_scene = true
|
|
||||||
extents = Vector3( 0.2, 0.2, 0.01 )
|
|
||||||
|
|
||||||
[node name="OverlayArea" type="Area"]
|
|
||||||
|
|
||||||
[node name="CollisionShape" type="CollisionShape" parent="."]
|
|
||||||
shape = SubResource( 1 )
|
|
|
@ -1,70 +0,0 @@
|
||||||
extends Node
|
|
||||||
|
|
||||||
|
|
||||||
var cursor_node = preload("res://addons/openvr_overlay/interaction/Cursor.tscn").instance()
|
|
||||||
onready var viewport: Viewport = get_node("../../OverlayViewport")
|
|
||||||
onready var _i = get_parent()
|
|
||||||
|
|
||||||
var curr_pos: Vector2
|
|
||||||
var prev_pos := Vector2(-1000, 1000)
|
|
||||||
|
|
||||||
func _ready() -> void:
|
|
||||||
viewport.add_child(cursor_node)
|
|
||||||
get_parent().connect("trigger_on", self, "_trigger_on")
|
|
||||||
get_parent().connect("trigger_off", self, "_trigger_off")
|
|
||||||
|
|
||||||
|
|
||||||
func _process(_delta: float) -> void:
|
|
||||||
curr_pos = get_canvas_pos()
|
|
||||||
_update_cursor()
|
|
||||||
_send_move_event()
|
|
||||||
prev_pos = curr_pos
|
|
||||||
|
|
||||||
|
|
||||||
#get canvas position of active controller
|
|
||||||
func get_canvas_pos() -> Vector2:
|
|
||||||
if not _i.active_controller:
|
|
||||||
return Vector2(-1000, 1000) # offscreen
|
|
||||||
|
|
||||||
var controller_local_pos = _i._overlay_area.global_transform.xform_inv(\
|
|
||||||
_i.tracker_nodes[_i.active_controller].translation)
|
|
||||||
var pos = Vector2(controller_local_pos.x, controller_local_pos.y)
|
|
||||||
|
|
||||||
var overlay_size = Vector2(2048, 2048)
|
|
||||||
# scale to pixels
|
|
||||||
pos *= overlay_size.x
|
|
||||||
pos /= _i.get_parent().width_meters
|
|
||||||
# adjust to center
|
|
||||||
pos.y *= -1
|
|
||||||
pos += overlay_size * 0.5
|
|
||||||
return pos
|
|
||||||
|
|
||||||
|
|
||||||
func _update_cursor():
|
|
||||||
cursor_node.rect_position = get_canvas_pos()
|
|
||||||
|
|
||||||
|
|
||||||
func _send_move_event():
|
|
||||||
var event = InputEventMouseMotion.new()
|
|
||||||
event.position = prev_pos
|
|
||||||
event.relative = curr_pos - prev_pos
|
|
||||||
event.speed = event.relative
|
|
||||||
viewport.input(event)
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
func _send_click_event(state: bool):
|
|
||||||
var click_event = InputEventMouseButton.new()
|
|
||||||
click_event.position = curr_pos
|
|
||||||
click_event.pressed = state
|
|
||||||
click_event.button_index = 1
|
|
||||||
viewport.input(click_event)
|
|
||||||
|
|
||||||
|
|
||||||
func _trigger_on():
|
|
||||||
_send_click_event(true)
|
|
||||||
|
|
||||||
|
|
||||||
func _trigger_off():
|
|
||||||
_send_click_event(false)
|
|
||||||
|
|
|
@ -1,126 +0,0 @@
|
||||||
extends Node
|
|
||||||
|
|
||||||
signal touch_on # a controller entered
|
|
||||||
signal touch_off # a controller exited
|
|
||||||
signal trigger_on # trigger pushed while touching
|
|
||||||
signal trigger_off# trigger released
|
|
||||||
|
|
||||||
var touch_state := false
|
|
||||||
var trigger_state := false
|
|
||||||
var grab_mode := false setget set_grab_mode
|
|
||||||
|
|
||||||
# controller that currently has the trigger down
|
|
||||||
var active_controller := ""
|
|
||||||
# reference to the area node thats used for touch
|
|
||||||
var _overlay_area = preload("res://addons/openvr_overlay/interaction/OverlayArea.tscn").instance()
|
|
||||||
var _right_is_activator := false # this hand has a collider on it to trigger things on the overlay
|
|
||||||
var _left_is_activator := false
|
|
||||||
|
|
||||||
var pause_triggers := false # disable triggers updating
|
|
||||||
|
|
||||||
onready var tracker_nodes = {
|
|
||||||
"head": $VR/head,
|
|
||||||
"left": $VR/left,
|
|
||||||
"right": $VR/right,
|
|
||||||
"world": $VR
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
func _ready() -> void:
|
|
||||||
add_child(_overlay_area)
|
|
||||||
_overlay_area.connect("body_entered", self, "_on_OverlayArea_entered")
|
|
||||||
_overlay_area.connect("body_exited", self, "_on_OverlayArea_exited")
|
|
||||||
|
|
||||||
get_parent().connect("width_changed", self, "_update_width")
|
|
||||||
get_parent().connect("offset_changed", self, "_update_offset")
|
|
||||||
get_parent().connect("target_changed", self, "_update_target")
|
|
||||||
|
|
||||||
OverlayManager.connect("grab_mode_changed", self, "update_selection")
|
|
||||||
|
|
||||||
_update_width()
|
|
||||||
_update_offset()
|
|
||||||
_update_target()
|
|
||||||
|
|
||||||
|
|
||||||
func _trigger_on(controller):
|
|
||||||
if touch_state:
|
|
||||||
active_controller = controller
|
|
||||||
trigger_state = true
|
|
||||||
emit_signal("trigger_on")
|
|
||||||
|
|
||||||
|
|
||||||
func _trigger_off():
|
|
||||||
trigger_state = false
|
|
||||||
emit_signal("trigger_off")
|
|
||||||
|
|
||||||
|
|
||||||
func _on_OverlayArea_entered(body: Node) -> void:
|
|
||||||
if body.get_node("../../..") != self or pause_triggers or !get_parent().overlay_visible:
|
|
||||||
return
|
|
||||||
touch_state = true
|
|
||||||
active_controller = body.get_parent().name
|
|
||||||
update_selection()
|
|
||||||
emit_signal("touch_on")
|
|
||||||
|
|
||||||
|
|
||||||
func _on_OverlayArea_exited(body: Node) -> void:
|
|
||||||
if body.get_node("../../..") != self or pause_triggers or !get_parent().overlay_visible:
|
|
||||||
return
|
|
||||||
# TODO revert to other controller if both were touching (edge case)
|
|
||||||
active_controller = ""
|
|
||||||
touch_state = false
|
|
||||||
update_selection()
|
|
||||||
emit_signal("touch_off")
|
|
||||||
|
|
||||||
|
|
||||||
func update_selection():
|
|
||||||
var sel = touch_state and (Settings.s.grab_mode or grab_mode)
|
|
||||||
get_parent().get_node("OverlayViewport/Selected").visible = sel
|
|
||||||
|
|
||||||
|
|
||||||
func set_grab_mode(state: bool) -> void:
|
|
||||||
grab_mode = state
|
|
||||||
update_selection()
|
|
||||||
|
|
||||||
|
|
||||||
func _update_width():
|
|
||||||
var ratio = OverlayInit.ovr_interface.get_render_targetsize()
|
|
||||||
var extents = get_parent().width_meters * 0.5
|
|
||||||
_overlay_area.get_child(0).shape.set_extents(Vector3(extents, extents * ratio.y/ratio.x, 0.05))
|
|
||||||
|
|
||||||
|
|
||||||
func _update_offset():
|
|
||||||
_overlay_area.translation = get_parent().translation
|
|
||||||
_overlay_area.rotation = get_parent().rotation
|
|
||||||
|
|
||||||
|
|
||||||
func _update_target():
|
|
||||||
# reparent _overlay_area
|
|
||||||
_overlay_area.get_parent().remove_child(_overlay_area)
|
|
||||||
tracker_nodes[get_parent().current_target].add_child(_overlay_area)
|
|
||||||
|
|
||||||
_left_is_activator = get_parent().current_target != "left"
|
|
||||||
_right_is_activator = get_parent().current_target != "right"
|
|
||||||
# toggle appropriate colliders
|
|
||||||
$VR/left/OverlayActivator/Collision.disabled = !_left_is_activator
|
|
||||||
$VR/right/OverlayActivator/Collision.disabled = !_right_is_activator
|
|
||||||
|
|
||||||
|
|
||||||
func _on_RightHand_button_pressed(button: int) -> void:
|
|
||||||
if button == JOY_VR_TRIGGER and _right_is_activator:
|
|
||||||
_trigger_on("right")
|
|
||||||
|
|
||||||
|
|
||||||
func _on_RightHand_button_release(button: int) -> void:
|
|
||||||
if button == JOY_VR_TRIGGER and active_controller == "right":
|
|
||||||
_trigger_off()
|
|
||||||
|
|
||||||
|
|
||||||
func _on_LeftHand_button_pressed(button: int) -> void:
|
|
||||||
if button == JOY_VR_TRIGGER and _left_is_activator:
|
|
||||||
_trigger_on("left")
|
|
||||||
|
|
||||||
|
|
||||||
func _on_LeftHand_button_release(button: int) -> void:
|
|
||||||
if button == JOY_VR_TRIGGER and active_controller == "left":
|
|
||||||
_trigger_off()
|
|
6
src/Main.tscn
Normal file
6
src/Main.tscn
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
[gd_scene format=2]
|
||||||
|
|
||||||
|
[node name="Main" type="Node"]
|
||||||
|
__meta__ = {
|
||||||
|
"_editor_description_": "Everything is loaded using autoloads so this scene is just a dummy"
|
||||||
|
}
|
|
@ -8,6 +8,5 @@
|
||||||
script = ExtResource( 4 )
|
script = ExtResource( 4 )
|
||||||
|
|
||||||
[node name="MainOverlay" parent="." instance=ExtResource( 2 )]
|
[node name="MainOverlay" parent="." instance=ExtResource( 2 )]
|
||||||
add_cursor = true
|
|
||||||
|
|
||||||
[node name="OverlaySettingsSync" parent="MainOverlay" instance=ExtResource( 3 )]
|
[node name="OverlaySettingsSync" parent="MainOverlay" instance=ExtResource( 3 )]
|
6
src/addons/gdvk/GDVK.tscn
Normal file
6
src/addons/gdvk/GDVK.tscn
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
[gd_scene load_steps=2 format=2]
|
||||||
|
|
||||||
|
[ext_resource path="res://addons/gdvk/gdvk.gdns" type="Script" id=1]
|
||||||
|
|
||||||
|
[node name="GDVK" type="Node"]
|
||||||
|
script = ExtResource( 1 )
|
BIN
ovr-utils/addons/godot-openvr/meshes/hands_albedo.png → src/addons/gdvk/bin/win64/libgdvk.dll
Normal file → Executable file
BIN
ovr-utils/addons/godot-openvr/meshes/hands_albedo.png → src/addons/gdvk/bin/win64/libgdvk.dll
Normal file → Executable file
Binary file not shown.
Before ![]() (image error) Size: 21 MiB After (image error) Size: 19 MiB ![]() |
BIN
src/addons/gdvk/bin/x11/libgdvk.so
Executable file
BIN
src/addons/gdvk/bin/x11/libgdvk.so
Executable file
Binary file not shown.
17
src/addons/gdvk/gdvk.gdnlib
Normal file
17
src/addons/gdvk/gdvk.gdnlib
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
[general]
|
||||||
|
|
||||||
|
singleton=false
|
||||||
|
load_once=true
|
||||||
|
symbol_prefix="gdvk_"
|
||||||
|
reloadable=true
|
||||||
|
|
||||||
|
[entry]
|
||||||
|
|
||||||
|
X11.64="res://addons/gdvk/bin/x11/libgdvk.so"
|
||||||
|
Windows.64="res://addons/gdvk/bin/win64/libgdvk.dll"
|
||||||
|
|
||||||
|
[dependencies]
|
||||||
|
|
||||||
|
X11.64=[ ]
|
||||||
|
Windows.64=[ ]
|
||||||
|
OSX.64=[ ]
|
8
src/addons/gdvk/gdvk.gdns
Normal file
8
src/addons/gdvk/gdvk.gdns
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
[gd_resource type="NativeScript" load_steps=2 format=2]
|
||||||
|
|
||||||
|
[ext_resource path="res://addons/gdvk/gdvk.gdnlib" type="GDNativeLibrary" id=1]
|
||||||
|
|
||||||
|
[resource]
|
||||||
|
resource_name = "gdvk"
|
||||||
|
class_name = "GDVK"
|
||||||
|
library = ExtResource( 1 )
|
10
src/addons/gdvk/gdvk_plugin.gd
Normal file
10
src/addons/gdvk/gdvk_plugin.gd
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
tool
|
||||||
|
extends EditorPlugin
|
||||||
|
|
||||||
|
|
||||||
|
func _enter_tree() -> void:
|
||||||
|
add_autoload_singleton("GDVK", "res://addons/gdvk/GDVK.tscn")
|
||||||
|
|
||||||
|
|
||||||
|
func _exit_tree() -> void:
|
||||||
|
remove_autoload_singleton("GDVK")
|
9
src/addons/gdvk/plugin.cfg
Normal file
9
src/addons/gdvk/plugin.cfg
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
[plugin]
|
||||||
|
|
||||||
|
name="GDVK"
|
||||||
|
description="Godot virtual keyboard plugin
|
||||||
|
|
||||||
|
see https://github.com/CrispyPin/gdvk"
|
||||||
|
author="CrispyPin"
|
||||||
|
version="0.1.0"
|
||||||
|
script="gdvk_plugin.gd"
|
Before ![]() (image error) Size: 3.4 KiB After ![]() (image error) Size: 3.4 KiB ![]() ![]() |
|
@ -1,6 +1,7 @@
|
||||||
[gd_scene load_steps=5 format=2]
|
[gd_scene load_steps=6 format=2]
|
||||||
|
|
||||||
[ext_resource path="res://addons/openvr_overlay/overlay_instance.gd" type="Script" id=1]
|
[ext_resource path="res://addons/openvr_overlay/overlay_instance.gd" type="Script" id=1]
|
||||||
|
[ext_resource path="res://addons/openvr_overlay/OverlayInteraction.tscn" type="PackedScene" id=2]
|
||||||
[ext_resource path="res://addons/godot-openvr/OpenVROverlay.gdns" type="Script" id=3]
|
[ext_resource path="res://addons/godot-openvr/OpenVROverlay.gdns" type="Script" id=3]
|
||||||
|
|
||||||
[sub_resource type="StyleBoxFlat" id=1]
|
[sub_resource type="StyleBoxFlat" id=1]
|
||||||
|
@ -21,7 +22,6 @@ script = ExtResource( 1 )
|
||||||
[node name="OverlayViewport" type="Viewport" parent="."]
|
[node name="OverlayViewport" type="Viewport" parent="."]
|
||||||
size = Vector2( 2048, 2048 )
|
size = Vector2( 2048, 2048 )
|
||||||
transparent_bg = true
|
transparent_bg = true
|
||||||
handle_input_locally = false
|
|
||||||
hdr = false
|
hdr = false
|
||||||
disable_3d = true
|
disable_3d = true
|
||||||
usage = 0
|
usage = 0
|
||||||
|
@ -64,3 +64,5 @@ texture = SubResource( 2 )
|
||||||
expand = true
|
expand = true
|
||||||
stretch_mode = 5
|
stretch_mode = 5
|
||||||
flip_v = true
|
flip_v = true
|
||||||
|
|
||||||
|
[node name="OverlayInteraction" parent="." instance=ExtResource( 2 )]
|
|
@ -1,7 +1,7 @@
|
||||||
[gd_scene load_steps=3 format=2]
|
[gd_scene load_steps=3 format=2]
|
||||||
|
|
||||||
[ext_resource path="res://addons/openvr_overlay/interaction/overlay_interaction.gd" type="Script" id=1]
|
[ext_resource path="res://addons/openvr_overlay/interaction/overlay_interaction.gd" type="Script" id=1]
|
||||||
[ext_resource path="res://addons/openvr_overlay/interaction/OverlayActivator.tscn" type="PackedScene" id=6]
|
[ext_resource path="res://addons/openvr_overlay/interaction/OverlayArea.tscn" type="PackedScene" id=2]
|
||||||
|
|
||||||
[node name="OverlayInteraction" type="Node"]
|
[node name="OverlayInteraction" type="Node"]
|
||||||
script = ExtResource( 1 )
|
script = ExtResource( 1 )
|
||||||
|
@ -10,16 +10,14 @@ script = ExtResource( 1 )
|
||||||
|
|
||||||
[node name="left" type="ARVRController" parent="VR"]
|
[node name="left" type="ARVRController" parent="VR"]
|
||||||
|
|
||||||
[node name="OverlayActivator" parent="VR/left" instance=ExtResource( 6 )]
|
|
||||||
|
|
||||||
[node name="right" type="ARVRController" parent="VR"]
|
[node name="right" type="ARVRController" parent="VR"]
|
||||||
controller_id = 2
|
controller_id = 2
|
||||||
|
|
||||||
[node name="OverlayActivator" parent="VR/right" instance=ExtResource( 6 )]
|
|
||||||
|
|
||||||
[node name="head" type="ARVRCamera" parent="VR"]
|
[node name="head" type="ARVRCamera" parent="VR"]
|
||||||
visible = false
|
visible = false
|
||||||
|
|
||||||
|
[node name="OverlayArea" parent="." instance=ExtResource( 2 )]
|
||||||
|
|
||||||
[connection signal="button_pressed" from="VR/left" to="." method="_on_LeftHand_button_pressed"]
|
[connection signal="button_pressed" from="VR/left" to="." method="_on_LeftHand_button_pressed"]
|
||||||
[connection signal="button_release" from="VR/left" to="." method="_on_LeftHand_button_release"]
|
[connection signal="button_release" from="VR/left" to="." method="_on_LeftHand_button_release"]
|
||||||
[connection signal="button_pressed" from="VR/right" to="." method="_on_RightHand_button_pressed"]
|
[connection signal="button_pressed" from="VR/right" to="." method="_on_RightHand_button_pressed"]
|
25
src/addons/openvr_overlay/OverlayInteractionRoot.tscn
Normal file
25
src/addons/openvr_overlay/OverlayInteractionRoot.tscn
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
[gd_scene load_steps=2 format=2]
|
||||||
|
|
||||||
|
[ext_resource path="res://addons/openvr_overlay/interaction/HandCollider.tscn" type="PackedScene" id=1]
|
||||||
|
|
||||||
|
[node name="OverlayInteractionRoot" type="Node"]
|
||||||
|
|
||||||
|
[node name="VR" type="ARVROrigin" parent="."]
|
||||||
|
|
||||||
|
[node name="left" type="ARVRController" parent="VR"]
|
||||||
|
|
||||||
|
[node name="HandCollider" parent="VR/left" groups=[
|
||||||
|
"left",
|
||||||
|
] instance=ExtResource( 1 )]
|
||||||
|
collision_layer = 20
|
||||||
|
|
||||||
|
[node name="right" type="ARVRController" parent="VR"]
|
||||||
|
controller_id = 2
|
||||||
|
|
||||||
|
[node name="HandCollider" parent="VR/right" groups=[
|
||||||
|
"right",
|
||||||
|
] instance=ExtResource( 1 )]
|
||||||
|
collision_layer = 10
|
||||||
|
|
||||||
|
[node name="head" type="ARVRCamera" parent="VR"]
|
||||||
|
visible = false
|
|
@ -4,7 +4,10 @@
|
||||||
margin = 0.001
|
margin = 0.001
|
||||||
radius = 0.01
|
radius = 0.01
|
||||||
|
|
||||||
[node name="OverlayActivator" type="StaticBody"]
|
[node name="HandCollider" type="Area"]
|
||||||
|
monitoring = false
|
||||||
|
collision_layer = 30
|
||||||
|
collision_mask = 0
|
||||||
|
|
||||||
[node name="Collision" type="CollisionShape" parent="."]
|
[node name="Collision" type="CollisionShape" parent="."]
|
||||||
shape = SubResource( 1 )
|
shape = SubResource( 1 )
|
27
src/addons/openvr_overlay/interaction/OverlayArea.tscn
Normal file
27
src/addons/openvr_overlay/interaction/OverlayArea.tscn
Normal file
|
@ -0,0 +1,27 @@
|
||||||
|
[gd_scene load_steps=3 format=2]
|
||||||
|
|
||||||
|
[sub_resource type="BoxShape" id=1]
|
||||||
|
resource_local_to_scene = true
|
||||||
|
extents = Vector3( 0.2, 0.2, 0.1 )
|
||||||
|
|
||||||
|
[sub_resource type="BoxShape" id=2]
|
||||||
|
resource_local_to_scene = true
|
||||||
|
extents = Vector3( 0.2, 0.2, 0.01 )
|
||||||
|
|
||||||
|
[node name="OverlayArea" type="Spatial"]
|
||||||
|
|
||||||
|
[node name="AreaNear" type="Area" parent="."]
|
||||||
|
monitorable = false
|
||||||
|
collision_layer = 0
|
||||||
|
collision_mask = 6
|
||||||
|
|
||||||
|
[node name="CollisionShape" type="CollisionShape" parent="AreaNear"]
|
||||||
|
shape = SubResource( 1 )
|
||||||
|
|
||||||
|
[node name="AreaTouch" type="Area" parent="."]
|
||||||
|
monitorable = false
|
||||||
|
collision_layer = 0
|
||||||
|
collision_mask = 24
|
||||||
|
|
||||||
|
[node name="CollisionShape" type="CollisionShape" parent="AreaTouch"]
|
||||||
|
shape = SubResource( 2 )
|
Before ![]() (image error) Size: 90 B After ![]() (image error) Size: 90 B ![]() ![]() |
6
src/addons/openvr_overlay/interaction/mod/Clickable.tscn
Normal file
6
src/addons/openvr_overlay/interaction/mod/Clickable.tscn
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
[gd_scene load_steps=2 format=2]
|
||||||
|
|
||||||
|
[ext_resource path="res://addons/openvr_overlay/interaction/mod/clickable.gd" type="Script" id=1]
|
||||||
|
|
||||||
|
[node name="Clickable" type="Node"]
|
||||||
|
script = ExtResource( 1 )
|
6
src/addons/openvr_overlay/interaction/mod/Grabbable.tscn
Normal file
6
src/addons/openvr_overlay/interaction/mod/Grabbable.tscn
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
[gd_scene load_steps=2 format=2]
|
||||||
|
|
||||||
|
[ext_resource path="res://addons/openvr_overlay/interaction/mod/grabbable.gd" type="Script" id=1]
|
||||||
|
|
||||||
|
[node name="Grabbable" type="Node"]
|
||||||
|
script = ExtResource( 1 )
|
7
src/addons/openvr_overlay/interaction/mod/Touchable.tscn
Normal file
7
src/addons/openvr_overlay/interaction/mod/Touchable.tscn
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
[gd_scene load_steps=2 format=2]
|
||||||
|
|
||||||
|
[ext_resource path="res://addons/openvr_overlay/interaction/mod/clickable.gd" type="Script" id=1]
|
||||||
|
|
||||||
|
[node name="Touchable" type="Node"]
|
||||||
|
script = ExtResource( 1 )
|
||||||
|
is_touch = true
|
109
src/addons/openvr_overlay/interaction/mod/clickable.gd
Normal file
109
src/addons/openvr_overlay/interaction/mod/clickable.gd
Normal file
|
@ -0,0 +1,109 @@
|
||||||
|
extends Node
|
||||||
|
|
||||||
|
export var is_touch := false
|
||||||
|
|
||||||
|
onready var viewport: Viewport = get_node("../../OverlayViewport")
|
||||||
|
onready var _i = get_parent()
|
||||||
|
|
||||||
|
var cursor_pos := {
|
||||||
|
"right": Vector2(),
|
||||||
|
"left": Vector2(),
|
||||||
|
}
|
||||||
|
var prev_pos := {
|
||||||
|
"right": Vector2(),
|
||||||
|
"left": Vector2(),
|
||||||
|
}
|
||||||
|
var click := {
|
||||||
|
"right": false,
|
||||||
|
"left": false,
|
||||||
|
}
|
||||||
|
var active_side := ""
|
||||||
|
|
||||||
|
var cursor_nodes := {
|
||||||
|
"right": preload("res://addons/openvr_overlay/interaction/Cursor.tscn").instance(),
|
||||||
|
"left": preload("res://addons/openvr_overlay/interaction/Cursor.tscn").instance(),
|
||||||
|
}
|
||||||
|
|
||||||
|
func _ready() -> void:
|
||||||
|
viewport.add_child(cursor_nodes.right)
|
||||||
|
viewport.add_child(cursor_nodes.left)
|
||||||
|
if is_touch:
|
||||||
|
get_parent().connect("touch_on", self, "_trigger_on")
|
||||||
|
get_parent().connect("touch_off", self, "_trigger_off")
|
||||||
|
else:
|
||||||
|
get_parent().connect("trigger_on", self, "_trigger_on")
|
||||||
|
get_parent().connect("trigger_off", self, "_trigger_off")
|
||||||
|
|
||||||
|
|
||||||
|
func _process(delta: float) -> void:
|
||||||
|
cursor_pos.right = get_canvas_pos("right")
|
||||||
|
cursor_pos.left = get_canvas_pos("left")
|
||||||
|
_update_cursors()
|
||||||
|
# _send_move_event()
|
||||||
|
prev_pos = cursor_pos.duplicate(true)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# get canvas position of controller
|
||||||
|
func get_canvas_pos(controller) -> Vector2:
|
||||||
|
var controller_local_pos = _i._overlay_area.global_transform.xform_inv(\
|
||||||
|
_i.tracker_nodes[controller].translation)
|
||||||
|
var pos = Vector2(controller_local_pos.x, controller_local_pos.y)
|
||||||
|
|
||||||
|
var overlay_size = Vector2(2048, 2048)
|
||||||
|
# scale to pixels
|
||||||
|
pos *= overlay_size.x
|
||||||
|
pos /= _i.get_parent().width_meters
|
||||||
|
# adjust to center
|
||||||
|
pos.y *= -1
|
||||||
|
pos += overlay_size * 0.5
|
||||||
|
return pos
|
||||||
|
|
||||||
|
|
||||||
|
func _update_cursors():
|
||||||
|
cursor_nodes.right.visible = _i.state.right.near
|
||||||
|
cursor_nodes.left.visible = _i.state.left.near
|
||||||
|
cursor_nodes.right.rect_position = cursor_pos.right
|
||||||
|
cursor_nodes.left.rect_position = cursor_pos.left
|
||||||
|
|
||||||
|
|
||||||
|
func _send_move_event():
|
||||||
|
if not active_side:
|
||||||
|
return# only send move events while a cursor is held down
|
||||||
|
|
||||||
|
var event = InputEventMouseMotion.new()
|
||||||
|
event.position = prev_pos[active_side]
|
||||||
|
event.relative = cursor_pos[active_side] - prev_pos[active_side]
|
||||||
|
event.speed = event.relative
|
||||||
|
viewport.input(event)
|
||||||
|
|
||||||
|
|
||||||
|
func _send_click_event(state: bool, controller: String):
|
||||||
|
if click[controller] == state:
|
||||||
|
return # already in that state
|
||||||
|
click[controller] = state
|
||||||
|
_update_active_side()
|
||||||
|
var click_event = InputEventMouseButton.new()
|
||||||
|
click_event.position = cursor_pos[controller]
|
||||||
|
click_event.pressed = state
|
||||||
|
click_event.button_index = 1
|
||||||
|
viewport.input(click_event)
|
||||||
|
# print("SENT EVENT ", click_event.position, " -- ", click_event.pressed)
|
||||||
|
|
||||||
|
|
||||||
|
func _trigger_on(controller):
|
||||||
|
if click.right or click.left:
|
||||||
|
return
|
||||||
|
_send_click_event(true, controller)
|
||||||
|
|
||||||
|
|
||||||
|
func _trigger_off(controller):
|
||||||
|
_send_click_event(false, controller)
|
||||||
|
|
||||||
|
func _update_active_side() -> void:
|
||||||
|
if click.right:
|
||||||
|
active_side = "right"
|
||||||
|
elif click.left:
|
||||||
|
active_side = "left"
|
||||||
|
else:
|
||||||
|
active_side = ""
|
|
@ -22,18 +22,18 @@ func _ready() -> void:
|
||||||
get_parent().connect("trigger_off", self, "_trigger_off")
|
get_parent().connect("trigger_off", self, "_trigger_off")
|
||||||
|
|
||||||
|
|
||||||
func _trigger_on():
|
func _trigger_on(controller):
|
||||||
if Settings.s.grab_mode or _interaction.grab_mode:
|
if Settings.s.grab_mode or _interaction.grab_mode:
|
||||||
begin_move()
|
begin_move(controller)
|
||||||
|
|
||||||
|
|
||||||
func _trigger_off():
|
func _trigger_off(_controller):
|
||||||
finish_move()
|
finish_move()
|
||||||
|
|
||||||
|
|
||||||
func begin_move():
|
func begin_move(controller="right"):
|
||||||
if not _interaction.active_controller:
|
if not _interaction.state[controller].near:
|
||||||
print("Could not begin moving overlay, no controller is touching overlay. <", _overlay.name, ">")
|
print("Could not begin moving overlay, " + controller + " controller is not touching overlay. <", _overlay.name, ">")
|
||||||
return
|
return
|
||||||
if is_moving:
|
if is_moving:
|
||||||
return
|
return
|
||||||
|
@ -41,7 +41,7 @@ func begin_move():
|
||||||
_interaction.pause_triggers = true
|
_interaction.pause_triggers = true
|
||||||
# store current states to revert after move
|
# store current states to revert after move
|
||||||
_pre_move_target = _overlay.current_target
|
_pre_move_target = _overlay.current_target
|
||||||
_mover_hand_name = _interaction.active_controller
|
_mover_hand_name = controller
|
||||||
_mover_hand_offsets = _overlay.get_offset(_mover_hand_name)
|
_mover_hand_offsets = _overlay.get_offset(_mover_hand_name)
|
||||||
|
|
||||||
# calculate offsets from active controller to overlay
|
# calculate offsets from active controller to overlay
|
188
src/addons/openvr_overlay/interaction/overlay_interaction.gd
Normal file
188
src/addons/openvr_overlay/interaction/overlay_interaction.gd
Normal file
|
@ -0,0 +1,188 @@
|
||||||
|
extends Node
|
||||||
|
|
||||||
|
|
||||||
|
signal near_on # a controller entered the near area (enable cursor and/or touch visualiser)
|
||||||
|
signal near_off # a controller exited
|
||||||
|
signal touch_on
|
||||||
|
signal touch_off
|
||||||
|
signal trigger_on # trigger pushed while touching
|
||||||
|
signal trigger_off # trigger released
|
||||||
|
|
||||||
|
var grab_mode := false setget set_grab_mode
|
||||||
|
|
||||||
|
# reference to the area node thats used for touch
|
||||||
|
var _overlay_area: Spatial# = preload("res://addons/openvr_overlay/interaction/OverlayArea.tscn").instance()
|
||||||
|
var _right_is_activator := false # this hand has a collider on it to trigger things on the overlay
|
||||||
|
var _left_is_activator := false
|
||||||
|
|
||||||
|
var pause_triggers := false # disable triggers updating (used by grab module)
|
||||||
|
|
||||||
|
var state := {
|
||||||
|
"right": {
|
||||||
|
"active": false,
|
||||||
|
"near": false,
|
||||||
|
"touch": false,
|
||||||
|
"trigger": false,
|
||||||
|
},
|
||||||
|
"left": {
|
||||||
|
"active": false,
|
||||||
|
"near": false,
|
||||||
|
"touch": false,
|
||||||
|
"trigger": false,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
onready var tracker_nodes = {
|
||||||
|
"head": $VR/head,
|
||||||
|
"left": $VR/left,
|
||||||
|
"right": $VR/right,
|
||||||
|
"world": $VR
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func _ready() -> void:
|
||||||
|
_overlay_area = $OverlayArea
|
||||||
|
_overlay_area.get_node("AreaNear"). connect("area_entered", self, "_on_Near_entered")
|
||||||
|
_overlay_area.get_node("AreaNear"). connect("area_exited", self, "_on_Near_exited")
|
||||||
|
_overlay_area.get_node("AreaTouch").connect("area_entered", self, "_on_Touch_entered")
|
||||||
|
_overlay_area.get_node("AreaTouch").connect("area_exited", self, "_on_Touch_exited")
|
||||||
|
|
||||||
|
get_parent().connect("width_changed", self, "_update_width")
|
||||||
|
get_parent().connect("offset_changed", self, "_update_offset")
|
||||||
|
get_parent().connect("target_changed", self, "_update_target")
|
||||||
|
|
||||||
|
OverlayManager.connect("grab_mode_changed", self, "update_selection")
|
||||||
|
|
||||||
|
call_deferred("_update_width")
|
||||||
|
call_deferred("_update_offset")
|
||||||
|
call_deferred("_update_target")
|
||||||
|
|
||||||
|
|
||||||
|
func _trigger_on(controller):
|
||||||
|
if state[controller].near:
|
||||||
|
state[controller].trigger = true
|
||||||
|
# print("TRIGGER ON ", controller)
|
||||||
|
emit_signal("trigger_on", controller)
|
||||||
|
|
||||||
|
|
||||||
|
func _trigger_off(controller):
|
||||||
|
state[controller].trigger = false
|
||||||
|
# print("TRIGGER OFF ", controller)
|
||||||
|
emit_signal("trigger_off", controller)
|
||||||
|
|
||||||
|
|
||||||
|
func _on_Near_entered(body: Node) -> void:
|
||||||
|
if pause_triggers or !get_parent().overlay_visible:
|
||||||
|
return
|
||||||
|
var hand = body.get_groups()[0]
|
||||||
|
state[hand].near = true
|
||||||
|
update_selection()
|
||||||
|
# print("NEAR ON ", hand)
|
||||||
|
emit_signal("near_on")
|
||||||
|
|
||||||
|
|
||||||
|
func _on_Near_exited(body: Node) -> void:
|
||||||
|
if pause_triggers or !get_parent().overlay_visible:
|
||||||
|
return
|
||||||
|
var hand = body.get_groups()[0]
|
||||||
|
state[hand].near = false
|
||||||
|
|
||||||
|
# print("NEAR OFF ", hand)
|
||||||
|
update_selection()
|
||||||
|
emit_signal("near_off")
|
||||||
|
|
||||||
|
|
||||||
|
func _on_Touch_entered(body: Node) -> void:
|
||||||
|
if pause_triggers or !get_parent().overlay_visible:
|
||||||
|
return
|
||||||
|
var hand = body.get_groups()[0]
|
||||||
|
state[hand].touch = true
|
||||||
|
update_selection()
|
||||||
|
# print("TOUCH ON ", hand)
|
||||||
|
emit_signal("touch_on", hand)
|
||||||
|
|
||||||
|
|
||||||
|
func _on_Touch_exited(body: Node) -> void:
|
||||||
|
if pause_triggers or !get_parent().overlay_visible:
|
||||||
|
return
|
||||||
|
var hand = body.get_groups()[0]
|
||||||
|
state[hand].touch = false
|
||||||
|
update_selection()
|
||||||
|
# print("TOUCH OFF ", hand)
|
||||||
|
emit_signal("touch_off", hand)
|
||||||
|
|
||||||
|
|
||||||
|
func update_selection():
|
||||||
|
var sel = (Settings.s.grab_mode or grab_mode)
|
||||||
|
sel = sel and (state.right.near or state.left.near)
|
||||||
|
get_parent().get_node("OverlayViewport/Selected").visible = sel
|
||||||
|
|
||||||
|
|
||||||
|
func set_grab_mode(state: bool) -> void:
|
||||||
|
grab_mode = state
|
||||||
|
update_selection()
|
||||||
|
|
||||||
|
|
||||||
|
func _update_width():
|
||||||
|
var ratio = OverlayInit.ovr_interface.get_render_targetsize()
|
||||||
|
var extents = get_parent().width_meters * 0.5
|
||||||
|
_overlay_area.get_node("AreaNear/CollisionShape").shape.set_extents(
|
||||||
|
Vector3(extents, extents * ratio.y/ratio.x, 0.1))
|
||||||
|
_overlay_area.get_node("AreaTouch/CollisionShape").shape.set_extents(
|
||||||
|
Vector3(extents, extents * ratio.y/ratio.x, 0.01))
|
||||||
|
|
||||||
|
|
||||||
|
func _update_offset():
|
||||||
|
_overlay_area.translation = get_parent().translation
|
||||||
|
_overlay_area.rotation = get_parent().rotation
|
||||||
|
|
||||||
|
|
||||||
|
func _update_target():
|
||||||
|
var t = get_parent().current_target
|
||||||
|
# reparent _overlay_area
|
||||||
|
_overlay_area.get_parent().remove_child(_overlay_area)
|
||||||
|
tracker_nodes[t].add_child(_overlay_area)
|
||||||
|
|
||||||
|
state.right.active = t != "right"
|
||||||
|
state.left.active = t != "left"
|
||||||
|
# make area only detect colliders of a different hand
|
||||||
|
_overlay_area.get_node("AreaNear").collision_mask = int(t!="right")*2 # detect right hand
|
||||||
|
_overlay_area.get_node("AreaNear").collision_mask += int(t!="left")*4 # detect left hand
|
||||||
|
_overlay_area.get_node("AreaNear").collision_mask = int(t!="right")*8 # detect right hand
|
||||||
|
_overlay_area.get_node("AreaNear").collision_mask += int(t!="left")*16 # detect left hand
|
||||||
|
|
||||||
|
|
||||||
|
# called by overlay_instance after properties are loaded and before overlay scene enters the tree
|
||||||
|
func spawn_modules():
|
||||||
|
if get_parent().get_property("grabbable"):
|
||||||
|
var module = preload("res://addons/openvr_overlay/interaction/mod/Grabbable.tscn")
|
||||||
|
add_child(module.instance())
|
||||||
|
|
||||||
|
if get_parent().get_property("clickable"):
|
||||||
|
var module = preload("res://addons/openvr_overlay/interaction/mod/Clickable.tscn")
|
||||||
|
add_child(module.instance())
|
||||||
|
|
||||||
|
if get_parent().get_property("touchable"):
|
||||||
|
var module = preload("res://addons/openvr_overlay/interaction/mod/Touchable.tscn")
|
||||||
|
add_child(module.instance())
|
||||||
|
|
||||||
|
|
||||||
|
func _on_RightHand_button_pressed(button: int) -> void:
|
||||||
|
if button == JOY_VR_TRIGGER and state.right.active:
|
||||||
|
_trigger_on("right")
|
||||||
|
|
||||||
|
|
||||||
|
func _on_RightHand_button_release(button: int) -> void:
|
||||||
|
if button == JOY_VR_TRIGGER and state.right.trigger:
|
||||||
|
_trigger_off("right")
|
||||||
|
|
||||||
|
|
||||||
|
func _on_LeftHand_button_pressed(button: int) -> void:
|
||||||
|
if button == JOY_VR_TRIGGER and state.left.active:
|
||||||
|
_trigger_on("left")
|
||||||
|
|
||||||
|
|
||||||
|
func _on_LeftHand_button_release(button: int) -> void:
|
||||||
|
if button == JOY_VR_TRIGGER and state.left.trigger:
|
||||||
|
_trigger_off("left")
|
|
@ -4,7 +4,9 @@ extends EditorPlugin
|
||||||
|
|
||||||
func _enter_tree() -> void:
|
func _enter_tree() -> void:
|
||||||
add_autoload_singleton("OverlayInit", "res://addons/openvr_overlay/overlay_init.gd")
|
add_autoload_singleton("OverlayInit", "res://addons/openvr_overlay/overlay_init.gd")
|
||||||
|
add_autoload_singleton("OverlayInteractionRoot", "res://addons/openvr_overlay/OverlayInteractionRoot.tscn")
|
||||||
|
|
||||||
|
|
||||||
func _exit_tree() -> void:
|
func _exit_tree() -> void:
|
||||||
remove_autoload_singleton("OverlayInit")
|
remove_autoload_singleton("OverlayInit")
|
||||||
|
remove_autoload_singleton("OverlayInteractionRoot")
|
|
@ -1,5 +1,14 @@
|
||||||
extends Node
|
extends Node
|
||||||
|
|
||||||
|
|
||||||
|
const OVERLAY_PROPERTIES_DEFAULT = {
|
||||||
|
"allow_delete": true,
|
||||||
|
"allow_hide": true,
|
||||||
|
"clickable": false,
|
||||||
|
"touchable": false,
|
||||||
|
"grabbable": true,
|
||||||
|
}
|
||||||
|
|
||||||
var ovr_interface: ARVRInterface
|
var ovr_interface: ARVRInterface
|
||||||
var ovr_config := preload("res://addons/godot-openvr/OpenVRConfig.gdns").new()
|
var ovr_config := preload("res://addons/godot-openvr/OpenVRConfig.gdns").new()
|
||||||
|
|
||||||
|
@ -11,9 +20,7 @@ var trackers = {
|
||||||
}
|
}
|
||||||
|
|
||||||
func _init() -> void:
|
func _init() -> void:
|
||||||
# OS.window_minimized = true
|
ovr_config.set_application_type(2) # Set to OVERLAY MODE
|
||||||
ovr_config = preload("res://addons/godot-openvr/OpenVRConfig.gdns").new()
|
|
||||||
ovr_config.set_application_type(2) # Set to OVERLAY MODE = 2, NORMAL MODE = 1
|
|
||||||
ovr_config.set_tracking_universe(1) # Set to SEATED MODE = 0, STANDING MODE = 1, RAW MODE = 2
|
ovr_config.set_tracking_universe(1) # Set to SEATED MODE = 0, STANDING MODE = 1, RAW MODE = 2
|
||||||
|
|
||||||
# Find the OpenVR interface and initialise it
|
# Find the OpenVR interface and initialise it
|
||||||
|
@ -23,9 +30,14 @@ func _init() -> void:
|
||||||
|
|
||||||
|
|
||||||
func _ready() -> void:
|
func _ready() -> void:
|
||||||
|
OS.window_size = Vector2(16, 16)
|
||||||
|
OS.window_position = Vector2(32, 32)
|
||||||
|
OS.window_minimized = true
|
||||||
|
|
||||||
ARVRServer.connect("tracker_added", self, "_tracker_added")
|
ARVRServer.connect("tracker_added", self, "_tracker_added")
|
||||||
ARVRServer.connect("tracker_removed", self, "_tracker_removed")
|
ARVRServer.connect("tracker_removed", self, "_tracker_removed")
|
||||||
update_hand_ids()
|
update_hand_ids()
|
||||||
|
#Input.set_use_accumulated_input(true)
|
||||||
|
|
||||||
|
|
||||||
func _tracker_added(tracker_name: String, type: int, id: int):
|
func _tracker_added(tracker_name: String, type: int, id: int):
|
|
@ -1,6 +1,6 @@
|
||||||
extends Spatial
|
extends Spatial
|
||||||
|
|
||||||
signal path_changed
|
#signal path_changed
|
||||||
signal overlay_visible_changed
|
signal overlay_visible_changed
|
||||||
signal width_changed
|
signal width_changed
|
||||||
signal alpha_changed
|
signal alpha_changed
|
||||||
|
@ -13,8 +13,7 @@ export (String, "head", "left", "right", "world") var target = "left" setget se
|
||||||
|
|
||||||
export var width_meters := 0.4 setget set_width_in_meters
|
export var width_meters := 0.4 setget set_width_in_meters
|
||||||
export var alpha := 1.0 setget set_alpha
|
export var alpha := 1.0 setget set_alpha
|
||||||
export var add_grabbing := true # add grabbing module
|
|
||||||
export var add_cursor := false # add cursor module
|
|
||||||
|
|
||||||
var _tracker_id := 0
|
var _tracker_id := 0
|
||||||
var _offsets:Dictionary = {
|
var _offsets:Dictionary = {
|
||||||
|
@ -29,15 +28,17 @@ var current_target: String = "world" setget _set_current_target
|
||||||
var fallback = ["left", "right", "head"] # TODO setget that updates tracking (not important)
|
var fallback = ["left", "right", "head"] # TODO setget that updates tracking (not important)
|
||||||
var interaction_handler: Node
|
var interaction_handler: Node
|
||||||
var overlay_visible := true setget set_overlay_visible
|
var overlay_visible := true setget set_overlay_visible
|
||||||
var path := "res://special_overlays/MainOverlay.tscn" setget set_path
|
var path : String = "res://special_overlays/MainOverlay.tscn"# setget set_path
|
||||||
var path_invalid := false
|
var path_invalid := false
|
||||||
var OVERLAY_PROPERTIES: Dictionary
|
var OVERLAY_PROPERTIES: Dictionary # defined in overlay root script (optional)
|
||||||
|
|
||||||
onready var container = $OverlayViewport/Container
|
onready var container = $OverlayViewport/Container
|
||||||
var overlay_scene: Node
|
var overlay_scene: Node
|
||||||
|
|
||||||
|
|
||||||
func _ready() -> void:
|
func _ready() -> void:
|
||||||
|
container = $OverlayViewport/Container
|
||||||
|
load_overlay()
|
||||||
current_target = target
|
current_target = target
|
||||||
|
|
||||||
ARVRServer.connect("tracker_added", self, "_tracker_changed")
|
ARVRServer.connect("tracker_added", self, "_tracker_changed")
|
||||||
|
@ -46,25 +47,27 @@ func _ready() -> void:
|
||||||
$VROverlayViewport.size = OverlayInit.ovr_interface.get_render_targetsize()
|
$VROverlayViewport.size = OverlayInit.ovr_interface.get_render_targetsize()
|
||||||
set_notify_transform(true)
|
set_notify_transform(true)
|
||||||
|
|
||||||
if add_cursor or add_grabbing:
|
|
||||||
interaction_handler = load("res://addons/openvr_overlay/OverlayInteraction.tscn").instance()
|
|
||||||
add_child(interaction_handler)
|
|
||||||
if add_cursor:
|
|
||||||
add_cursor()
|
|
||||||
if add_grabbing:
|
|
||||||
add_grab()
|
|
||||||
|
|
||||||
update_tracker_id()
|
update_tracker_id()
|
||||||
call_deferred("update_offset")
|
call_deferred("update_offset")
|
||||||
|
|
||||||
|
func load_overlay() -> void:
|
||||||
|
path_invalid = false
|
||||||
|
|
||||||
func add_cursor():
|
var packed_overlay = load(path)
|
||||||
interaction_handler.add_child(load("res://addons/openvr_overlay/OverlayCursor.tscn").instance())
|
if not packed_overlay:
|
||||||
|
path_invalid = true
|
||||||
|
overlay_scene = load("res://special_overlays/UnknownType.tscn").instance()
|
||||||
|
else:
|
||||||
|
overlay_scene = packed_overlay.instance()
|
||||||
|
|
||||||
|
if overlay_scene.get("OVERLAY_PROPERTIES") != null:
|
||||||
|
OVERLAY_PROPERTIES = overlay_scene.OVERLAY_PROPERTIES
|
||||||
|
|
||||||
func add_grab():
|
$OverlayInteraction.spawn_modules()
|
||||||
interaction_handler.add_child(load("res://addons/openvr_overlay/OverlayGrab.tscn").instance())
|
|
||||||
|
|
||||||
|
if container.get_child_count() > 0:
|
||||||
|
container.get_child(0).queue_free()
|
||||||
|
container.add_child(overlay_scene)
|
||||||
|
|
||||||
func update_tracker_id():
|
func update_tracker_id():
|
||||||
_tracker_id = -1
|
_tracker_id = -1
|
||||||
|
@ -78,7 +81,7 @@ func update_tracker_id():
|
||||||
|
|
||||||
if _tracker_id == -1:
|
if _tracker_id == -1:
|
||||||
# could not find controller, fallback
|
# could not find controller, fallback
|
||||||
print("Missing controller ", current_target, " ", target, " ", fallback, " - ", name)
|
# print("Missing controller ", current_target, " ", target, " ", fallback, " - ", name)
|
||||||
_tracker_id = 63 # highest tracker id (unused, at origin)
|
_tracker_id = 63 # highest tracker id (unused, at origin)
|
||||||
|
|
||||||
|
|
||||||
|
@ -146,27 +149,6 @@ func set_width_in_meters(width: float) -> void:
|
||||||
emit_signal("width_changed")
|
emit_signal("width_changed")
|
||||||
|
|
||||||
|
|
||||||
func set_path(new: String) -> void:
|
|
||||||
path = new
|
|
||||||
path_invalid = false
|
|
||||||
|
|
||||||
var packed_overlay = load(path)
|
|
||||||
if not packed_overlay:
|
|
||||||
path_invalid = true
|
|
||||||
overlay_scene = load("res://special_overlays/UnknownType.tscn").instance()
|
|
||||||
else:
|
|
||||||
overlay_scene = packed_overlay.instance()
|
|
||||||
|
|
||||||
if container.get_child_count() > 0:
|
|
||||||
container.get_child(0).queue_free()
|
|
||||||
container.add_child(overlay_scene)
|
|
||||||
|
|
||||||
if overlay_scene.get("OVERLAY_PROPERTIES") != null:
|
|
||||||
OVERLAY_PROPERTIES = overlay_scene.OVERLAY_PROPERTIES
|
|
||||||
|
|
||||||
emit_signal("path_changed")
|
|
||||||
|
|
||||||
|
|
||||||
func set_alpha(val: float):
|
func set_alpha(val: float):
|
||||||
alpha = val
|
alpha = val
|
||||||
$VROverlayViewport/TextureRect.modulate.a = val
|
$VROverlayViewport/TextureRect.modulate.a = val
|
||||||
|
@ -184,3 +166,10 @@ func reset_offset() -> void:
|
||||||
func _notification(what: int) -> void:
|
func _notification(what: int) -> void:
|
||||||
if what == NOTIFICATION_TRANSFORM_CHANGED:
|
if what == NOTIFICATION_TRANSFORM_CHANGED:
|
||||||
emit_signal("offset_changed")
|
emit_signal("offset_changed")
|
||||||
|
|
||||||
|
|
||||||
|
func get_property(p_name: String):
|
||||||
|
if OVERLAY_PROPERTIES.has(p_name):
|
||||||
|
return OVERLAY_PROPERTIES[p_name]
|
||||||
|
|
||||||
|
return OverlayInit.OVERLAY_PROPERTIES_DEFAULT[p_name]
|
|
@ -5,7 +5,7 @@ platform="Linux/X11"
|
||||||
runnable=true
|
runnable=true
|
||||||
custom_features=""
|
custom_features=""
|
||||||
export_filter="all_resources"
|
export_filter="all_resources"
|
||||||
include_filter=""
|
include_filter="*.json"
|
||||||
exclude_filter=""
|
exclude_filter=""
|
||||||
export_path="../builds/linux/ovr-utils.x86_64"
|
export_path="../builds/linux/ovr-utils.x86_64"
|
||||||
script_export_mode=1
|
script_export_mode=1
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Reference in a new issue