2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
									
										
										
										
											2019-01-01 12:46:36 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								/*  mobile_vr_interface.cpp                                              */  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                       This file is part of:                           */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                           GODOT ENGINE                                */  
						 
					
						
							
								
									
										
										
										
											2018-01-05 00:50:27 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								/*                      https://godotengine.org                          */  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
									
										
										
										
											2021-01-01 20:13:46 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								/* Copyright (c) 2007-2021 Juan Linietsky, Ariel Manzur.                 */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* Copyright (c) 2014-2021 Godot Engine contributors (cf. AUTHORS.md).   */  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*                                                                       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* Permission is hereby granted, free of charge, to any person obtaining */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* a copy of this software and associated documentation files (the       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* "Software"), to deal in the Software without restriction, including   */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* without limitation the rights to use, copy, modify, merge, publish,   */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* distribute, sublicense, and/or sell copies of the Software, and to    */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* permit persons to whom the Software is furnished to do so, subject to */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* the following conditions:                                             */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                                                                       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* The above copyright notice and this permission notice shall be        */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* included in all copies or substantial portions of the Software.       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                                                                       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF    */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY  */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,  */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE     */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.                */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-07-27 18:43:50 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "mobile_vr_interface.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-04-28 15:19:37 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "core/input/input.h" 
  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								# include  "core/os/os.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-03-03 10:36:29 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "servers/display_server.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-03-27 15:21:27 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "servers/rendering/rendering_server_globals.h" 
  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								StringName  MobileVRInterface : : get_name ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  " Native mobile " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-09-29 21:36:27 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  MobileVRInterface : : get_capabilities ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  XRInterface : : XR_STEREO ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-29 21:36:27 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								Vector3  MobileVRInterface : : scale_magneto ( const  Vector3  & p_magnetometer )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Our magnetometer doesn't give us nice clean data.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Well it may on Mac OS X because we're getting a calibrated value in the current implementation but Android we're getting raw data.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// This is a fairly simple adjustment we can do to correct for the magnetometer data being elliptical
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  mag_raw  =  p_magnetometer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  mag_scaled  =  p_magnetometer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// update our variables every x frames
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( mag_count  >  20 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_current_min  =  mag_next_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_current_max  =  mag_next_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_count  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_count + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// adjust our min and max
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( mag_raw . x  >  mag_next_max . x )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mag_next_max . x  =  mag_raw . x ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( mag_raw . y  >  mag_next_max . y )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mag_next_max . y  =  mag_raw . y ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( mag_raw . z  >  mag_next_max . z )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mag_next_max . z  =  mag_raw . z ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( mag_raw . x  <  mag_next_min . x )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mag_next_min . x  =  mag_raw . x ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( mag_raw . y  <  mag_next_min . y )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mag_next_min . y  =  mag_raw . y ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( mag_raw . z  <  mag_next_min . z )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mag_next_min . z  =  mag_raw . z ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// scale our x, y and z
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! ( mag_current_max . x  -  mag_current_min . x ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_raw . x  - =  ( mag_current_min . x  +  mag_current_max . x )  /  2.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_scaled . x  =  ( mag_raw . x  -  mag_current_min . x )  /  ( ( mag_current_max . x  -  mag_current_min . x )  *  2.0  -  1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! ( mag_current_max . y  -  mag_current_min . y ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_raw . y  - =  ( mag_current_min . y  +  mag_current_max . y )  /  2.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_scaled . y  =  ( mag_raw . y  -  mag_current_min . y )  /  ( ( mag_current_max . y  -  mag_current_min . y )  *  2.0  -  1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! ( mag_current_max . z  -  mag_current_min . z ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_raw . z  - =  ( mag_current_min . z  +  mag_current_max . z )  /  2.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_scaled . z  =  ( mag_raw . z  -  mag_current_min . z )  /  ( ( mag_current_max . z  -  mag_current_min . z )  *  2.0  -  1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  mag_scaled ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Basis  MobileVRInterface : : combine_acc_mag ( const  Vector3  & p_grav ,  const  Vector3  & p_magneto )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// yup, stock standard cross product solution...
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  up  =  - p_grav . normalized ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  magneto_east  =  up . cross ( p_magneto . normalized ( ) ) ;  // or is this west?, but should be horizon aligned now
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									magneto_east . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  magneto  =  up . cross ( magneto_east ) ;  // and now we have a horizon aligned north
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									magneto . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// We use our gravity and magnetometer vectors to construct our matrix
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Basis  acc_mag_m3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									acc_mag_m3 . elements [ 0 ]  =  - magneto_east ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									acc_mag_m3 . elements [ 1 ]  =  up ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									acc_mag_m3 . elements [ 2 ]  =  magneto ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  acc_mag_m3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_position_from_sensors ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_THREAD_SAFE_METHOD_ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// this is a helper function that attempts to adjust our transform using our 9dof sensors
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// 9dof is a misleading marketing term coming from 3 accelerometer axis + 3 gyro axis + 3 magnetometer axis = 9 axis
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// but in reality this only offers 3 dof (yaw, pitch, roll) orientation
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint64_t  ticks  =  OS : : get_singleton ( ) - > get_ticks_usec ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint64_t  ticks_elapsed  =  ticks  -  last_ticks ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									float  delta_time  =  ( double ) ticks_elapsed  /  1000000.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// few things we need
 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-28 15:19:37 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Input  * input  =  Input : : get_singleton ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector3  down ( 0.0 ,  - 1.0 ,  0.0 ) ;  // Down is Y negative
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  north ( 0.0 ,  0.0 ,  1.0 ) ;  // North is Z positive
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// make copies of our inputs
 
							 
						 
					
						
							
								
									
										
										
										
											2017-11-08 12:09:43 +11:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  has_grav  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector3  acc  =  input - > get_accelerometer ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  gyro  =  input - > get_gyroscope ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  grav  =  input - > get_gravity ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  magneto  =  scale_magneto ( input - > get_magnetometer ( ) ) ;  // this may be overkill on iOS because we're already getting a calibrated magnetometer reading
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( sensor_first )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sensor_first  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										acc  =  scrub ( acc ,  last_accerometer_data ,  2 ,  0.2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										magneto  =  scrub ( magneto ,  last_magnetometer_data ,  3 ,  0.3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									last_accerometer_data  =  acc ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									last_magnetometer_data  =  magneto ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( grav . length ( )  <  0.1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// not ideal but use our accelerometer, this will contain shakey shakey user behaviour
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// maybe look into some math but I'm guessing that if this isn't available, its because we lack the gyro sensor to actually work out
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// what a stable gravity vector is
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										grav  =  acc ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( grav . length ( )  >  0.1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-11-08 12:09:43 +11:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											has_grav  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-11-08 12:09:43 +11:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										has_grav  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  has_magneto  =  magneto . length ( )  >  0.1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-11-08 12:09:43 +11:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( gyro . length ( )  >  0.1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										/* this can return to 0.0 if the user doesn't move the phone, so once on, it's on */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										has_gyro  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( has_gyro )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// start with applying our gyro (do NOT smooth our gyro!)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Basis  rotate ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rotate . rotate ( orientation . get_axis ( 0 ) ,  gyro . x  *  delta_time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rotate . rotate ( orientation . get_axis ( 1 ) ,  gyro . y  *  delta_time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rotate . rotate ( orientation . get_axis ( 2 ) ,  gyro . z  *  delta_time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										orientation  =  rotate  *  orientation ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-29 21:36:27 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										tracking_state  =  XRInterface : : XR_NORMAL_TRACKING ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									///@TODO improve this, the magnetometer is very fidgity sometimes flipping the axis for no apparent reason (probably a bug on my part)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// if you have a gyro + accelerometer that combo tends to be better then combining all three but without a gyro you need the magnetometer..
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( has_magneto  & &  has_grav  & &  ! has_gyro )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// convert to quaternions, easier to smooth those out
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Quat  transform_quat ( orientation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Quat  acc_mag_quat ( combine_acc_mag ( grav ,  magneto ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										transform_quat  =  transform_quat . slerp ( acc_mag_quat ,  0.1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										orientation  =  Basis ( transform_quat ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-29 21:36:27 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										tracking_state  =  XRInterface : : XR_NORMAL_TRACKING ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									}  else  if  ( has_grav )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// use gravity vector to make sure down is down...
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// transform gravity into our world space
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										grav . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  grav_adj  =  orientation . xform ( grav ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  dot  =  grav_adj . dot ( down ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ( dot  >  - 1.0 )  & &  ( dot  <  1.0 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// axis around which we have this rotation
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector3  axis  =  grav_adj . cross ( down ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											axis . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Basis  drift_compensation ( axis ,  acos ( dot )  *  delta_time  *  10 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											orientation  =  drift_compensation  *  orientation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// JIC
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									orientation . orthonormalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									last_ticks  =  ticks ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : _bind_methods ( )  {  
						 
					
						
							
								
									
										
										
										
											2019-04-10 00:14:10 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_eye_height " ,  " eye_height " ) ,  & MobileVRInterface : : set_eye_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_eye_height " ) ,  & MobileVRInterface : : get_eye_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_iod " ,  " iod " ) ,  & MobileVRInterface : : set_iod ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_iod " ) ,  & MobileVRInterface : : get_iod ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_display_width " ,  " display_width " ) ,  & MobileVRInterface : : set_display_width ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_display_width " ) ,  & MobileVRInterface : : get_display_width ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_display_to_lens " ,  " display_to_lens " ) ,  & MobileVRInterface : : set_display_to_lens ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_display_to_lens " ) ,  & MobileVRInterface : : get_display_to_lens ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_oversample " ,  " oversample " ) ,  & MobileVRInterface : : set_oversample ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_oversample " ) ,  & MobileVRInterface : : get_oversample ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_k1 " ,  " k " ) ,  & MobileVRInterface : : set_k1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_k1 " ) ,  & MobileVRInterface : : get_k1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_k2 " ,  " k " ) ,  & MobileVRInterface : : set_k2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_k2 " ) ,  & MobileVRInterface : : get_k2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
											
												Variant: Added 64-bit packed arrays, renamed Variant::REAL to FLOAT.
- Renames PackedIntArray to PackedInt32Array.
- Renames PackedFloatArray to PackedFloat32Array.
- Adds PackedInt64Array and PackedFloat64Array.
- Renames Variant::REAL to Variant::FLOAT for consistency.
Packed arrays are for storing large amount of data and creating stuff like
meshes, buffers. textures, etc. Forcing them to be 64 is a huge waste of
memory. That said, many users requested the ability to have 64 bits packed
arrays for their games, so this is just an optional added type.
For Variant, the float datatype is always 64 bits, and exposed as `float`.
We still have `real_t` which is the datatype that can change from 32 to 64
bits depending on a compile flag (not entirely working right now, but that's
the idea). It affects math related datatypes and code only.
Neither Variant nor PackedArray make use of real_t, which is only intended
for math precision, so the term is removed from there to keep only float.
											 
										 
										
											2020-02-24 15:20:53 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " eye_height " ,  PROPERTY_HINT_RANGE ,  " 0.0,3.0,0.1 " ) ,  " set_eye_height " ,  " get_eye_height " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " iod " ,  PROPERTY_HINT_RANGE ,  " 4.0,10.0,0.1 " ) ,  " set_iod " ,  " get_iod " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " display_width " ,  PROPERTY_HINT_RANGE ,  " 5.0,25.0,0.1 " ) ,  " set_display_width " ,  " get_display_width " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " display_to_lens " ,  PROPERTY_HINT_RANGE ,  " 5.0,25.0,0.1 " ) ,  " set_display_to_lens " ,  " get_display_to_lens " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " oversample " ,  PROPERTY_HINT_RANGE ,  " 1.0,2.0,0.1 " ) ,  " set_oversample " ,  " get_oversample " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " k1 " ,  PROPERTY_HINT_RANGE ,  " 0.1,10.0,0.0001 " ) ,  " set_k1 " ,  " get_k1 " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " k2 " ,  PROPERTY_HINT_RANGE ,  " 0.1,10.0,0.0001 " ) ,  " set_k2 " ,  " get_k2 " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-10 00:14:10 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_eye_height ( const  real_t  p_eye_height )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									eye_height  =  p_eye_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								real_t  MobileVRInterface : : get_eye_height ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  eye_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_iod ( const  real_t  p_iod )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									intraocular_dist  =  p_iod ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								real_t  MobileVRInterface : : get_iod ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  intraocular_dist ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_display_width ( const  real_t  p_display_width )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									display_width  =  p_display_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								real_t  MobileVRInterface : : get_display_width ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  display_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_display_to_lens ( const  real_t  p_display_to_lens )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									display_to_lens  =  p_display_to_lens ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								real_t  MobileVRInterface : : get_display_to_lens ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  display_to_lens ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_oversample ( const  real_t  p_oversample )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									oversample  =  p_oversample ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								real_t  MobileVRInterface : : get_oversample ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  oversample ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_k1 ( const  real_t  p_k1 )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									k1  =  p_k1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								real_t  MobileVRInterface : : get_k1 ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  k1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : set_k2 ( const  real_t  p_k2 )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									k2  =  p_k2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								real_t  MobileVRInterface : : get_k2 ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  k2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								bool  MobileVRInterface : : is_stereo ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// needs stereo...
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-07-27 18:43:50 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								bool  MobileVRInterface : : is_initialized ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  ( initialized ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								bool  MobileVRInterface : : initialize ( )  {  
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									XRServer  * xr_server  =  XRServer : : get_singleton ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V ( xr_server ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! initialized )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// reset our sensor data and orientation
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_count  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										has_gyro  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sensor_first  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_next_min  =  Vector3 ( 10000 ,  10000 ,  10000 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_next_max  =  Vector3 ( - 10000 ,  - 10000 ,  - 10000 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_current_min  =  Vector3 ( 0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mag_current_max  =  Vector3 ( 0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// reset our orientation
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										orientation  =  Basis ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// make this our primary interface
 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										xr_server - > set_primary_interface ( this ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										last_ticks  =  OS : : get_singleton ( ) - > get_ticks_usec ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-16 20:42:47 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										initialized  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : uninitialize ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( initialized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										XRServer  * xr_server  =  XRServer : : get_singleton ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( xr_server  ! =  nullptr )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											// no longer our primary interface
 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											xr_server - > clear_primary_interface_if ( this ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										initialized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-11-04 11:50:05 +11:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Size2  MobileVRInterface : : get_render_targetsize ( )  {  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									_THREAD_SAFE_METHOD_ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// we use half our window size
 
							 
						 
					
						
							
								
									
										
										
										
											2020-03-03 10:36:29 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Size2  target_size  =  DisplayServer : : get_singleton ( ) - > window_get_size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-10 00:14:10 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									target_size . x  * =  0.5  *  oversample ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									target_size . y  * =  oversample ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  target_size ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Transform  MobileVRInterface : : get_transform_for_eye ( XRInterface : : Eyes  p_eye ,  const  Transform  & p_cam_transform )  {  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									_THREAD_SAFE_METHOD_ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Transform  transform_for_eye ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									XRServer  * xr_server  =  XRServer : : get_singleton ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V ( xr_server ,  transform_for_eye ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( initialized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										float  world_scale  =  xr_server - > get_world_scale ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-01-18 21:37:17 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// we don't need to check for the existence of our HMD, doesn't effect our values...
 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										// note * 0.01 to convert cm to m and * 0.5 as we're moving half in each direction...
 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_eye  = =  XRInterface : : EYE_LEFT )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											transform_for_eye . origin . x  =  - ( intraocular_dist  *  0.01  *  0.5  *  world_scale ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  if  ( p_eye  = =  XRInterface : : EYE_RIGHT )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											transform_for_eye . origin . x  =  intraocular_dist  *  0.01  *  0.5  *  world_scale ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// for mono we don't reposition, we want our center position.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// just scale our origin point of our transform
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Transform  hmd_transform ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										hmd_transform . basis  =  orientation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										hmd_transform . origin  =  Vector3 ( 0.0 ,  eye_height  *  world_scale ,  0.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										transform_for_eye  =  p_cam_transform  *  ( xr_server - > get_reference_frame ( ) )  *  hmd_transform  *  transform_for_eye ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// huh? well just return what we got....
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										transform_for_eye  =  p_cam_transform ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  transform_for_eye ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								CameraMatrix  MobileVRInterface : : get_projection_for_eye ( XRInterface : : Eyes  p_eye ,  real_t  p_aspect ,  real_t  p_z_near ,  real_t  p_z_far )  {  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									_THREAD_SAFE_METHOD_ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CameraMatrix  eye ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_eye  = =  XRInterface : : EYE_MONO )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										///@TODO for now hardcode some of this, what is really needed here is that this needs to be in sync with the real cameras properties
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// which probably means implementing a specific class for iOS and Android. For now this is purely here as an example.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Note also that if you use a normal viewport with AR/VR turned off you can still use the tracker output of this interface
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// to position a stock standard Godot camera and have control over this.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// This will make more sense when we implement ARkit on iOS (probably a separate interface).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										eye . set_perspective ( 60.0 ,  p_aspect ,  p_z_near ,  p_z_far ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										eye . set_for_hmd ( p_eye  = =  XRInterface : : EYE_LEFT  ?  1  :  2 ,  p_aspect ,  intraocular_dist ,  display_width ,  display_to_lens ,  oversample ,  p_z_near ,  p_z_far ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  eye ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  MobileVRInterface : : commit_for_eye ( XRInterface : : Eyes  p_eye ,  RID  p_render_target ,  const  Rect2  & p_screen_rect )  {  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									_THREAD_SAFE_METHOD_ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// We must have a valid render target
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! p_render_target . is_valid ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Because we are rendering to our device we must use our main viewport!
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( p_screen_rect  = =  Rect2 ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-10-01 06:51:50 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rect2  dest  =  p_screen_rect ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector2  eye_center ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-10-01 06:51:50 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// we output half a screen
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									dest . size . x  * =  0.5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_eye  = =  XRInterface : : EYE_LEFT )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										eye_center . x  =  ( ( - intraocular_dist  /  2.0 )  +  ( display_width  /  4.0 ) )  /  ( display_width  /  2.0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-09 00:47:36 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( p_eye  = =  XRInterface : : EYE_RIGHT )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-01 06:51:50 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										dest . position . x  =  dest . size . x ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										eye_center . x  =  ( ( intraocular_dist  /  2.0 )  -  ( display_width  /  4.0 ) )  /  ( display_width  /  2.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-01 06:51:50 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// we don't offset the eye center vertically (yet)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									eye_center . y  =  0.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-06-15 23:45:24 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  MobileVRInterface : : process ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_THREAD_SAFE_METHOD_ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( initialized )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										set_position_from_sensors ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								MobileVRInterface : : MobileVRInterface ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									initialized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Just set some defaults for these. At some point we need to look at adding a lookup table for common device + headset combos and/or support reading cardboard QR codes
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									eye_height  =  1.85 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									intraocular_dist  =  6.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-29 21:36:27 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									display_width  =  14.5 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									display_to_lens  =  4.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									oversample  =  1.5 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-29 21:36:27 +10:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									k1  =  0.215 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									k2  =  0.215 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-28 22:15:21 +10:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									last_ticks  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								MobileVRInterface : : ~ MobileVRInterface ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// and make sure we cleanup if we haven't already
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( is_initialized ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uninitialize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;