├── .gitignore ├── Assets ├── DemoScene.meta ├── DemoScene │ ├── HandScene.unity │ ├── HandScene.unity.meta │ ├── TransformReset.cs │ └── TransformReset.cs.meta ├── ViveSRWorksHand.meta └── ViveSRWorksHand │ ├── Materials.meta │ ├── Materials │ ├── handmat.mat │ └── handmat.mat.meta │ ├── Prefabs.meta │ ├── Prefabs │ ├── DepthMask.prefab │ ├── DepthMask.prefab.meta │ ├── HandRacketCollisionObj.prefab │ ├── HandRacketCollisionObj.prefab.meta │ ├── SRWorksHand.prefab │ └── SRWorksHand.prefab.meta │ ├── README.md │ ├── README.md.meta │ ├── Scripts.meta │ ├── Scripts │ ├── HandTouch.cs │ ├── HandTouch.cs.meta │ ├── MyPhysics.cs │ ├── MyPhysics.cs.meta │ ├── MySingleton.cs │ ├── MySingleton.cs.meta │ ├── SRHandManager.cs │ ├── SRHandManager.cs.meta │ ├── SRWorksHand.cs │ └── SRWorksHand.cs.meta │ ├── Shaders.meta │ └── Shaders │ ├── ViveSRCG.cginc │ ├── ViveSRCG.cginc.meta │ ├── WireframeGeoShader.shader │ └── WireframeGeoShader.shader.meta ├── COTRIBUTING..md ├── ProjectSettings └── EditorSettings.asset ├── README.md └── readme_images ├── CollisionObj.png ├── HandScene.png ├── ViveSR.png ├── manager.png └── screenshot.png /.gitignore: -------------------------------------------------------------------------------- 1 | /[Ll]ibrary/ 2 | /[Tt]emp/ 3 | /[Oo]bj/ 4 | /[Bb]uild/ 5 | /[Bb]uilds/ 6 | /[Pp111]ackages/ 7 | /.vs/ 8 | /.vscode/ 9 | /UnityPackageManager/ 10 | Assets/AssetStoreTools* 11 | 12 | ProjectSettings/* 13 | !ProjectSettings/EditorSettings.asset 14 | 15 | Assets/* 16 | !Assets/ViveSRWorksHand/ 17 | !Assets/ViveSRWorksHand.meta 18 | !Assets/DemoScene/ 19 | !Assets/DemoScene.meta 20 | 21 | *.cfg 22 | *.log 23 | 24 | # Autogenerated VS/MD/Consulo solution and project files 25 | ExportedObj/ 26 | .consulo/ 27 | *.csproj 28 | *.unityproj 29 | *.sln 30 | *.suo 31 | *.tmp 32 | *.user 33 | *.userprefs 34 | *.pidb 35 | *.booproj 36 | *.svd 37 | *.pdb 38 | *.opendb 39 | 40 | # Unity3D generated meta files 41 | *.pidb.meta 42 | *.pdb.meta 43 | 44 | # Unity3D Generated File On Crash Reports 45 | sysinfo.txt 46 | 47 | # Builds 48 | *.apk 49 | *.unitypackage 50 | -------------------------------------------------------------------------------- /Assets/DemoScene.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 4f704ae4b4f98ae41a0bce26658850c1 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/DemoScene/HandScene.unity: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!29 &1 4 | OcclusionCullingSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 2 7 | m_OcclusionBakeSettings: 8 | smallestOccluder: 5 9 | smallestHole: 0.25 10 | backfaceThreshold: 100 11 | m_SceneGUID: 00000000000000000000000000000000 12 | m_OcclusionCullingData: {fileID: 0} 13 | --- !u!104 &2 14 | RenderSettings: 15 | m_ObjectHideFlags: 0 16 | serializedVersion: 8 17 | m_Fog: 0 18 | m_FogColor: {r: 0.5, g: 0.5, b: 0.5, a: 1} 19 | m_FogMode: 3 20 | m_FogDensity: 0.01 21 | m_LinearFogStart: 0 22 | m_LinearFogEnd: 300 23 | m_AmbientSkyColor: {r: 0.212, g: 0.227, b: 0.259, a: 1} 24 | m_AmbientEquatorColor: {r: 0.114, g: 0.125, b: 0.133, a: 1} 25 | m_AmbientGroundColor: {r: 0.047, g: 0.043, b: 0.035, a: 1} 26 | m_AmbientIntensity: 1 27 | m_AmbientMode: 0 28 | m_SubtractiveShadowColor: {r: 0.42, g: 0.478, b: 0.627, a: 1} 29 | m_SkyboxMaterial: {fileID: 10304, guid: 0000000000000000f000000000000000, type: 0} 30 | m_HaloStrength: 0.5 31 | m_FlareStrength: 1 32 | m_FlareFadeSpeed: 3 33 | m_HaloTexture: {fileID: 0} 34 | m_SpotCookie: {fileID: 10001, guid: 0000000000000000e000000000000000, type: 0} 35 | m_DefaultReflectionMode: 0 36 | m_DefaultReflectionResolution: 128 37 | m_ReflectionBounces: 1 38 | m_ReflectionIntensity: 1 39 | m_CustomReflection: {fileID: 0} 40 | m_Sun: {fileID: 0} 41 | m_IndirectSpecularColor: {r: 0.44657898, g: 0.4964133, b: 0.5748178, a: 1} 42 | --- !u!157 &3 43 | LightmapSettings: 44 | m_ObjectHideFlags: 0 45 | serializedVersion: 11 46 | m_GIWorkflowMode: 0 47 | m_GISettings: 48 | serializedVersion: 2 49 | m_BounceScale: 1 50 | m_IndirectOutputScale: 1 51 | m_AlbedoBoost: 1 52 | m_TemporalCoherenceThreshold: 1 53 | m_EnvironmentLightingMode: 0 54 | m_EnableBakedLightmaps: 1 55 | m_EnableRealtimeLightmaps: 1 56 | m_LightmapEditorSettings: 57 | serializedVersion: 9 58 | m_Resolution: 2 59 | m_BakeResolution: 40 60 | m_TextureWidth: 1024 61 | m_TextureHeight: 1024 62 | m_AO: 0 63 | m_AOMaxDistance: 1 64 | m_CompAOExponent: 1 65 | m_CompAOExponentDirect: 0 66 | m_Padding: 2 67 | m_LightmapParameters: {fileID: 0} 68 | m_LightmapsBakeMode: 1 69 | m_TextureCompression: 1 70 | m_FinalGather: 0 71 | m_FinalGatherFiltering: 1 72 | m_FinalGatherRayCount: 256 73 | m_ReflectionCompression: 2 74 | m_MixedBakeMode: 2 75 | m_BakeBackend: 0 76 | m_PVRSampling: 1 77 | m_PVRDirectSampleCount: 32 78 | m_PVRSampleCount: 500 79 | m_PVRBounces: 2 80 | m_PVRFilterTypeDirect: 0 81 | m_PVRFilterTypeIndirect: 0 82 | m_PVRFilterTypeAO: 0 83 | m_PVRFilteringMode: 1 84 | m_PVRCulling: 1 85 | m_PVRFilteringGaussRadiusDirect: 1 86 | m_PVRFilteringGaussRadiusIndirect: 5 87 | m_PVRFilteringGaussRadiusAO: 2 88 | m_PVRFilteringAtrousPositionSigmaDirect: 0.5 89 | m_PVRFilteringAtrousPositionSigmaIndirect: 2 90 | m_PVRFilteringAtrousPositionSigmaAO: 1 91 | m_ShowResolutionOverlay: 1 92 | m_LightingDataAsset: {fileID: 0} 93 | m_UseShadowmask: 1 94 | --- !u!196 &4 95 | NavMeshSettings: 96 | serializedVersion: 2 97 | m_ObjectHideFlags: 0 98 | m_BuildSettings: 99 | serializedVersion: 2 100 | agentTypeID: 0 101 | agentRadius: 0.5 102 | agentHeight: 2 103 | agentSlope: 45 104 | agentClimb: 0.4 105 | ledgeDropHeight: 0 106 | maxJumpAcrossDistance: 0 107 | minRegionArea: 2 108 | manualCellSize: 0 109 | cellSize: 0.16666667 110 | manualTileSize: 0 111 | tileSize: 256 112 | accuratePlacement: 0 113 | debug: 114 | m_Flags: 0 115 | m_NavMeshData: {fileID: 0} 116 | --- !u!1001 &216487684 117 | Prefab: 118 | m_ObjectHideFlags: 0 119 | serializedVersion: 2 120 | m_Modification: 121 | m_TransformParent: {fileID: 0} 122 | m_Modifications: 123 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 124 | propertyPath: m_LocalPosition.x 125 | value: 0 126 | objectReference: {fileID: 0} 127 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 128 | propertyPath: m_LocalPosition.y 129 | value: 0 130 | objectReference: {fileID: 0} 131 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 132 | propertyPath: m_LocalPosition.z 133 | value: 0 134 | objectReference: {fileID: 0} 135 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 136 | propertyPath: m_LocalRotation.x 137 | value: 0 138 | objectReference: {fileID: 0} 139 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 140 | propertyPath: m_LocalRotation.y 141 | value: 0 142 | objectReference: {fileID: 0} 143 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 144 | propertyPath: m_LocalRotation.z 145 | value: 0 146 | objectReference: {fileID: 0} 147 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 148 | propertyPath: m_LocalRotation.w 149 | value: 1 150 | objectReference: {fileID: 0} 151 | - target: {fileID: 4133659887173690, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 152 | propertyPath: m_RootOrder 153 | value: 3 154 | objectReference: {fileID: 0} 155 | - target: {fileID: 1069074635598660, guid: 32116cf82e231a74c9167acf46fcbdd4, type: 2} 156 | propertyPath: m_IsActive 157 | value: 1 158 | objectReference: {fileID: 0} 159 | m_RemovedComponents: [] 160 | m_ParentPrefab: {fileID: 0} 161 | m_IsPrefabParent: 0 162 | --- !u!1001 &360538022 163 | Prefab: 164 | m_ObjectHideFlags: 0 165 | serializedVersion: 2 166 | m_Modification: 167 | m_TransformParent: {fileID: 0} 168 | m_Modifications: 169 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 170 | propertyPath: m_LocalPosition.x 171 | value: 0 172 | objectReference: {fileID: 0} 173 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 174 | propertyPath: m_LocalPosition.y 175 | value: 0 176 | objectReference: {fileID: 0} 177 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 178 | propertyPath: m_LocalPosition.z 179 | value: 0 180 | objectReference: {fileID: 0} 181 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 182 | propertyPath: m_LocalRotation.x 183 | value: 0 184 | objectReference: {fileID: 0} 185 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 186 | propertyPath: m_LocalRotation.y 187 | value: 0 188 | objectReference: {fileID: 0} 189 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 190 | propertyPath: m_LocalRotation.z 191 | value: 0 192 | objectReference: {fileID: 0} 193 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 194 | propertyPath: m_LocalRotation.w 195 | value: 1 196 | objectReference: {fileID: 0} 197 | - target: {fileID: 4216087492277088, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 198 | propertyPath: m_RootOrder 199 | value: 4 200 | objectReference: {fileID: 0} 201 | m_RemovedComponents: [] 202 | m_ParentPrefab: {fileID: 100100000, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 203 | m_IsPrefabParent: 0 204 | --- !u!4 &360538023 stripped 205 | Transform: 206 | m_PrefabParentObject: {fileID: 4353928477221820, guid: 043c7faf0fdcecd499d4424a614b2482, 207 | type: 2} 208 | m_PrefabInternal: {fileID: 360538022} 209 | --- !u!4 &360538024 stripped 210 | Transform: 211 | m_PrefabParentObject: {fileID: 4611580045034616, guid: 043c7faf0fdcecd499d4424a614b2482, 212 | type: 2} 213 | m_PrefabInternal: {fileID: 360538022} 214 | --- !u!1 &811093233 215 | GameObject: 216 | m_ObjectHideFlags: 0 217 | m_PrefabParentObject: {fileID: 0} 218 | m_PrefabInternal: {fileID: 0} 219 | serializedVersion: 5 220 | m_Component: 221 | - component: {fileID: 811093238} 222 | - component: {fileID: 811093237} 223 | - component: {fileID: 811093236} 224 | - component: {fileID: 811093235} 225 | - component: {fileID: 811093234} 226 | - component: {fileID: 811093239} 227 | m_Layer: 0 228 | m_Name: Sphere 229 | m_TagString: Untagged 230 | m_Icon: {fileID: 0} 231 | m_NavMeshLayer: 0 232 | m_StaticEditorFlags: 0 233 | m_IsActive: 1 234 | --- !u!54 &811093234 235 | Rigidbody: 236 | m_ObjectHideFlags: 0 237 | m_PrefabParentObject: {fileID: 0} 238 | m_PrefabInternal: {fileID: 0} 239 | m_GameObject: {fileID: 811093233} 240 | serializedVersion: 2 241 | m_Mass: 1 242 | m_Drag: 0 243 | m_AngularDrag: 0.05 244 | m_UseGravity: 0 245 | m_IsKinematic: 0 246 | m_Interpolate: 0 247 | m_Constraints: 0 248 | m_CollisionDetection: 2 249 | --- !u!135 &811093235 250 | SphereCollider: 251 | m_ObjectHideFlags: 0 252 | m_PrefabParentObject: {fileID: 0} 253 | m_PrefabInternal: {fileID: 0} 254 | m_GameObject: {fileID: 811093233} 255 | m_Material: {fileID: 0} 256 | m_IsTrigger: 0 257 | m_Enabled: 1 258 | serializedVersion: 2 259 | m_Radius: 0.5 260 | m_Center: {x: 0, y: 0, z: 0} 261 | --- !u!23 &811093236 262 | MeshRenderer: 263 | m_ObjectHideFlags: 0 264 | m_PrefabParentObject: {fileID: 0} 265 | m_PrefabInternal: {fileID: 0} 266 | m_GameObject: {fileID: 811093233} 267 | m_Enabled: 1 268 | m_CastShadows: 1 269 | m_ReceiveShadows: 1 270 | m_DynamicOccludee: 1 271 | m_MotionVectors: 1 272 | m_LightProbeUsage: 1 273 | m_ReflectionProbeUsage: 1 274 | m_Materials: 275 | - {fileID: 10303, guid: 0000000000000000f000000000000000, type: 0} 276 | m_StaticBatchInfo: 277 | firstSubMesh: 0 278 | subMeshCount: 0 279 | m_StaticBatchRoot: {fileID: 0} 280 | m_ProbeAnchor: {fileID: 0} 281 | m_LightProbeVolumeOverride: {fileID: 0} 282 | m_ScaleInLightmap: 1 283 | m_PreserveUVs: 0 284 | m_IgnoreNormalsForChartDetection: 0 285 | m_ImportantGI: 0 286 | m_StitchLightmapSeams: 0 287 | m_SelectedEditorRenderState: 3 288 | m_MinimumChartSize: 4 289 | m_AutoUVMaxDistance: 0.5 290 | m_AutoUVMaxAngle: 89 291 | m_LightmapParameters: {fileID: 0} 292 | m_SortingLayerID: 0 293 | m_SortingLayer: 0 294 | m_SortingOrder: 0 295 | --- !u!33 &811093237 296 | MeshFilter: 297 | m_ObjectHideFlags: 0 298 | m_PrefabParentObject: {fileID: 0} 299 | m_PrefabInternal: {fileID: 0} 300 | m_GameObject: {fileID: 811093233} 301 | m_Mesh: {fileID: 10207, guid: 0000000000000000e000000000000000, type: 0} 302 | --- !u!4 &811093238 303 | Transform: 304 | m_ObjectHideFlags: 0 305 | m_PrefabParentObject: {fileID: 0} 306 | m_PrefabInternal: {fileID: 0} 307 | m_GameObject: {fileID: 811093233} 308 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 309 | m_LocalPosition: {x: 0, y: 1.3, z: 0.6} 310 | m_LocalScale: {x: 0.5, y: 0.5, z: 0.5} 311 | m_Children: [] 312 | m_Father: {fileID: 0} 313 | m_RootOrder: 2 314 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 315 | --- !u!114 &811093239 316 | MonoBehaviour: 317 | m_ObjectHideFlags: 0 318 | m_PrefabParentObject: {fileID: 0} 319 | m_PrefabInternal: {fileID: 0} 320 | m_GameObject: {fileID: 811093233} 321 | m_Enabled: 1 322 | m_EditorHideFlags: 0 323 | m_Script: {fileID: 11500000, guid: 80d5d3d4bbecc8c42878475f97577b86, type: 3} 324 | m_Name: 325 | m_EditorClassIdentifier: 326 | --- !u!1 &845894752 327 | GameObject: 328 | m_ObjectHideFlags: 0 329 | m_PrefabParentObject: {fileID: 0} 330 | m_PrefabInternal: {fileID: 0} 331 | serializedVersion: 5 332 | m_Component: 333 | - component: {fileID: 845894754} 334 | - component: {fileID: 845894753} 335 | m_Layer: 0 336 | m_Name: Directional Light 337 | m_TagString: Untagged 338 | m_Icon: {fileID: 0} 339 | m_NavMeshLayer: 0 340 | m_StaticEditorFlags: 0 341 | m_IsActive: 1 342 | --- !u!108 &845894753 343 | Light: 344 | m_ObjectHideFlags: 0 345 | m_PrefabParentObject: {fileID: 0} 346 | m_PrefabInternal: {fileID: 0} 347 | m_GameObject: {fileID: 845894752} 348 | m_Enabled: 1 349 | serializedVersion: 8 350 | m_Type: 1 351 | m_Color: {r: 1, g: 0.95686275, b: 0.8392157, a: 1} 352 | m_Intensity: 1 353 | m_Range: 10 354 | m_SpotAngle: 30 355 | m_CookieSize: 10 356 | m_Shadows: 357 | m_Type: 2 358 | m_Resolution: -1 359 | m_CustomResolution: -1 360 | m_Strength: 1 361 | m_Bias: 0.05 362 | m_NormalBias: 0.4 363 | m_NearPlane: 0.2 364 | m_Cookie: {fileID: 0} 365 | m_DrawHalo: 0 366 | m_Flare: {fileID: 0} 367 | m_RenderMode: 0 368 | m_CullingMask: 369 | serializedVersion: 2 370 | m_Bits: 4294967295 371 | m_Lightmapping: 4 372 | m_AreaSize: {x: 1, y: 1} 373 | m_BounceIntensity: 1 374 | m_ColorTemperature: 6570 375 | m_UseColorTemperature: 0 376 | m_ShadowRadius: 0 377 | m_ShadowAngle: 0 378 | --- !u!4 &845894754 379 | Transform: 380 | m_ObjectHideFlags: 0 381 | m_PrefabParentObject: {fileID: 0} 382 | m_PrefabInternal: {fileID: 0} 383 | m_GameObject: {fileID: 845894752} 384 | m_LocalRotation: {x: 0.40821788, y: -0.23456968, z: 0.10938163, w: 0.8754261} 385 | m_LocalPosition: {x: 0, y: 3, z: 0} 386 | m_LocalScale: {x: 1, y: 1, z: 1} 387 | m_Children: [] 388 | m_Father: {fileID: 0} 389 | m_RootOrder: 0 390 | m_LocalEulerAnglesHint: {x: 50, y: -30, z: 0} 391 | --- !u!1 &1497590266 392 | GameObject: 393 | m_ObjectHideFlags: 0 394 | m_PrefabParentObject: {fileID: 0} 395 | m_PrefabInternal: {fileID: 0} 396 | serializedVersion: 5 397 | m_Component: 398 | - component: {fileID: 1497590270} 399 | - component: {fileID: 1497590269} 400 | - component: {fileID: 1497590268} 401 | - component: {fileID: 1497590267} 402 | - component: {fileID: 1497590272} 403 | - component: {fileID: 1497590271} 404 | m_Layer: 0 405 | m_Name: Cube 406 | m_TagString: Untagged 407 | m_Icon: {fileID: 0} 408 | m_NavMeshLayer: 0 409 | m_StaticEditorFlags: 0 410 | m_IsActive: 1 411 | --- !u!65 &1497590267 412 | BoxCollider: 413 | m_ObjectHideFlags: 0 414 | m_PrefabParentObject: {fileID: 0} 415 | m_PrefabInternal: {fileID: 0} 416 | m_GameObject: {fileID: 1497590266} 417 | m_Material: {fileID: 0} 418 | m_IsTrigger: 0 419 | m_Enabled: 1 420 | serializedVersion: 2 421 | m_Size: {x: 1, y: 1, z: 1} 422 | m_Center: {x: 0, y: 0, z: 0} 423 | --- !u!23 &1497590268 424 | MeshRenderer: 425 | m_ObjectHideFlags: 0 426 | m_PrefabParentObject: {fileID: 0} 427 | m_PrefabInternal: {fileID: 0} 428 | m_GameObject: {fileID: 1497590266} 429 | m_Enabled: 1 430 | m_CastShadows: 1 431 | m_ReceiveShadows: 1 432 | m_DynamicOccludee: 1 433 | m_MotionVectors: 1 434 | m_LightProbeUsage: 1 435 | m_ReflectionProbeUsage: 1 436 | m_Materials: 437 | - {fileID: 10303, guid: 0000000000000000f000000000000000, type: 0} 438 | m_StaticBatchInfo: 439 | firstSubMesh: 0 440 | subMeshCount: 0 441 | m_StaticBatchRoot: {fileID: 0} 442 | m_ProbeAnchor: {fileID: 0} 443 | m_LightProbeVolumeOverride: {fileID: 0} 444 | m_ScaleInLightmap: 1 445 | m_PreserveUVs: 0 446 | m_IgnoreNormalsForChartDetection: 0 447 | m_ImportantGI: 0 448 | m_StitchLightmapSeams: 0 449 | m_SelectedEditorRenderState: 3 450 | m_MinimumChartSize: 4 451 | m_AutoUVMaxDistance: 0.5 452 | m_AutoUVMaxAngle: 89 453 | m_LightmapParameters: {fileID: 0} 454 | m_SortingLayerID: 0 455 | m_SortingLayer: 0 456 | m_SortingOrder: 0 457 | --- !u!33 &1497590269 458 | MeshFilter: 459 | m_ObjectHideFlags: 0 460 | m_PrefabParentObject: {fileID: 0} 461 | m_PrefabInternal: {fileID: 0} 462 | m_GameObject: {fileID: 1497590266} 463 | m_Mesh: {fileID: 10202, guid: 0000000000000000e000000000000000, type: 0} 464 | --- !u!4 &1497590270 465 | Transform: 466 | m_ObjectHideFlags: 0 467 | m_PrefabParentObject: {fileID: 0} 468 | m_PrefabInternal: {fileID: 0} 469 | m_GameObject: {fileID: 1497590266} 470 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 471 | m_LocalPosition: {x: 0, y: 1, z: 0.2} 472 | m_LocalScale: {x: 0.04, y: 0.04, z: 0.04} 473 | m_Children: [] 474 | m_Father: {fileID: 0} 475 | m_RootOrder: 1 476 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 477 | --- !u!114 &1497590271 478 | MonoBehaviour: 479 | m_ObjectHideFlags: 0 480 | m_PrefabParentObject: {fileID: 0} 481 | m_PrefabInternal: {fileID: 0} 482 | m_GameObject: {fileID: 1497590266} 483 | m_Enabled: 1 484 | m_EditorHideFlags: 0 485 | m_Script: {fileID: 11500000, guid: 80d5d3d4bbecc8c42878475f97577b86, type: 3} 486 | m_Name: 487 | m_EditorClassIdentifier: 488 | --- !u!54 &1497590272 489 | Rigidbody: 490 | m_ObjectHideFlags: 0 491 | m_PrefabParentObject: {fileID: 0} 492 | m_PrefabInternal: {fileID: 0} 493 | m_GameObject: {fileID: 1497590266} 494 | serializedVersion: 2 495 | m_Mass: 1 496 | m_Drag: 0 497 | m_AngularDrag: 0.05 498 | m_UseGravity: 0 499 | m_IsKinematic: 0 500 | m_Interpolate: 0 501 | m_Constraints: 0 502 | m_CollisionDetection: 0 503 | --- !u!1 &1834704843 504 | GameObject: 505 | m_ObjectHideFlags: 0 506 | m_PrefabParentObject: {fileID: 0} 507 | m_PrefabInternal: {fileID: 216487684} 508 | serializedVersion: 5 509 | m_Component: 510 | - component: {fileID: 1834704844} 511 | m_Layer: 0 512 | m_Name: HandRacketMover 513 | m_TagString: Untagged 514 | m_Icon: {fileID: 0} 515 | m_NavMeshLayer: 0 516 | m_StaticEditorFlags: 0 517 | m_IsActive: 1 518 | --- !u!4 &1834704844 519 | Transform: 520 | m_ObjectHideFlags: 0 521 | m_PrefabParentObject: {fileID: 0} 522 | m_PrefabInternal: {fileID: 216487684} 523 | m_GameObject: {fileID: 1834704843} 524 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 525 | m_LocalPosition: {x: 0, y: 0, z: 0} 526 | m_LocalScale: {x: 1, y: 1, z: 1} 527 | m_Children: [] 528 | m_Father: {fileID: 0} 529 | m_RootOrder: 3 530 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 531 | --- !u!1001 &1863420235 532 | Prefab: 533 | m_ObjectHideFlags: 0 534 | serializedVersion: 2 535 | m_Modification: 536 | m_TransformParent: {fileID: 0} 537 | m_Modifications: 538 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 539 | propertyPath: m_LocalPosition.x 540 | value: 1.5453217 541 | objectReference: {fileID: 0} 542 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 543 | propertyPath: m_LocalPosition.y 544 | value: 2.6748576 545 | objectReference: {fileID: 0} 546 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 547 | propertyPath: m_LocalPosition.z 548 | value: 0.6738696 549 | objectReference: {fileID: 0} 550 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 551 | propertyPath: m_LocalRotation.x 552 | value: 0 553 | objectReference: {fileID: 0} 554 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 555 | propertyPath: m_LocalRotation.y 556 | value: 0 557 | objectReference: {fileID: 0} 558 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 559 | propertyPath: m_LocalRotation.z 560 | value: 0 561 | objectReference: {fileID: 0} 562 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 563 | propertyPath: m_LocalRotation.w 564 | value: 1 565 | objectReference: {fileID: 0} 566 | - target: {fileID: 4268336702793526, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 567 | propertyPath: m_RootOrder 568 | value: 6 569 | objectReference: {fileID: 0} 570 | - target: {fileID: 114592397292101090, guid: 31466ecebd9395d4998235933ef2f889, 571 | type: 2} 572 | propertyPath: RacketFollowHand 573 | value: 574 | objectReference: {fileID: 1834704843} 575 | - target: {fileID: 114592397292101090, guid: 31466ecebd9395d4998235933ef2f889, 576 | type: 2} 577 | propertyPath: PlayerBase 578 | value: 579 | objectReference: {fileID: 360538023} 580 | - target: {fileID: 1163590719579758, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 581 | propertyPath: m_IsActive 582 | value: 0 583 | objectReference: {fileID: 0} 584 | m_RemovedComponents: [] 585 | m_ParentPrefab: {fileID: 100100000, guid: 31466ecebd9395d4998235933ef2f889, type: 2} 586 | m_IsPrefabParent: 0 587 | --- !u!1001 &2074053802 588 | Prefab: 589 | m_ObjectHideFlags: 0 590 | serializedVersion: 2 591 | m_Modification: 592 | m_TransformParent: {fileID: 0} 593 | m_Modifications: 594 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 595 | propertyPath: m_LocalPosition.x 596 | value: 0 597 | objectReference: {fileID: 0} 598 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 599 | propertyPath: m_LocalPosition.y 600 | value: 0 601 | objectReference: {fileID: 0} 602 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 603 | propertyPath: m_LocalPosition.z 604 | value: 0 605 | objectReference: {fileID: 0} 606 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 607 | propertyPath: m_LocalRotation.x 608 | value: 0 609 | objectReference: {fileID: 0} 610 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 611 | propertyPath: m_LocalRotation.y 612 | value: 0 613 | objectReference: {fileID: 0} 614 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 615 | propertyPath: m_LocalRotation.z 616 | value: 0 617 | objectReference: {fileID: 0} 618 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 619 | propertyPath: m_LocalRotation.w 620 | value: 1 621 | objectReference: {fileID: 0} 622 | - target: {fileID: 4372407139801650, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 623 | propertyPath: m_RootOrder 624 | value: 5 625 | objectReference: {fileID: 0} 626 | - target: {fileID: 114453581304663162, guid: 981f90a823714d44db0d2a65ceef2a49, 627 | type: 2} 628 | propertyPath: handRacketMover 629 | value: 630 | objectReference: {fileID: 1834704843} 631 | - target: {fileID: 114084852135292966, guid: 981f90a823714d44db0d2a65ceef2a49, 632 | type: 2} 633 | propertyPath: eye 634 | value: 635 | objectReference: {fileID: 360538024} 636 | - target: {fileID: 114084852135292966, guid: 981f90a823714d44db0d2a65ceef2a49, 637 | type: 2} 638 | propertyPath: showHandMesh 639 | value: 0 640 | objectReference: {fileID: 0} 641 | - target: {fileID: 114453581304663162, guid: 981f90a823714d44db0d2a65ceef2a49, 642 | type: 2} 643 | propertyPath: enableDepthMask 644 | value: 1 645 | objectReference: {fileID: 0} 646 | m_RemovedComponents: [] 647 | m_ParentPrefab: {fileID: 100100000, guid: 981f90a823714d44db0d2a65ceef2a49, type: 2} 648 | m_IsPrefabParent: 0 649 | -------------------------------------------------------------------------------- /Assets/DemoScene/HandScene.unity.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 1d5c316fdae3e734a951741d4e1b05c3 3 | timeCreated: 1526956703 4 | licenseType: Free 5 | DefaultImporter: 6 | externalObjects: {} 7 | userData: 8 | assetBundleName: 9 | assetBundleVariant: 10 | -------------------------------------------------------------------------------- /Assets/DemoScene/TransformReset.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | 3 | public class TransformReset : MonoBehaviour { 4 | 5 | Vector3 originPos = new Vector3(); 6 | Rigidbody rigidBody; 7 | 8 | void Start () { 9 | originPos = transform.position; 10 | rigidBody = GetComponent(); 11 | } 12 | 13 | void Update () { 14 | float pos = Vector3.Distance(originPos, transform.position); 15 | if (pos>4f) { 16 | rigidBody.constraints = RigidbodyConstraints.FreezeAll; 17 | transform.position = originPos; 18 | rigidBody.constraints = RigidbodyConstraints.None; 19 | } 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /Assets/DemoScene/TransformReset.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 80d5d3d4bbecc8c42878475f97577b86 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 0973ae8004b355846864b16ff9c1a463 3 | folderAsset: yes 4 | timeCreated: 1526960215 5 | licenseType: Free 6 | DefaultImporter: 7 | externalObjects: {} 8 | userData: 9 | assetBundleName: 10 | assetBundleVariant: 11 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Materials.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 912aa8e4b785a8949affe4ac80e6d5eb 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Materials/handmat.mat: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!21 &2100000 4 | Material: 5 | serializedVersion: 6 6 | m_ObjectHideFlags: 0 7 | m_PrefabParentObject: {fileID: 0} 8 | m_PrefabInternal: {fileID: 0} 9 | m_Name: handmat 10 | m_Shader: {fileID: 4800000, guid: 9403751ca38f3124ba819ab433a444cc, type: 3} 11 | m_ShaderKeywords: _GLOSSYREFLECTIONS_OFF _SMOOTHNESS_TEXTURE_ALBEDO_CHANNEL_A _SPECULARHIGHLIGHTS_OFF 12 | m_LightmapFlags: 6 13 | m_EnableInstancingVariants: 0 14 | m_DoubleSidedGI: 0 15 | m_CustomRenderQueue: -1 16 | stringTagMap: {} 17 | disabledShaderPasses: [] 18 | m_SavedProperties: 19 | serializedVersion: 3 20 | m_TexEnvs: 21 | - _BumpMap: 22 | m_Texture: {fileID: 0} 23 | m_Scale: {x: 1, y: 1} 24 | m_Offset: {x: 0, y: 0} 25 | - _DetailAlbedoMap: 26 | m_Texture: {fileID: 0} 27 | m_Scale: {x: 1, y: 1} 28 | m_Offset: {x: 0, y: 0} 29 | - _DetailMask: 30 | m_Texture: {fileID: 0} 31 | m_Scale: {x: 1, y: 1} 32 | m_Offset: {x: 0, y: 0} 33 | - _DetailNormalMap: 34 | m_Texture: {fileID: 0} 35 | m_Scale: {x: 1, y: 1} 36 | m_Offset: {x: 0, y: 0} 37 | - _EmissionMap: 38 | m_Texture: {fileID: 0} 39 | m_Scale: {x: 1, y: 1} 40 | m_Offset: {x: 0, y: 0} 41 | - _Illum: 42 | m_Texture: {fileID: 0} 43 | m_Scale: {x: 1, y: 1} 44 | m_Offset: {x: 0, y: 0} 45 | - _MainTex: 46 | m_Texture: {fileID: 2800000, guid: 4bcb2d2adbb90044c8edf8a527700613, type: 3} 47 | m_Scale: {x: 1, y: 1} 48 | m_Offset: {x: 0, y: 0} 49 | - _MainTex2: 50 | m_Texture: {fileID: 0} 51 | m_Scale: {x: 1, y: 1} 52 | m_Offset: {x: 0, y: 0} 53 | - _MetallicGlossMap: 54 | m_Texture: {fileID: 0} 55 | m_Scale: {x: 1, y: 1} 56 | m_Offset: {x: 0, y: 0} 57 | - _OcclusionMap: 58 | m_Texture: {fileID: 0} 59 | m_Scale: {x: 1, y: 1} 60 | m_Offset: {x: 0, y: 0} 61 | - _ParallaxMap: 62 | m_Texture: {fileID: 0} 63 | m_Scale: {x: 1, y: 1} 64 | m_Offset: {x: 0, y: 0} 65 | - _SpecGlossMap: 66 | m_Texture: {fileID: 0} 67 | m_Scale: {x: 1, y: 1} 68 | m_Offset: {x: 0, y: 0} 69 | m_Floats: 70 | - _BumpScale: 1 71 | - _ColorLevel: 7 72 | - _Cutoff: 0.5 73 | - _DetailNormalMapScale: 1 74 | - _Distortion: 1 75 | - _DotSize: 0 76 | - _DstBlend: 0 77 | - _EdgeWeight: 1 78 | - _Emission: 1 79 | - _GlossMapScale: 0 80 | - _Glossiness: 0.5 81 | - _GlossyReflections: 0 82 | - _Linecount: 90 83 | - _Metallic: 0 84 | - _Mode: 0 85 | - _OcclusionStrength: 1 86 | - _Parallax: 0.02 87 | - _Shininess: 0.7 88 | - _SmoothnessTextureChannel: 1 89 | - _SpecularHighlights: 0 90 | - _SrcBlend: 1 91 | - _StencilComp: 3 92 | - _StencilValue: 0 93 | - _Thickness: 0 94 | - _TimeX: 1 95 | - _UVSec: 0 96 | - _Value: 1 97 | - _Vignette: 1.5 98 | - _ZTest: 4 99 | - _ZWrite: 1 100 | m_Colors: 101 | - _Color: {r: 0, g: 0, b: 0, a: 0} 102 | - _ColorRGB: {r: 1, g: 1, b: 1, a: 1} 103 | - _EmissionColor: {r: 0, g: 0, b: 0, a: 0} 104 | - _ScreenResolution: {r: 0, g: 0, b: 0, a: 0} 105 | - _SpecColor: {r: 0.7068459, g: 0.7554687, b: 0.7794118, a: 1} 106 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Materials/handmat.mat.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: c3e9333e75968484f894d1f93d7f4024 3 | timeCreated: 1467005667 4 | licenseType: Free 5 | NativeFormatImporter: 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Prefabs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 41fbe010f1b1da148ac6e776027da479 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Prefabs/DepthMask.prefab: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!1001 &100100000 4 | Prefab: 5 | m_ObjectHideFlags: 1 6 | serializedVersion: 2 7 | m_Modification: 8 | m_TransformParent: {fileID: 0} 9 | m_Modifications: [] 10 | m_RemovedComponents: [] 11 | m_ParentPrefab: {fileID: 0} 12 | m_RootGameObject: {fileID: 1854828209721920} 13 | m_IsPrefabParent: 0 14 | --- !u!1 &1854828209721920 15 | GameObject: 16 | m_ObjectHideFlags: 0 17 | m_PrefabParentObject: {fileID: 0} 18 | m_PrefabInternal: {fileID: 100100000} 19 | serializedVersion: 5 20 | m_Component: 21 | - component: {fileID: 4754392168165110} 22 | - component: {fileID: 33128831506864518} 23 | - component: {fileID: 23610675285627666} 24 | m_Layer: 0 25 | m_Name: DepthMask 26 | m_TagString: Untagged 27 | m_Icon: {fileID: 0} 28 | m_NavMeshLayer: 0 29 | m_StaticEditorFlags: 0 30 | m_IsActive: 1 31 | --- !u!4 &4754392168165110 32 | Transform: 33 | m_ObjectHideFlags: 1 34 | m_PrefabParentObject: {fileID: 0} 35 | m_PrefabInternal: {fileID: 100100000} 36 | m_GameObject: {fileID: 1854828209721920} 37 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 38 | m_LocalPosition: {x: 0, y: 0, z: 2} 39 | m_LocalScale: {x: 4.57, y: 3.42, z: 1} 40 | m_Children: [] 41 | m_Father: {fileID: 0} 42 | m_RootOrder: 0 43 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 44 | --- !u!23 &23610675285627666 45 | MeshRenderer: 46 | m_ObjectHideFlags: 1 47 | m_PrefabParentObject: {fileID: 0} 48 | m_PrefabInternal: {fileID: 100100000} 49 | m_GameObject: {fileID: 1854828209721920} 50 | m_Enabled: 1 51 | m_CastShadows: 0 52 | m_ReceiveShadows: 0 53 | m_DynamicOccludee: 1 54 | m_MotionVectors: 1 55 | m_LightProbeUsage: 1 56 | m_ReflectionProbeUsage: 1 57 | m_Materials: 58 | - {fileID: 2100000, guid: 4bb8bf6460d9cb24aa02a1340d61a9ac, type: 2} 59 | m_StaticBatchInfo: 60 | firstSubMesh: 0 61 | subMeshCount: 0 62 | m_StaticBatchRoot: {fileID: 0} 63 | m_ProbeAnchor: {fileID: 0} 64 | m_LightProbeVolumeOverride: {fileID: 0} 65 | m_ScaleInLightmap: 1 66 | m_PreserveUVs: 1 67 | m_IgnoreNormalsForChartDetection: 0 68 | m_ImportantGI: 0 69 | m_StitchLightmapSeams: 0 70 | m_SelectedEditorRenderState: 3 71 | m_MinimumChartSize: 4 72 | m_AutoUVMaxDistance: 0.5 73 | m_AutoUVMaxAngle: 89 74 | m_LightmapParameters: {fileID: 0} 75 | m_SortingLayerID: 0 76 | m_SortingLayer: 0 77 | m_SortingOrder: 0 78 | --- !u!33 &33128831506864518 79 | MeshFilter: 80 | m_ObjectHideFlags: 1 81 | m_PrefabParentObject: {fileID: 0} 82 | m_PrefabInternal: {fileID: 100100000} 83 | m_GameObject: {fileID: 1854828209721920} 84 | m_Mesh: {fileID: 10210, guid: 0000000000000000e000000000000000, type: 0} 85 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Prefabs/DepthMask.prefab.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 44796e0087354784594379b0f3844f6e 3 | NativeFormatImporter: 4 | externalObjects: {} 5 | mainObjectFileID: 100100000 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Prefabs/HandRacketCollisionObj.prefab: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!1001 &100100000 4 | Prefab: 5 | m_ObjectHideFlags: 1 6 | serializedVersion: 2 7 | m_Modification: 8 | m_TransformParent: {fileID: 0} 9 | m_Modifications: [] 10 | m_RemovedComponents: [] 11 | m_ParentPrefab: {fileID: 0} 12 | m_RootGameObject: {fileID: 1163590719579758} 13 | m_IsPrefabParent: 1 14 | --- !u!1 &1163590719579758 15 | GameObject: 16 | m_ObjectHideFlags: 0 17 | m_PrefabParentObject: {fileID: 0} 18 | m_PrefabInternal: {fileID: 100100000} 19 | serializedVersion: 5 20 | m_Component: 21 | - component: {fileID: 4268336702793526} 22 | - component: {fileID: 33828842715923924} 23 | - component: {fileID: 135931790246375864} 24 | - component: {fileID: 23888207796196254} 25 | - component: {fileID: 114990384989883582} 26 | - component: {fileID: 114592397292101090} 27 | m_Layer: 0 28 | m_Name: HandRacketCollisionObj 29 | m_TagString: Untagged 30 | m_Icon: {fileID: 0} 31 | m_NavMeshLayer: 0 32 | m_StaticEditorFlags: 0 33 | m_IsActive: 1 34 | --- !u!4 &4268336702793526 35 | Transform: 36 | m_ObjectHideFlags: 1 37 | m_PrefabParentObject: {fileID: 0} 38 | m_PrefabInternal: {fileID: 100100000} 39 | m_GameObject: {fileID: 1163590719579758} 40 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 41 | m_LocalPosition: {x: 1.5453217, y: 2.6748576, z: 0.6738696} 42 | m_LocalScale: {x: 0.1, y: 0.1, z: 0.1} 43 | m_Children: [] 44 | m_Father: {fileID: 0} 45 | m_RootOrder: 0 46 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 47 | --- !u!23 &23888207796196254 48 | MeshRenderer: 49 | m_ObjectHideFlags: 1 50 | m_PrefabParentObject: {fileID: 0} 51 | m_PrefabInternal: {fileID: 100100000} 52 | m_GameObject: {fileID: 1163590719579758} 53 | m_Enabled: 0 54 | m_CastShadows: 1 55 | m_ReceiveShadows: 1 56 | m_DynamicOccludee: 1 57 | m_MotionVectors: 1 58 | m_LightProbeUsage: 1 59 | m_ReflectionProbeUsage: 1 60 | m_Materials: 61 | - {fileID: 10303, guid: 0000000000000000f000000000000000, type: 0} 62 | m_StaticBatchInfo: 63 | firstSubMesh: 0 64 | subMeshCount: 0 65 | m_StaticBatchRoot: {fileID: 0} 66 | m_ProbeAnchor: {fileID: 0} 67 | m_LightProbeVolumeOverride: {fileID: 0} 68 | m_ScaleInLightmap: 1 69 | m_PreserveUVs: 1 70 | m_IgnoreNormalsForChartDetection: 0 71 | m_ImportantGI: 0 72 | m_StitchLightmapSeams: 0 73 | m_SelectedEditorRenderState: 3 74 | m_MinimumChartSize: 4 75 | m_AutoUVMaxDistance: 0.5 76 | m_AutoUVMaxAngle: 89 77 | m_LightmapParameters: {fileID: 0} 78 | m_SortingLayerID: 0 79 | m_SortingLayer: 0 80 | m_SortingOrder: 0 81 | --- !u!33 &33828842715923924 82 | MeshFilter: 83 | m_ObjectHideFlags: 1 84 | m_PrefabParentObject: {fileID: 0} 85 | m_PrefabInternal: {fileID: 100100000} 86 | m_GameObject: {fileID: 1163590719579758} 87 | m_Mesh: {fileID: 10207, guid: 0000000000000000e000000000000000, type: 0} 88 | --- !u!114 &114592397292101090 89 | MonoBehaviour: 90 | m_ObjectHideFlags: 1 91 | m_PrefabParentObject: {fileID: 0} 92 | m_PrefabInternal: {fileID: 100100000} 93 | m_GameObject: {fileID: 1163590719579758} 94 | m_Enabled: 1 95 | m_EditorHideFlags: 0 96 | m_Script: {fileID: 11500000, guid: 3546a1c6401f9254f906461ff1f615a5, type: 3} 97 | m_Name: 98 | m_EditorClassIdentifier: 99 | UseGravity: 0 100 | FreezeAll: 0 101 | forceCollision: 2 102 | IsRacketRigidbody: 1 103 | RacketFollowHand: {fileID: 0} 104 | PlayerBase: {fileID: 0} 105 | IsBallRigidbody: 0 106 | --- !u!114 &114990384989883582 107 | MonoBehaviour: 108 | m_ObjectHideFlags: 1 109 | m_PrefabParentObject: {fileID: 0} 110 | m_PrefabInternal: {fileID: 100100000} 111 | m_GameObject: {fileID: 1163590719579758} 112 | m_Enabled: 1 113 | m_EditorHideFlags: 0 114 | m_Script: {fileID: 11500000, guid: 79370d21936d76b44910c29c302dc4a3, type: 3} 115 | m_Name: 116 | m_EditorClassIdentifier: 117 | --- !u!135 &135931790246375864 118 | SphereCollider: 119 | m_ObjectHideFlags: 1 120 | m_PrefabParentObject: {fileID: 0} 121 | m_PrefabInternal: {fileID: 100100000} 122 | m_GameObject: {fileID: 1163590719579758} 123 | m_Material: {fileID: 0} 124 | m_IsTrigger: 0 125 | m_Enabled: 1 126 | serializedVersion: 2 127 | m_Radius: 0.5 128 | m_Center: {x: 0, y: 0, z: 0} 129 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Prefabs/HandRacketCollisionObj.prefab.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 31466ecebd9395d4998235933ef2f889 3 | NativeFormatImporter: 4 | externalObjects: {} 5 | mainObjectFileID: 100100000 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Prefabs/SRWorksHand.prefab: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!1001 &100100000 4 | Prefab: 5 | m_ObjectHideFlags: 1 6 | serializedVersion: 2 7 | m_Modification: 8 | m_TransformParent: {fileID: 0} 9 | m_Modifications: [] 10 | m_RemovedComponents: [] 11 | m_ParentPrefab: {fileID: 0} 12 | m_RootGameObject: {fileID: 1325028295477620} 13 | m_IsPrefabParent: 1 14 | --- !u!1 &1325028295477620 15 | GameObject: 16 | m_ObjectHideFlags: 0 17 | m_PrefabParentObject: {fileID: 0} 18 | m_PrefabInternal: {fileID: 100100000} 19 | serializedVersion: 5 20 | m_Component: 21 | - component: {fileID: 4372407139801650} 22 | - component: {fileID: 114453581304663162} 23 | - component: {fileID: 114084852135292966} 24 | m_Layer: 0 25 | m_Name: SRWorksHand 26 | m_TagString: Untagged 27 | m_Icon: {fileID: 0} 28 | m_NavMeshLayer: 0 29 | m_StaticEditorFlags: 0 30 | m_IsActive: 1 31 | --- !u!4 &4372407139801650 32 | Transform: 33 | m_ObjectHideFlags: 1 34 | m_PrefabParentObject: {fileID: 0} 35 | m_PrefabInternal: {fileID: 100100000} 36 | m_GameObject: {fileID: 1325028295477620} 37 | m_LocalRotation: {x: 0, y: 0, z: 0, w: 1} 38 | m_LocalPosition: {x: 0, y: 0, z: 0} 39 | m_LocalScale: {x: 1, y: 1, z: 1} 40 | m_Children: [] 41 | m_Father: {fileID: 0} 42 | m_RootOrder: 0 43 | m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0} 44 | --- !u!114 &114084852135292966 45 | MonoBehaviour: 46 | m_ObjectHideFlags: 1 47 | m_PrefabParentObject: {fileID: 0} 48 | m_PrefabInternal: {fileID: 100100000} 49 | m_GameObject: {fileID: 1325028295477620} 50 | m_Enabled: 1 51 | m_EditorHideFlags: 0 52 | m_Script: {fileID: 11500000, guid: 49051db3cbcaf7448a77d3c0386917ff, type: 3} 53 | m_Name: 54 | m_EditorClassIdentifier: 55 | showHandMesh: 1 56 | handSizeRange: 0.15 57 | DebugShow: 0 58 | handMaterial: {fileID: 2100000, guid: c3e9333e75968484f894d1f93d7f4024, type: 2} 59 | viveSR: {fileID: 114030089609639150, guid: 043c7faf0fdcecd499d4424a614b2482, type: 2} 60 | eye: {fileID: 0} 61 | dynamicHandDisDivided: 0.2 62 | _OutNear: {x: 0, y: 0, z: 0} 63 | _OutFar: {x: 0, y: 0, z: 0} 64 | --- !u!114 &114453581304663162 65 | MonoBehaviour: 66 | m_ObjectHideFlags: 1 67 | m_PrefabParentObject: {fileID: 0} 68 | m_PrefabInternal: {fileID: 100100000} 69 | m_GameObject: {fileID: 1325028295477620} 70 | m_Enabled: 1 71 | m_EditorHideFlags: 0 72 | m_Script: {fileID: 11500000, guid: 79d8999e97457ad44afbb90831b1b675, type: 3} 73 | m_Name: 74 | m_EditorClassIdentifier: 75 | handRacketMover: {fileID: 0} 76 | depthMask: {fileID: 1854828209721920, guid: 44796e0087354784594379b0f3844f6e, type: 2} 77 | enableDepthMask: 1 78 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Prefabs/SRWorksHand.prefab.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 981f90a823714d44db0d2a65ceef2a49 3 | NativeFormatImporter: 4 | externalObjects: {} 5 | mainObjectFileID: 100100000 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/README.md: -------------------------------------------------------------------------------- 1 | A Vive SRWorks Hand Interaction example for Unity 2 | 3 | The example sceme shows how to occlude and interact with virtual objects with your hands 4 | 5 | - In this example, by default the occlusion is using a depth mask (you can enable/disable it in SRWorksHand) 6 | 7 | - You can also view the hand's mesh instead of the occlusion depth mask by enabling it in SRWorksHand 8 | 9 | - To slap/punch (without going through) enable the HandRacketCollisionObj in the scene 10 | (you can make it visible by enabling the Mesh Renderer on it) 11 | 12 | - Depth mask occlusion settings can be edited at runtime in the inspector on the DualCamera (head) object 13 | in addition to the Game Window SRWorks settings that can be called up by pressing the S and R keys. 14 | 15 | Requirements: 16 | - VIVE Pro (make sure cameras are enabled and working in settings) 17 | - ViveSRWorks Unity package: Vive-SRWorks-0.7.5.0-Unity-Plugin.unitypackage (install this first) 18 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/README.md.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 2a274843e2ba9254f8f1eeb8d5445e68 3 | TextScriptImporter: 4 | externalObjects: {} 5 | userData: 6 | assetBundleName: 7 | assetBundleVariant: 8 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 00622c1c421e5c1419d69f017de9df07 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/HandTouch.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | 5 | public class HandTouch : MonoBehaviour 6 | { 7 | public static int HandTouchLayer 8 | { 9 | get 10 | { 11 | int layer = LayerMask.NameToLayer("HandTouch"); 12 | if (layer < 0) 13 | { Debug.LogError("please add a layer => HandTouch, and set 'HandTouch' to the object you want to touch!"); return 0; } 14 | return layer; 15 | } 16 | } 17 | 18 | float recoverTime; 19 | private void OnCollisionEnter(Collision collision) 20 | { 21 | GetComponent().material.color = Color.red; 22 | recoverTime = 0.5f; 23 | } 24 | 25 | private void Awake() 26 | { 27 | gameObject.layer = HandTouchLayer; 28 | } 29 | 30 | private void Update() 31 | { 32 | recoverTime -= Time.deltaTime; 33 | if (recoverTime < 0) 34 | GetComponent().material.color = Color.white; 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/HandTouch.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 79370d21936d76b44910c29c302dc4a3 3 | timeCreated: 1526957997 4 | licenseType: Free 5 | MonoImporter: 6 | externalObjects: {} 7 | serializedVersion: 2 8 | defaultReferences: [] 9 | executionOrder: 0 10 | icon: {instanceID: 0} 11 | userData: 12 | assetBundleName: 13 | assetBundleVariant: 14 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/MyPhysics.cs: -------------------------------------------------------------------------------- 1 | using UnityEngine; 2 | 3 | public class MyPhysics : MonoBehaviour 4 | { 5 | public bool UseGravity; 6 | public bool FreezeAll; 7 | public CollisionDetectionMode forceCollision = CollisionDetectionMode.ContinuousDynamic; 8 | 9 | [Header("Racket-------------------------------------------")] 10 | public bool IsRacketRigidbody; 11 | public GameObject RacketFollowHand; 12 | public Transform PlayerBase; 13 | 14 | [Header("Ball-------------------------------------------")] 15 | public bool IsBallRigidbody; 16 | 17 | RacketRigidbody _RacketRigidbody; 18 | 19 | private void Awake() 20 | { 21 | if (IsRacketRigidbody) 22 | { 23 | _RacketRigidbody = SetRacketRigidbody(gameObject, RacketFollowHand, PlayerBase); 24 | } 25 | else if (IsBallRigidbody) 26 | { 27 | SetBallRigidbody(gameObject); 28 | } 29 | } 30 | 31 | private void Update() 32 | { 33 | if (_RacketRigidbody != null && _RacketRigidbody._playerBase != PlayerBase) 34 | _RacketRigidbody._playerBase = PlayerBase; 35 | } 36 | 37 | /// 38 | /// Add a rigidbody for Racket, very high speed wave racket and the ball not through racket. 39 | /// and use _rb.MovePosition to follow hand. 40 | /// 41 | public class RacketRigidbody : MonoBehaviour 42 | { 43 | GameObject _followObj; 44 | Rigidbody _rb; 45 | public Transform _playerBase; 46 | 47 | /// 48 | /// Add a rigidbody for Racket, very hight speed wave racket and the ball not through racket. 49 | /// 50 | public void Init(GameObject followHandObj) 51 | { 52 | _followObj = followHandObj; 53 | _rb = this.gameObject.GetComponent(); 54 | 55 | if (_rb == null) 56 | _rb = this.gameObject.AddComponent(); 57 | 58 | _rb.velocity = Vector3.zero; 59 | _rb.position = followHandObj.transform.position; 60 | _rb.rotation = followHandObj.transform.rotation; 61 | _rb.isKinematic = true; 62 | _rb.interpolation = RigidbodyInterpolation.Interpolate; 63 | //_rb.collisionDetectionMode = CollisionDetectionMode.ContinuousDynamic; 64 | } 65 | 66 | private void FixedUpdate() 67 | { 68 | Vector3 pos = _followObj.transform.position; 69 | Quaternion rot = _followObj.transform.rotation; 70 | if (_playerBase != null) 71 | { 72 | pos = _playerBase.TransformPoint(pos); 73 | rot = rot * _playerBase.rotation; 74 | } 75 | _rb.MovePosition(pos); 76 | _rb.MoveRotation(rot); 77 | } 78 | } 79 | 80 | public static RacketRigidbody SetRacketRigidbody(GameObject racketObj, GameObject followHandObj, Transform playerBase) 81 | { 82 | RacketRigidbody racket = racketObj.AddComponent(); 83 | racket.Init(followHandObj); 84 | 85 | MyPhysics myPhys = racketObj.GetComponent(); 86 | // if (racketObj.GetComponent() != null) 87 | // { 88 | racketObj.GetComponent().useGravity = myPhys.UseGravity; 89 | racketObj.GetComponent().constraints = (myPhys.FreezeAll) ? RigidbodyConstraints.FreezeAll : RigidbodyConstraints.None; 90 | racketObj.GetComponent().collisionDetectionMode = myPhys.forceCollision; 91 | // } 92 | 93 | return racket; 94 | } 95 | 96 | public static void SetBallRigidbody(GameObject ballObj) 97 | { 98 | Rigidbody rb = ballObj.GetComponent(); 99 | if (rb == null) 100 | rb = ballObj.AddComponent(); 101 | rb.isKinematic = false; 102 | rb.interpolation = RigidbodyInterpolation.Interpolate; 103 | //rb.collisionDetectionMode = CollisionDetectionMode.ContinuousDynamic; 104 | 105 | MyPhysics myPhys = ballObj.GetComponent(); 106 | // if (ballObj.GetComponent() != null) 107 | // { 108 | ballObj.GetComponent().useGravity = myPhys.UseGravity; 109 | ballObj.GetComponent().constraints = (myPhys.FreezeAll) ? RigidbodyConstraints.FreezeAll : RigidbodyConstraints.None; 110 | ballObj.GetComponent().collisionDetectionMode = myPhys.forceCollision; 111 | // } 112 | } 113 | } 114 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/MyPhysics.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 3546a1c6401f9254f906461ff1f615a5 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/MySingleton.cs: -------------------------------------------------------------------------------- 1 | using System.Collections.Generic; 2 | using UnityEngine; 3 | 4 | /// 5 | /// http://wiki.unity3d.com/index.php/Singleton 6 | /// Be aware this will not prevent a non singleton constructor 7 | /// such as `T myT = new T();` 8 | /// To prevent that, add `protected T () {}` to your singleton class. 9 | /// 10 | /// As a note, this is made as MonoBehaviour because we need Coroutines. 11 | /// 12 | public class MySingleton : MonoBehaviour where T : MonoBehaviour 13 | { 14 | private static T _instance; 15 | 16 | private static object _lock = new object(); 17 | 18 | //private static List instanceRec = new List(); 19 | 20 | private static int _findNullCount = 0; 21 | 22 | public static T Instance 23 | { 24 | get 25 | { 26 | if (_findNullCount > 1) 27 | { 28 | //Debug.LogError("[MySingleton] not found > 1 time: " + typeof(T).ToString()); 29 | return null; 30 | } 31 | 32 | //if (applicationIsQuitting) 33 | //{ 34 | // Debug.LogWarning("[Singleton] Instance '" + typeof(T) + 35 | // "' already destroyed on application quit." + 36 | // " Won't create again - returning null."); 37 | // return null; 38 | //} 39 | 40 | lock (_lock) 41 | { 42 | if (_instance == null) 43 | { 44 | _instance = (T)FindObjectOfType(typeof(T)); 45 | 46 | if (_instance == null) 47 | { 48 | _findNullCount++; 49 | 50 | //讓warning只印一次就好 51 | //if (instanceRec.IndexOf(typeof(T).ToString()) == -1) 52 | if (_findNullCount == 1) 53 | { 54 | Debug.LogWarning("[Singleton] FindObjectOfType not found :" + typeof(T)); 55 | //instanceRec.Add(typeof(T).ToString()); 56 | } 57 | 58 | //GameObject singleton = new GameObject(); 59 | //_instance = singleton.AddComponent(); 60 | //singleton.name = "(singleton) " + typeof(T).ToString(); 61 | 62 | //DontDestroyOnLoad(singleton); 63 | 64 | //Debug.Log("[Singleton] An instance of " + typeof(T) + 65 | // " is needed in the scene, so '" + singleton + 66 | // "' was created with DontDestroyOnLoad."); 67 | } 68 | else 69 | { 70 | Debug.Log("[Singleton] Using instance already created: " + typeof(T)); 71 | if (FindObjectsOfType(typeof(T)).Length > 1) 72 | { 73 | Debug.LogError("[Singleton] Something went really wrong " + 74 | " - there should never be more than 1 singleton!" + 75 | " Reopening the scene might fix it."); 76 | return _instance; 77 | } 78 | } 79 | } 80 | 81 | return _instance; 82 | } 83 | } 84 | } 85 | 86 | //private static bool applicationIsQuitting = false; 87 | /// 88 | /// When Unity quits, it destroys objects in a random order. 89 | /// In principle, a Singleton is only destroyed when application quits. 90 | /// If any script calls Instance after it have been destroyed, 91 | /// it will create a buggy ghost object that will stay on the Editor scene 92 | /// even after stopping playing the Application. Really bad! 93 | /// So, this was made to be sure we're not creating that buggy ghost object. 94 | /// 95 | //public void OnDestroy() 96 | //{ 97 | // applicationIsQuitting = true; 98 | //} 99 | /* 100 | public static void CreateSingleton(string name) 101 | { 102 | if (_instance != null) 103 | return; 104 | GameObject singleton = new GameObject(); 105 | _instance = singleton.AddComponent(); 106 | singleton.name = name;// "(singleton) " + typeof(T).ToString(); 107 | Debug.LogWarning("[Singleton] : " + name + " , create..."); 108 | } 109 | */ 110 | } -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/MySingleton.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: cfea4536d70ac5e49bd5b41a0994228e 3 | MonoImporter: 4 | externalObjects: {} 5 | serializedVersion: 2 6 | defaultReferences: [] 7 | executionOrder: 0 8 | icon: {instanceID: 0} 9 | userData: 10 | assetBundleName: 11 | assetBundleVariant: 12 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/SRHandManager.cs: -------------------------------------------------------------------------------- 1 | using System.Collections; 2 | using UnityEngine; 3 | using Vive.Plugin.SR; 4 | 5 | public class SRHandManager : MySingleton 6 | { 7 | public GameObject handRacketMover; 8 | public GameObject depthMask; 9 | private GameObject depthMaskR; 10 | public bool enableDepthMask; 11 | private bool prevDepthMaskEnabled; 12 | private SRWorksHand srWorksHand; 13 | 14 | void Start() 15 | { 16 | srWorksHand = gameObject.GetComponent(); 17 | 18 | if (srWorksHand.showHandMesh) 19 | enableDepthMask = false; 20 | 21 | // get depth mask for occlusion 22 | GameObject root = GameObject.Find("Anchor (Left)"); 23 | Transform trans = root.transform.Find("DepthMask (left)"); 24 | GameObject depthObjectTest = null; 25 | if (trans != null) 26 | depthObjectTest = trans.gameObject; 27 | if(depthObjectTest == null) 28 | { 29 | GameObject quad = Instantiate(depthMask); 30 | quad.transform.parent = root.transform; 31 | quad.name = "DepthMask"; 32 | quad.SetActive(true); 33 | } 34 | else 35 | { 36 | depthMask.SetActive(true); 37 | root = GameObject.Find("Anchor (Right)"); 38 | depthMaskR = root.transform.Find("DepthMask (right)").gameObject; 39 | depthMaskR.SetActive(true); 40 | } 41 | 42 | StartLoadReconstructData(); 43 | } 44 | 45 | void StartLoadReconstructData() 46 | { 47 | //TODO: load previously scanned reconstruction mesh if available 48 | 49 | StartCoroutine(_waitReconstructMeshLoadDone()); 50 | } 51 | 52 | IEnumerator _waitReconstructMeshLoadDone() 53 | { 54 | yield return new WaitForSeconds(1); 55 | 56 | //Set touch hand 57 | SRWorksHand.Instance.SetDetectHand(null, handRacketMover, null); 58 | 59 | //enable depth mask 60 | if (enableDepthMask) 61 | { 62 | ViveSR_DualCameraImageRenderer.UpdateDepthMaterial = true; 63 | } else 64 | { 65 | SRWorksHand.GetDynamicHand().gameObject.layer = LayerMask.NameToLayer("HandTouch"); 66 | } 67 | 68 | } 69 | private void LateUpdate() 70 | { 71 | if (prevDepthMaskEnabled != enableDepthMask) { 72 | if (enableDepthMask){ 73 | ViveSR_DualCameraImageRenderer.UpdateDepthMaterial = true; 74 | } else { 75 | ViveSR_DualCameraImageRenderer.UpdateDepthMaterial = false; 76 | if (srWorksHand.showHandMesh) 77 | { 78 | SRWorksHand.Instance.SetDetectHand(null, handRacketMover, null); 79 | // SRWorksHand.GetDynamicHand().gameObject.layer = LayerMask.NameToLayer("HandTouch"); 80 | } 81 | } 82 | prevDepthMaskEnabled = enableDepthMask; 83 | } 84 | if (srWorksHand.showHandMesh) 85 | enableDepthMask = false; 86 | } 87 | } 88 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/SRHandManager.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 79d8999e97457ad44afbb90831b1b675 3 | timeCreated: 1526960316 4 | licenseType: Free 5 | MonoImporter: 6 | externalObjects: {} 7 | serializedVersion: 2 8 | defaultReferences: [] 9 | executionOrder: 0 10 | icon: {instanceID: 0} 11 | userData: 12 | assetBundleName: 13 | assetBundleVariant: 14 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/SRWorksHand.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using UnityEngine; 4 | using Vive.Plugin.SR; 5 | 6 | public class SRWorksHand : MySingleton 7 | { 8 | public bool showHandMesh = true; 9 | [Range(0.01f, 0.5f)] 10 | public float handSizeRange = 0.15f; 11 | public const float Near = 0f, Far = 0.7f; 12 | public bool DebugShow; 13 | public const string DynamicHandName = "Depth Collider"; 14 | public Material handMaterial = null; 15 | private bool materialSet = false; 16 | 17 | public ViveSR viveSR; 18 | public Transform eye; 19 | 20 | static bool isEnableDepth; 21 | public static void OpenDynamicHandCollider() 22 | { 23 | Debug.LogWarning("OpenDynamicHandCollider"); 24 | // if (isEnableDepth) 25 | // return; 26 | isEnableDepth = true; 27 | ViveSR_DualCameraImageCapture.EnableDepthProcess(true); 28 | ViveSR_DualCameraDepthCollider.UpdateDepthCollider = true; 29 | ViveSR_DualCameraImageCapture.ChangeDepthCase(DepthCase.CLOSE_RANGE); 30 | ViveSR_DualCameraDepthCollider.UpdateDepthColliderRange = true; 31 | ViveSR_DualCameraDepthCollider.UpdateColliderNearDistance = Near; 32 | ViveSR_DualCameraDepthCollider.UpdateColliderFarDistance = Far; 33 | 34 | ViveSR_DualCameraImageCapture.DepthRefinement = true; 35 | ViveSR_DualCameraImageCapture.DepthEdgeEnhance = true; 36 | 37 | _dynamicHandMesh = null; 38 | Debug.LogWarning("OpenDynamicHandCollider"); 39 | } 40 | 41 | public static void CloseDynamicHandCollider() 42 | { 43 | if (!isEnableDepth) 44 | return; 45 | isEnableDepth = false; 46 | ViveSR_DualCameraImageCapture.EnableDepthProcess(false); 47 | ViveSR_DualCameraDepthCollider.UpdateDepthCollider = false; 48 | ViveSR_DualCameraDepthCollider.UpdateDepthColliderRange = false; 49 | _dynamicHandMesh = null; 50 | SRWorksHand.GetDynamicHandMesh().Clear(); 51 | Debug.LogWarning("CloseDynamicHandCollider"); 52 | } 53 | 54 | public static Transform GetDynamicHand() 55 | { 56 | Transform handCollider; 57 | FindTransform(SRWorksHand.Instance.viveSR.transform, DynamicHandName, out handCollider); 58 | return handCollider; 59 | } 60 | public static void FindTransform(Transform root, string findName, out Transform outFind, bool isContain = false, bool toLower = false) 61 | { 62 | outFind = null; 63 | _findTransform(root, findName, ref outFind, isContain, toLower); 64 | } 65 | 66 | public static void _findTransform(Transform root, string findName, ref Transform outFind, bool isContain, bool toLower) 67 | { 68 | if (outFind != null) 69 | return; 70 | 71 | string rootName = (toLower) ? root.name.ToLower() : root.name; 72 | if (rootName == findName) 73 | { 74 | outFind = root; 75 | return; 76 | } 77 | else if (isContain && rootName.Contains(findName)) 78 | { 79 | outFind = root; 80 | return; 81 | } 82 | 83 | for (int a = 0; a < root.childCount; a++) 84 | _findTransform(root.GetChild(a), findName, ref outFind, isContain, toLower); 85 | } 86 | 87 | 88 | static Mesh _dynamicHandMesh; 89 | static Mesh GetDynamicHandMesh() 90 | { 91 | if (_dynamicHandMesh == null) 92 | { 93 | Transform handCollider = GetDynamicHand(); 94 | if(handCollider!=null) 95 | _dynamicHandMesh = handCollider.GetComponent().mesh; 96 | } 97 | return _dynamicHandMesh; 98 | } 99 | 100 | [Range(0, 5)] 101 | public float dynamicHandDisDivided = 0.2f; 102 | //[Range(0, 2)] 103 | //public float dynamicHandDisThreshold = 0.3f; 104 | TextMesh _showDebug; 105 | float oldHandSize; 106 | Vector3 oldNearPoint, oldFarPoint;//, oldDirection; 107 | Quaternion oldHandRot; 108 | GameObject nearDebug, farDebug; 109 | 110 | 111 | class FindHandData : IComparable 112 | { 113 | public float cameraPlaneDis; 114 | public Vector3 vert; 115 | public int CompareTo(FindHandData other) 116 | { 117 | if (this.cameraPlaneDis < other.cameraPlaneDis) 118 | return -1; 119 | return 1; 120 | } 121 | } 122 | List findHandDataList = new List(); 123 | 124 | public Vector3 _OutNear, _OutFar; 125 | void _findHandFromVerticesUpdate2(int[] triangles, Vector3[] vertices, out Vector3 outNearPoint, out Vector3 outFarPoint, out Quaternion handRot) 126 | { 127 | Vector3 newNearPoint, newFarPoint; 128 | //MyHelpMesh.GetLineFromVertices(null, vertices, out newNearPoint, out newFarPoint); 129 | 130 | //get 10 point which is nearest with camera plane 131 | findHandDataList.Clear(); 132 | Vector3 localEyePos = SRWorksHand.Instance.viveSR.transform.InverseTransformPoint(SRWorksHand.Instance.eye.position); 133 | Vector3 localEyeDir = SRWorksHand.Instance.viveSR.transform.InverseTransformDirection(SRWorksHand.Instance.eye.forward); 134 | 135 | Vector3 cameraNormal = localEyeDir; 136 | //cameraNormal.y = 0; cameraNormal.Normalize(); 137 | Plane cameraPlane = new Plane(cameraNormal, localEyePos); 138 | 139 | foreach (Vector3 v in vertices) 140 | { 141 | //limit nearest not too high 142 | if (Mathf.Abs(v.y - localEyePos.y) > 0.4f) 143 | continue; 144 | 145 | FindHandData data = new FindHandData(); 146 | data.cameraPlaneDis = cameraPlane.GetDistanceToPoint(v); 147 | data.vert = v; 148 | findHandDataList.Add(data); 149 | } 150 | findHandDataList.Sort(); 151 | 152 | //get the closest points. 153 | float nearestDis = 99999; 154 | FindHandData nearestData = null; 155 | for (int a = 0; a < 10; a++) 156 | { 157 | if (a == findHandDataList.Count) 158 | break; 159 | float sqrDis = (findHandDataList[a].vert - localEyePos).sqrMagnitude; 160 | if (sqrDis < nearestDis) 161 | { 162 | nearestDis = sqrDis; 163 | nearestData = findHandDataList[a]; 164 | } 165 | } 166 | 167 | if (nearestData == null) 168 | { 169 | outNearPoint = oldNearPoint; 170 | outFarPoint = oldFarPoint; 171 | handRot = Quaternion.identity; 172 | return; 173 | } 174 | 175 | newNearPoint = nearestData.vert; 176 | 177 | //get 10 point which is farest with camera plane 178 | findHandDataList.Clear(); 179 | foreach (Vector3 v in vertices) 180 | { 181 | //limit farest not too high 182 | if (Mathf.Abs(v.y - localEyePos.y) > 0.5f) 183 | { 184 | continue; 185 | } 186 | 187 | FindHandData data = new FindHandData(); 188 | data.cameraPlaneDis = cameraPlane.GetDistanceToPoint(v); 189 | data.vert = v; 190 | findHandDataList.Add(data); 191 | } 192 | findHandDataList.Sort(); 193 | 194 | //get the point which is farthest from newNearPoint 195 | float maxDis = 0; 196 | newFarPoint = newNearPoint; 197 | for (int a = 0; a < findHandDataList.Count; a++) 198 | { 199 | // if (a == 10)//there are too many other point, so cannot limit the head amount 200 | // break; 201 | 202 | FindHandData data = findHandDataList[findHandDataList.Count - a - 1]; 203 | 204 | float sqrDis = (data.vert - newNearPoint).sqrMagnitude; 205 | //float dddd = (data.vert - newNearPoint).magnitude; 206 | if (sqrDis > maxDis && sqrDis < 0.5f * 0.5f) 207 | { 208 | maxDis = sqrDis; 209 | newFarPoint = data.vert; 210 | } 211 | } 212 | 213 | Vector3 newDirection = newFarPoint - newNearPoint; 214 | if (Vector3.Dot(localEyeDir, newDirection.normalized) < 0) 215 | { 216 | Vector3 rec = newNearPoint; 217 | newNearPoint = newFarPoint; 218 | newFarPoint = rec; 219 | } 220 | 221 | newNearPoint = Vector3.Lerp(oldNearPoint, newNearPoint, dynamicHandDisDivided); 222 | newFarPoint = Vector3.Lerp(oldFarPoint, newFarPoint, dynamicHandDisDivided); 223 | 224 | //save old position 225 | oldFarPoint = newFarPoint; 226 | oldNearPoint = newNearPoint; 227 | 228 | //get hand direction 229 | //Vector3 handPoint; 230 | //if (MyHelpMesh.GetLongestPointInRange(vertices, newFarPoint, 0.1f, out handPoint)) 231 | //{ 232 | // Vector3 handDir = handPoint - newFarPoint; 233 | // handDir.Normalize(); 234 | // handRot = Quaternion.LookRotation(-handDir, Vector3.up); 235 | // handRot = Quaternion.Slerp(oldHandRot, handRot, dynamicHandDisDivided); 236 | // oldHandRot = handRot; 237 | //} 238 | 239 | //get hand size in range 240 | //float handSize = 0; 241 | List handIB = new List(); 242 | List handVB = new List(); 243 | int count = 0; 244 | for (int a = 0; a < triangles.Length; a += 3) 245 | { 246 | Vector3 vA = vertices[triangles[a + 0]]; 247 | Vector3 vB = vertices[triangles[a + 1]]; 248 | Vector3 vC = vertices[triangles[a + 2]]; 249 | Vector3 dA = newFarPoint - vA; 250 | Vector3 dB = newFarPoint - vB; 251 | Vector3 dC = newFarPoint - vC; 252 | 253 | if ( 254 | dA.sqrMagnitude < handSizeRange * handSizeRange || 255 | dB.sqrMagnitude < handSizeRange * handSizeRange || 256 | dC.sqrMagnitude < handSizeRange * handSizeRange) 257 | { 258 | //get area 259 | //https://answers.unity.com/questions/291923/area-of-a-triangle-this-code-seems-to-work-why.html 260 | //Vector3 V = Vector3.Cross(vA - vB, vA - vC); 261 | // handSize += V.magnitude * 0.5f; 262 | 263 | handVB.Add(vA + SRWorksHand.Instance.viveSR.transform.position); 264 | handVB.Add(vB + SRWorksHand.Instance.viveSR.transform.position); 265 | handVB.Add(vC + SRWorksHand.Instance.viveSR.transform.position); 266 | 267 | handIB.Add(count + 0); 268 | handIB.Add(count + 1); 269 | handIB.Add(count + 2); 270 | count += 3; 271 | } 272 | } 273 | 274 | //recalculate far point 275 | if (handVB.Count > 0) 276 | { 277 | newFarPoint = Vector3.zero; 278 | foreach (Vector3 v in handVB) 279 | newFarPoint += v - SRWorksHand.Instance.viveSR.transform.position; 280 | newFarPoint /= handVB.Count; 281 | } 282 | 283 | //set point to world coordinate 284 | _OutFar = outFarPoint = newFarPoint;// + SRWorkHand.Instance.viveSR.transform.position; 285 | _OutNear = outNearPoint = newNearPoint;// + SRWorkHand.Instance.viveSR.transform.position; 286 | handRot = Quaternion.identity; 287 | 288 | if (showHandMesh) 289 | { 290 | ColliderMeshes.sharedMesh.Clear(); 291 | if (handVB.Count > 0) 292 | { 293 | ColliderMeshes.sharedMesh.SetVertices(handVB); 294 | ColliderMeshes.sharedMesh.SetIndices(handIB.ToArray(), MeshTopology.Triangles, 0); 295 | } 296 | ColliderObjs.GetComponent().enabled = true; 297 | GetDynamicHand().GetComponent().enabled = true; 298 | } 299 | else 300 | { 301 | ColliderObjs.GetComponent().enabled = false; 302 | GetDynamicHand().GetComponent().enabled = false; 303 | } 304 | 305 | _showDebug.gameObject.SetActive(false); 306 | if (Debug.isDebugBuild && DebugShow) 307 | { 308 | if (nearDebug == null) 309 | nearDebug = GameObject.CreatePrimitive(PrimitiveType.Sphere); 310 | if (farDebug == null) 311 | farDebug = GameObject.CreatePrimitive(PrimitiveType.Cube); 312 | nearDebug.transform.localScale = Vector3.one * 0.05f; 313 | farDebug.transform.localScale = Vector3.one * 0.05f; 314 | //Vector3.Lerp(Vector3.one * handSize, farDebug.transform.localScale, 0.1f); 315 | 316 | nearDebug.transform.position = outNearPoint + SRWorksHand.Instance.viveSR.transform.position; 317 | farDebug.transform.position = outFarPoint + SRWorksHand.Instance.viveSR.transform.position; 318 | nearDebug.GetComponent().material.color = Color.red; 319 | farDebug.GetComponent().material.color = Color.green; 320 | 321 | Destroy(nearDebug.GetComponent()); 322 | Destroy(farDebug.GetComponent()); 323 | 324 | float farDis = cameraPlane.GetDistanceToPoint(_OutFar); 325 | 326 | _showDebug.gameObject.SetActive(true); 327 | _showDebug.text = 328 | //"handSize : " + handSize + Environment.NewLine + 329 | "farDis : " + farDis; 330 | } 331 | } 332 | 333 | private static GameObject ColliderObjs; 334 | private static MeshFilter ColliderMeshes = new MeshFilter(); 335 | void CreateHandDetectMesh() 336 | { 337 | ColliderObjs = new GameObject("Hand Depth Collider"); 338 | ColliderObjs.transform.SetParent(gameObject.transform, false); 339 | 340 | ColliderMeshes = ColliderObjs.AddComponent(); 341 | ColliderMeshes.mesh = new Mesh(); 342 | ColliderMeshes.mesh.MarkDynamic(); 343 | 344 | MeshRenderer ColliderMeshRenderer = ColliderObjs.AddComponent(); 345 | ColliderMeshRenderer.material = handMaterial; 346 | if (handMaterial == null) { 347 | handMaterial = new Material(Shader.Find("ViveSR/Wireframe")) { 348 | color = new Color(0f, 0.94f, 0f, 0f) 349 | }; 350 | } 351 | ColliderMeshes.sharedMesh.Clear(); 352 | } 353 | 354 | bool isDetectingHand; 355 | GameObject _handObjNear, _handObjFar, _handObjArm; 356 | //Coroutine waitDetectHandCoroutine; 357 | public void SetDetectHand(GameObject handObjNear, GameObject handObjFar, GameObject handObjArm) 358 | { 359 | if (isDetectingHand) 360 | return; 361 | isDetectingHand = true; 362 | 363 | Debug.LogWarning("SetDetectHand"); 364 | SRWorksHand.OpenDynamicHandCollider(); 365 | 366 | _handObjNear = handObjNear; 367 | _handObjFar = handObjFar; 368 | _handObjArm = handObjArm; 369 | //if (waitDetectHandCoroutine != null) 370 | //{ 371 | // StopCoroutine(waitDetectHandCoroutine); 372 | // waitDetectHandCoroutine = null; 373 | //} 374 | //waitDetectHandCoroutine = StartCoroutine(WaitDetectHand(handObjNear, handObjFar, arm)); 375 | 376 | if (_showDebug == null) 377 | { 378 | _showDebug = CreateTextMeshOnHead(SRWorksHand.Instance.eye); 379 | CreateHandDetectMesh(); 380 | } 381 | } 382 | 383 | public static TextMesh CreateTextMeshOnHead(Transform head) 384 | { 385 | GameObject obj = new GameObject("TextMesh", new System.Type[] { typeof(MeshRenderer), typeof(TextMesh) }); 386 | TextMesh _showText = obj.GetComponent(); 387 | _showText.transform.parent = head; 388 | _showText.transform.localPosition = Vector3.right * -5f + Vector3.up * 1.5f + Vector3.forward * 10; 389 | _showText.transform.localRotation = Quaternion.identity; 390 | _showText.characterSize = 0.4f; 391 | //backPlane = GameObject.CreatePrimitive(PrimitiveType.Plane); 392 | //backPlane.transform.parent = _showText.transform; 393 | //Destroy(backPlane.GetComponent()); 394 | return _showText; 395 | } 396 | 397 | 398 | private void LateUpdate() 399 | { 400 | if (isDetectingHand) 401 | { 402 | if (!materialSet) { 403 | ViveSR_DualCameraDepthCollider.ChangeColliderMaterial(handMaterial); 404 | materialSet = true; 405 | } 406 | Mesh handMesh = SRWorksHand.GetDynamicHandMesh(); 407 | if (handMesh != null) 408 | { 409 | Vector3 outNearPoint, outFarPoint; 410 | Quaternion handRot = Quaternion.identity; 411 | SRWorksHand.Instance._findHandFromVerticesUpdate2(handMesh.triangles, handMesh.vertices, out outNearPoint, out outFarPoint, out handRot); 412 | if (_handObjNear != null) 413 | { 414 | _handObjNear.transform.position = outNearPoint; 415 | _handObjNear.transform.rotation = handRot; 416 | } 417 | if (_handObjFar != null) 418 | { 419 | _handObjFar.transform.position = outFarPoint; 420 | _handObjFar.transform.rotation = handRot; 421 | } 422 | if (_handObjArm != null) 423 | { 424 | _handObjArm.transform.position = outNearPoint; 425 | _handObjArm.transform.forward = outFarPoint - outNearPoint; 426 | } 427 | } 428 | } 429 | } 430 | 431 | public void CloseDetectHand() 432 | { 433 | if (!isDetectingHand) 434 | return; 435 | isDetectingHand = false; 436 | Debug.LogWarning("CloseDetectHand"); 437 | SRWorksHand.CloseDynamicHandCollider(); 438 | // StopCoroutine(waitDetectHandCoroutine); 439 | //waitDetectHandCoroutine = null; 440 | } 441 | 442 | } 443 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Scripts/SRWorksHand.cs.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 49051db3cbcaf7448a77d3c0386917ff 3 | timeCreated: 1526958090 4 | licenseType: Free 5 | MonoImporter: 6 | externalObjects: {} 7 | serializedVersion: 2 8 | defaultReferences: [] 9 | executionOrder: 0 10 | icon: {instanceID: 0} 11 | userData: 12 | assetBundleName: 13 | assetBundleVariant: 14 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Shaders.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 27fb9440139c01f44b0a67ceb417ce5b 3 | folderAsset: yes 4 | DefaultImporter: 5 | externalObjects: {} 6 | userData: 7 | assetBundleName: 8 | assetBundleVariant: 9 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Shaders/ViveSRCG.cginc: -------------------------------------------------------------------------------- 1 | #ifndef VIVESR_CG_INCLUDE 2 | #define VIVESR_CG_INCLUDE 3 | 4 | float PointOverPlane(float4 plane, float3 worldPos) 5 | { 6 | return ( dot(plane.xyz, worldPos) + plane.w ); 7 | } 8 | 9 | // --------------- 10 | // V/G/F shader struct declare 11 | // --------------- 12 | #ifdef CLIP_PLANE 13 | #define WORLD_POS_FORCLIP(idx) float3 worldPos:TEXCOORD##idx; 14 | #else 15 | #define WORLD_POS_FORCLIP(idx) 16 | #endif 17 | 18 | // --------------- 19 | // surface shader struct declare 20 | // --------------- 21 | #ifdef CLIP_PLANE 22 | #define WORLD_POS_FORCLIP_SURF float3 worldPos; 23 | #else 24 | #define WORLD_POS_FORCLIP_SURF 25 | #endif 26 | 27 | // ---------- 28 | // Variables 29 | // ---------- 30 | #ifdef CLIP_PLANE 31 | #define DECLARE_CLIP_PLANE_VARIABLE float4 _ClipPlane; 32 | #else 33 | #define DECLARE_CLIP_PLANE_VARIABLE 34 | #endif 35 | 36 | 37 | // ---------- 38 | // Function Macro 39 | // ---------- 40 | #ifdef CLIP_PLANE 41 | #define COMPUTE_CLIP_WORLD_POS(vertOut, vertInPos) vertOut.worldPos = mul(unity_ObjectToWorld, vertInPos).xyz; 42 | #else 43 | #define COMPUTE_CLIP_WORLD_POS(vertOut, vertInPos) 44 | #endif 45 | 46 | #ifdef CLIP_PLANE 47 | #define ASSIGN_CLIP_WORLD_POS_GEOSHADER(geoIn, geoOut) geoOut.worldPos = geoIn.worldPos; 48 | #else 49 | #define ASSIGN_CLIP_WORLD_POS_GEOSHADER(geoIn, geoOut) 50 | #endif 51 | 52 | #ifdef CLIP_PLANE 53 | #define CLIP_PLANE_TEST(fragIn) clip( PointOverPlane(_ClipPlane, fragIn.worldPos) ); 54 | #else 55 | #define CLIP_PLANE_TEST(fragIn) 56 | #endif 57 | 58 | #endif -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Shaders/ViveSRCG.cginc.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 4f9209cb61cfca94b9561a868e58f4a4 3 | ShaderImporter: 4 | externalObjects: {} 5 | defaultTextures: [] 6 | nonModifiableTextures: [] 7 | userData: 8 | assetBundleName: 9 | assetBundleVariant: 10 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Shaders/WireframeGeoShader.shader: -------------------------------------------------------------------------------- 1 | Shader "SRWorksHand/Wireframe" 2 | { 3 | //TODO: integrate with ViveSR/Wireframe to handle not drawing wire 4 | Properties 5 | { 6 | _Thickness ("Wire Thickness", RANGE(0, 800)) = 100 7 | _Color ("Wire Color", Color) = (0.0, 1.0, 0.0, 1.0) 8 | [Enum(Normal, 4, Always, 0)] _ZTest("Z Test Func", Float) = 4 9 | _StencilValue ("StencilRefValue", float) = 0 10 | [Enum(UnityEngine.Rendering.CompareFunction)]_StencilComp("Stencil Compare", int) = 0 // disable 11 | } 12 | 13 | SubShader 14 | { 15 | Tags { "RenderType"="Opaque" "Queue" = "Geometry-1" "LightMode"="ForwardBase"} 16 | 17 | Stencil{ 18 | Ref [_StencilValue] 19 | Comp [_StencilComp] 20 | } 21 | 22 | Pass 23 | { 24 | ZTest [_ZTest] 25 | ZWrite On 26 | ColorMask 0 27 | } 28 | 29 | GrabPass{ "_SeeThroughBeforeWireframeTex" } 30 | 31 | Pass 32 | { 33 | // http://developer.download.nvidia.com/SDK/10/direct3d/Source/SolidWireframe/Doc/SolidWireframe.pdf 34 | CGPROGRAM 35 | #pragma vertex vert 36 | #pragma geometry geom 37 | #pragma fragment frag 38 | #pragma multi_compile_fwdbase 39 | #pragma multi_compile __ CLIP_PLANE 40 | #include "UnityCG.cginc" 41 | #include "AutoLight.cginc" 42 | #include "ViveSRCG.cginc" 43 | 44 | uniform float _Thickness; 45 | uniform float4 _Color; 46 | sampler2D _SeeThroughBeforeWireframeTex; 47 | DECLARE_CLIP_PLANE_VARIABLE 48 | 49 | struct appdata 50 | { 51 | float4 vertex : POSITION; 52 | }; 53 | 54 | struct v2g 55 | { 56 | float4 cPos : SV_POSITION; 57 | WORLD_POS_FORCLIP(0) 58 | }; 59 | 60 | struct g2f 61 | { 62 | float4 pos : SV_POSITION; 63 | float3 screenPos : TEXCOORD0; 64 | float4 dist : TEXCOORD1; 65 | WORLD_POS_FORCLIP(2) 66 | SHADOW_COORDS(3) 67 | }; 68 | 69 | v2g vert (appdata v) 70 | { 71 | v2g o; 72 | o.cPos = UnityObjectToClipPos(v.vertex); 73 | COMPUTE_CLIP_WORLD_POS(o, v.vertex) 74 | return o; 75 | } 76 | 77 | [maxvertexcount(3)] 78 | void geom(triangle v2g i[3], inout TriangleStream triangleStream) 79 | { 80 | float2 p0 = i[0].cPos.xy / i[0].cPos.w; 81 | float2 p1 = i[1].cPos.xy / i[1].cPos.w; 82 | float2 p2 = i[2].cPos.xy / i[2].cPos.w; 83 | 84 | float2 edge0 = p2 - p1; 85 | float2 edge1 = p2 - p0; 86 | float2 edge2 = p1 - p0; 87 | 88 | // To find the distance to the opposite edge, we take the 89 | // formula for finding the area of a triangle Area = Base/2 * Height, 90 | // and solve for the Height = (Area * 2)/Base. 91 | // We can get the area of a triangle by taking its cross product 92 | // divided by 2. However we can avoid dividing our area/base by 2 93 | // since our cross product will already be double our area. 94 | float area = abs(edge1.x * edge2.y - edge1.y * edge2.x); 95 | float wireThickness = 1500 - _Thickness; 96 | 97 | g2f o; 98 | 99 | ASSIGN_CLIP_WORLD_POS_GEOSHADER( i[0], o ) 100 | o.pos = i[0].cPos; 101 | o.screenPos = o.pos.xyw; 102 | o.dist.xyz = float3( (area / length(edge0)), 0.0, 0.0) * o.pos.w * wireThickness; 103 | o.dist.w = 1.0 / o.pos.w; 104 | TRANSFER_SHADOW(o) 105 | triangleStream.Append(o); 106 | 107 | ASSIGN_CLIP_WORLD_POS_GEOSHADER( i[1], o ) 108 | o.pos = i[1].cPos; 109 | o.screenPos = o.pos.xyw; 110 | o.dist.xyz = float3(0.0, (area / length(edge1)), 0.0) * o.pos.w * wireThickness; 111 | o.dist.w = 1.0 / o.pos.w; 112 | TRANSFER_SHADOW(o) 113 | triangleStream.Append(o); 114 | 115 | ASSIGN_CLIP_WORLD_POS_GEOSHADER( i[2], o ) 116 | o.pos = i[2].cPos; 117 | o.screenPos = o.pos.xyw; 118 | o.dist.xyz = float3(0.0, 0.0, (area / length(edge2))) * o.pos.w * wireThickness; 119 | o.dist.w = 1.0 / o.pos.w; 120 | TRANSFER_SHADOW(o) 121 | triangleStream.Append(o); 122 | } 123 | 124 | float4 frag (g2f i) : SV_Target 125 | { 126 | CLIP_PLANE_TEST(i) 127 | 128 | float2 scrPos = i.screenPos.xy / i.screenPos.z; 129 | scrPos.x = 0.5 + scrPos.x * 0.5; 130 | scrPos.y = 0.5 - scrPos.y * 0.5; 131 | 132 | fixed shadow = SHADOW_ATTENUATION(i); 133 | 134 | //float minDistanceToEdge = min(i.dist[0], min(i.dist[1], i.dist[2])) * i.dist[3]; 135 | float4 bgColor = tex2D(_SeeThroughBeforeWireframeTex, scrPos); 136 | 137 | // Smooth our line out / or not on a line 138 | //float t = (minDistanceToEdge > 0.9) ? 0 : exp2(-2 * minDistanceToEdge * minDistanceToEdge); 139 | fixed4 finalColor = bgColor;// lerp(bgColor, _Color, t); // disable drawing wire 140 | finalColor.rgb *= shadow; 141 | 142 | return finalColor; 143 | } 144 | ENDCG 145 | } 146 | } 147 | 148 | FallBack "Standard" 149 | } 150 | -------------------------------------------------------------------------------- /Assets/ViveSRWorksHand/Shaders/WireframeGeoShader.shader.meta: -------------------------------------------------------------------------------- 1 | fileFormatVersion: 2 2 | guid: 9403751ca38f3124ba819ab433a444cc 3 | ShaderImporter: 4 | externalObjects: {} 5 | defaultTextures: [] 6 | nonModifiableTextures: [] 7 | userData: 8 | assetBundleName: 9 | assetBundleVariant: 10 | -------------------------------------------------------------------------------- /COTRIBUTING..md: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ViveSoftware/ViveSRWorksHand/1fc02a2705814d4bef917166f4dfa227366daf56/COTRIBUTING..md -------------------------------------------------------------------------------- /ProjectSettings/EditorSettings.asset: -------------------------------------------------------------------------------- 1 | %YAML 1.1 2 | %TAG !u! tag:unity3d.com,2011: 3 | --- !u!159 &1 4 | EditorSettings: 5 | m_ObjectHideFlags: 0 6 | serializedVersion: 7 7 | m_ExternalVersionControlSupport: Visible Meta Files 8 | m_SerializationMode: 2 9 | m_LineEndingsForNewScripts: 2 10 | m_DefaultBehaviorMode: 0 11 | m_SpritePackerMode: 0 12 | m_SpritePackerPaddingPower: 1 13 | m_EtcTextureCompressorBehavior: 1 14 | m_EtcTextureFastCompressor: 1 15 | m_EtcTextureNormalCompressor: 2 16 | m_EtcTextureBestCompressor: 4 17 | m_ProjectGenerationIncludedExtensions: txt;xml;fnt;cd 18 | m_ProjectGenerationRootNamespace: 19 | m_UserGeneratedProjectSuffix: 20 | m_CollabEditorSettings: 21 | inProgressEnabled: 1 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | A Vive SRWorks Hand Interaction example for Unity 2 | 3 | 4 | ![screenshot](./readme_images/screenshot.png) 5 | 6 | The example scene included shows how to occlude and interact with virtual objects (a sphere and a cube) with your hands. 7 | 8 | - In this example, by default the occlusion is using a depth mask (you can enable/disable it in the Manager object) 9 | 10 | - You can also view the hand's mesh instead of the occlusion depth mask by enabling it in the Manager object: 11 | 12 | ![Manager](./readme_images/manager.png) 13 | 14 | - To slap/punch (without going through the object) enable the HandRacketCollisionObj in the scene 15 | (you can optionally make it visible by enabling the Mesh Renderer on it) 16 | 17 | ![CollisionObj](./readme_images/CollisionObj.png) 18 | 19 | - Depth mask occlusion settings can be edited at runtime in the inspector on the DualCamera (head) object 20 | in addition to using the SRWorks settings in the game window that can be called up by pressing the S and R keys at the same time. 21 | For more info: 22 | http://community.viveport.com/t5/Vive-SRWorks-SDK/Use-Depth-Image-to-Occlude-Virtual-Objects-in-Unity/gpm-p/20707#M229 23 | 24 | Requirements: 25 | - VIVE Pro (make sure cameras are enabled and working in settings) 26 | - ViveSRWorks Unity package: Vive-SRWorks-0.7.5.0-Unity-Plugin.unitypackage or later versions. 27 | Download the latest VIVE SRWorks SDK from: http://developer.vive.com/resources 28 | 29 | UPDATE: 30 | 31 | Note 1: tested on Unity 2018.2.16f1 32 | Earlier versions of Unity had prefab issues on importing so the unity package was updated using 2017.4 but can be updated to Unity's latest release version. 33 | 34 | Note 2: as of SRWorks v0.8.0.2 the ViveSR prefab requires you to enable the modules you will be using as shown: 35 | 36 | 37 | ![ViveSR](./readme_images/ViveSR.png) 38 | 39 | -------------------------------------------------------------------------------- /readme_images/CollisionObj.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ViveSoftware/ViveSRWorksHand/1fc02a2705814d4bef917166f4dfa227366daf56/readme_images/CollisionObj.png -------------------------------------------------------------------------------- /readme_images/HandScene.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ViveSoftware/ViveSRWorksHand/1fc02a2705814d4bef917166f4dfa227366daf56/readme_images/HandScene.png -------------------------------------------------------------------------------- /readme_images/ViveSR.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ViveSoftware/ViveSRWorksHand/1fc02a2705814d4bef917166f4dfa227366daf56/readme_images/ViveSR.png -------------------------------------------------------------------------------- /readme_images/manager.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ViveSoftware/ViveSRWorksHand/1fc02a2705814d4bef917166f4dfa227366daf56/readme_images/manager.png -------------------------------------------------------------------------------- /readme_images/screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ViveSoftware/ViveSRWorksHand/1fc02a2705814d4bef917166f4dfa227366daf56/readme_images/screenshot.png --------------------------------------------------------------------------------