internal static void HMDWritePose(this XmlWriter file, EyeTrackerOriginPose pose) { file.WriteStartElement("Pose"); file.WriteAttributeString("Position", pose.Position.ToString(FORMAT_FLOAT)); file.WriteAttributeString("Rotation", pose.Rotation.ToString(FORMAT_FLOAT)); file.WriteAttributeString("Valid", pose.Valid.ToString()); file.WriteEndElement(); }
internal void Add(EyeTrackerOriginPose pose) { // Save the current pose for the current time. _list.Add(pose); while (_list.Count > _maxCount) { _list.RemoveAt(0); } }
internal VRGazeData(HMDGazeDataEventArgs originalGaze, EyeTrackerOriginPose pose) { Pose = pose; var eyeTrackerOrigin = VRUtility.TemporaryTransformWithAppliedPose(pose); Left = new GazeDataEye(originalGaze.LeftEye, eyeTrackerOrigin); Right = new GazeDataEye(originalGaze.RightEye, eyeTrackerOrigin); var combinedDirection = ((Left.GazeDirection + Right.GazeDirection) / 2f).normalized; var combinedOrigin = (Left.GazeOrigin + Right.GazeOrigin) / 2f; CombinedGazeRayWorld = new Ray(eyeTrackerOrigin.TransformPoint(combinedOrigin), eyeTrackerOrigin.TransformDirection(combinedDirection)); CombinedGazeRayWorldValid = Left.GazeRayWorldValid && Right.GazeRayWorldValid; OriginalGaze = originalGaze; }
/// <summary> /// Look up the best matching pose corresponding to the provided time stamp. /// If the list is empty, an invalid pose will be returned. /// If the time stamp is: /// - before the first pose, the first pose will be returned. /// - after the last pose, the last pose will be returned. /// - a perfect match, the corresponding pose will be returned. /// - between two poses, the interpolated pose will be returned. /// </summary> /// <param name="timeStamp">The gaze time stamp in the system clock</param> /// <returns>The best matching pose</returns> internal EyeTrackerOriginPose GetBestMatchingPose(long timeStamp) { var comparer = new EyeTrackerOriginPose(timeStamp); var index = _list.BinarySearch(comparer); if (_list.Count == 0) { // No poses to compare. Return invalid object. return(comparer); } if (index < 0) { // No direct hit. This should be the common case. // Bitwise complement gives the index of the next larger item. index = ~index; if (index > 0) { if (index == _list.Count) { // There is no larger time stamp. Return the last item. return(_list[_list.Count - 1]); } // Interpolate a new pose and return it. return(_list[index - 1].Interpolate(_list[index], timeStamp)); } // If index is zero, then the time stamp we provided is before // the first item in the poses list. This is normally long ago. // Anyway, return the first item. return(_list[0]); } // Direct hit. Could happen, but should be very rare. return(_list[index]); }
internal static Transform ApplyPose(this Transform transform, EyeTrackerOriginPose pose) { transform.position = pose.Position; transform.rotation = pose.Rotation; return(transform); }
/// <summary> /// Get a <see cref="Transform"/> object with the provided pose applied. /// It is temporary since it will change to then next provided pose on /// the next call, or by direct manipulation. /// </summary> /// <param name="pose">The pose to apply</param> /// <returns>The temporary transform</returns> internal static Transform TemporaryTransformWithAppliedPose(EyeTrackerOriginPose pose) { return(_historicalEyeTrackerOrigin.ApplyPose(pose)); }