public void Filter(TobiiXR_EyeTrackingData data) { if (_settings.Active) { foreach (var gazeModifier in _modifiers) { gazeModifier.Modify(data, _camera.Forward); } } }
public void Tick() { _provider.Tick(); _dataHelper.CopyGazeDirection(_provider.EyeTrackingData, EyeTrackingData); if (_settings.EnableGazeModifier) { foreach (var gazeModifier in _modifiers) { _eyetrackingData = gazeModifier.Modify(EyeTrackingData, _camera.Forward); } } }
public void FilterAccuracyOnly(TobiiXR_EyeTrackingData data, Vector3 forward) { if (!enabled) { return; } if (!_settings.Active) { return; } _accuracyModifier.Modify(data, forward); }
public TobiiXR_EyeTrackingData Modify(TobiiXR_EyeTrackingData data, Vector3 forward) { var trackability = GetTrackability(data.GazeRay.Direction, forward); _queue.Enqueue(data.GazeRay.IsValid ? 1f : 0f); _queue.Dequeue(); var currentTrackability = _queue.Average(); if (data.GazeRay.IsValid) { var r = Random.Range(0f, 1f); var shouldSetToInvalid = r > trackability; if (shouldSetToInvalid && _latestValidData != null) { if (currentTrackability > trackability) { if (_invalidCount > 0) { _invalidCount--; } else { data.GazeRay.IsValid = false; data.GazeRay.Origin = _latestValidData.GazeRay.Origin; data.GazeRay.Direction = _latestValidData.GazeRay.Direction; data.IsLeftEyeBlinking = _latestValidData.IsLeftEyeBlinking; data.IsRightEyeBlinking = _latestValidData.IsRightEyeBlinking; data.ConvergenceDistance = _latestValidData.ConvergenceDistance; data.ConvergenceDistanceIsValid = _latestValidData.ConvergenceDistanceIsValid; } } } else { _latestValidData = data; } } else { if (_invalidCount < _cacheSize) { _invalidCount++; } } return(data); }
public override void Filter(TobiiXR_EyeTrackingData data, Vector3 forward) { if (!enabled) { return; } if (!_settings.Active) { return; } foreach (var gazeModifier in Modifiers) { gazeModifier.Modify(data, forward); } }
public TobiiXR_EyeTrackingData Modify(TobiiXR_EyeTrackingData data, Vector3 forward) { var combined = Modify(data.GazeRay.Direction, forward); var ret = new TobiiXR_EyeTrackingData { Timestamp = data.Timestamp, GazeRay = new TobiiXR_GazeRay() { Direction = combined, Origin = data.GazeRay.Origin, IsValid = data.GazeRay.IsValid }, ConvergenceDistance = data.ConvergenceDistance, ConvergenceDistanceIsValid = data.ConvergenceDistanceIsValid, IsLeftEyeBlinking = data.IsLeftEyeBlinking, IsRightEyeBlinking = data.IsRightEyeBlinking }; return(ret); }
public void ProcessInputs() { // Get local copies. eyeData = TobiiXR.GetEyeTrackingData(TobiiXR_TrackingSpace.Local); }
public void Modify(TobiiXR_EyeTrackingData data, Vector3 forward) { data.GazeRay.Direction = Modify(data.GazeRay.Direction, forward); }
/// <summary> /// Verifies whether the gaze ray can be used by checking its validity and the eye openness. /// </summary> /// <param name="eyeData">The eye to check validity and openness for.</param> /// <returns>True if ray is valid and eye is open.</returns> private static bool IsDirectionDataGood(TobiiXR_EyeTrackingData eyeData) { return(eyeData.GazeRay.IsValid && !eyeData.IsLeftEyeBlinking && !eyeData.IsRightEyeBlinking); }
/// <summary> /// Animate facial expression blend shapes. /// </summary> /// <param name="newDirectionL">The gaze direction for the left eye.</param> /// <param name="newDirectionR">The gaze direction for the right eye.</param> /// <param name="eyeDataLeft">Eye data for the left eye.</param> /// <param name="eyeDataRight">Eye data for the right eye.</param> private void AnimateFacialExpressions(Vector3 newDirectionL, Vector3 newDirectionR, TobiiXR_EyeTrackingData eyeData) { // Eyebrows. var leftEyeBrowBlendShapeWeight = -newDirectionL.x * EyeBrowBlendShapeHorizontalFactor + newDirectionL.y * EyeBrowBlendShapeVerticalFactor; var rightEyeBrowBlendShapeWeight = newDirectionR.x * EyeBrowBlendShapeHorizontalFactor + newDirectionR.y * EyeBrowBlendShapeVerticalFactor; _faceBlendShapes.SetBlendShapeWeight(BlendShapeLeftEyeBrowUp, leftEyeBrowBlendShapeWeight); _faceBlendShapes.SetBlendShapeWeight(BlendShapeRightEyeBrowUp, rightEyeBrowBlendShapeWeight); // If eye openness data is invalid use last value. var leftEyeClosed = eyeData.IsLeftEyeBlinking; var rightEyeClosed = eyeData.IsRightEyeBlinking; // Use a timer to filter unintentional winks. if (leftEyeClosed ^ rightEyeClosed) { _winkTimer += Time.deltaTime; } else { _winkTimer = 0; } // If eye openness has changed reset animation curve. if (leftEyeClosed != _leftEyeClosed || rightEyeClosed != _rightEyeClosed) { _animationProgress = 0; } var leftEyeBlendShapeWinkValue = (leftEyeClosed && _winkTimer > BlinkWinkTime ? BlendShapeFactor : 0); var rightEyeBlendShapeWinkValue = (rightEyeClosed && _winkTimer > BlinkWinkTime ? BlendShapeFactor : 0); _winkL = Mathf.Lerp(_winkL, leftEyeBlendShapeWinkValue, _blendShapeAnimationCurve.Evaluate(_animationProgress)); _winkR = Mathf.Lerp(_winkR, rightEyeBlendShapeWinkValue, _blendShapeAnimationCurve.Evaluate(_animationProgress)); _faceBlendShapes.SetBlendShapeWeight(BlendShapeLeftWink, _winkL); _faceBlendShapes.SetBlendShapeWeight(BlendShapeRightWink, _winkR); _teethBlendShapes.SetBlendShapeWeight(BlendShapeTeethLeftWink, _winkL); _teethBlendShapes.SetBlendShapeWeight(BlendShapeTeethRightWink, _winkR); // Cross eyed snarl. if (!leftEyeClosed && !rightEyeClosed) { var crossEyedness = Mathf.Abs(newDirectionL.x - newDirectionR.x); var crossEyedThisFrame = crossEyedness > CrossEyednessSnarlTriggerValue; if (crossEyedThisFrame != _crossEyed) { _animationProgress = 0; } _currentSnarlExtent = Mathf.Lerp(_currentSnarlExtent, crossEyedThisFrame ? crossEyedness * BlendShapeFactor : 0, _blendShapeAnimationCurve.Evaluate(_animationProgress)); _crossEyed = crossEyedThisFrame; _faceBlendShapes.SetBlendShapeWeight(BlendShapeCrossEyedSnarl, _currentSnarlExtent); } _leftEyeClosed = leftEyeClosed; _rightEyeClosed = rightEyeClosed; _animationProgress += Time.deltaTime / _blendShapeAnimationTimeSeconds; }
public void GetEyeTrackingDataLocal(TobiiXR_EyeTrackingData data) { EyeTrackingDataHelper.Copy(_eyeTrackingDataLocal, data); }
public StringBuilder StartTracking(String time, int frameCount, StringBuilder csvLogger) { // Get Eye data from TOBI API TobiiXR_EyeTrackingData localEyeData = TobiiXR.GetEyeTrackingData(TobiiXR_TrackingSpace.Local); TobiiXR_EyeTrackingData worldEyeData = TobiiXR.GetEyeTrackingData(TobiiXR_TrackingSpace.World); // Get Eye data from SRNipal ViveSR.Error error = SRanipal_Eye_API.GetEyeData(ref _eyeData); if (error == Error.WORK) { _sRanipalEyeVerboseData = _eyeData.verbose_data; // Left Eye Data SingleEyeData sRleftEyeData = _sRanipalEyeVerboseData.left; // Right Eye SingleEyeData sRrightEyeData = _sRanipalEyeVerboseData.right; // Write in the CSV file csvLogger.AppendFormat( "{0}, {1}, {2}, {3}, {4}, {5}, {6}, {7}, {8}, {9}, {10}, {11}, {12}, {13}, {14}, {15}, {16}, {17}, {18}," + "{19}, {20}, {21}, {22}, {23}, {24}, {25},{26}, {27}, {28}, {29}, {30}, {31}, {32}, {33}, {34}, {35}," + "{36}, {37}, {38}, {39}", // Time and Frame count time, frameCount, // Convergence Distance worldEyeData.ConvergenceDistanceIsValid, worldEyeData.ConvergenceDistance, // Eye Openness sRleftEyeData.eye_openness, sRrightEyeData.eye_openness, // Eye blinking localEyeData.IsLeftEyeBlinking, localEyeData.IsRightEyeBlinking, // Pupil Diameter sRleftEyeData.pupil_diameter_mm, sRrightEyeData.pupil_diameter_mm, // Pupil Position in Sensor area (x, y) sRleftEyeData.pupil_position_in_sensor_area.x, sRleftEyeData.pupil_position_in_sensor_area.y, sRrightEyeData.pupil_position_in_sensor_area.x, sRrightEyeData.pupil_position_in_sensor_area.y, // IS local Gaze Valid localEyeData.GazeRay.IsValid, // Local Space Gaze Origin Combined localEyeData.GazeRay.Origin.x, localEyeData.GazeRay.Origin.y, localEyeData.GazeRay.Origin.z, // Local Space Gaze Direction Combined localEyeData.GazeRay.Direction.x, localEyeData.GazeRay.Direction.y, localEyeData.GazeRay.Direction.z, // IS World Gaze Valid worldEyeData.GazeRay.IsValid, //world space Gaze Origin Combined worldEyeData.GazeRay.Origin.x, worldEyeData.GazeRay.Origin.y, worldEyeData.GazeRay.Origin.z, // world space Gaze Direction Combined worldEyeData.GazeRay.Direction.x, worldEyeData.GazeRay.Direction.y, worldEyeData.GazeRay.Direction.z, // Gaze Origin in mm sRleftEyeData.gaze_origin_mm.x, sRleftEyeData.gaze_origin_mm.y, sRleftEyeData.gaze_origin_mm.z, sRrightEyeData.gaze_origin_mm.x, sRrightEyeData.gaze_origin_mm.y, sRrightEyeData.gaze_origin_mm.z, // Normalized Gaze direction sRleftEyeData.gaze_direction_normalized.x, sRleftEyeData.gaze_direction_normalized.y, sRleftEyeData.gaze_direction_normalized.z, sRrightEyeData.gaze_direction_normalized.x, sRrightEyeData.gaze_direction_normalized.y, sRrightEyeData.gaze_direction_normalized.z ); csvLogger.AppendLine(); } return(csvLogger); }
public void FilterAccuracyOnly(TobiiXR_EyeTrackingData data) { _accuracyModifier.Modify(data, _camera.Forward); }
public HTCProvider() { EyeTrackingData = new TobiiXR_EyeTrackingData(); _hmdToWorldTransformer = new HmdToWorldTransformer(estimatedEyeTrackerLatency_s: 0.040f); EnsureHTCFrameworkRunning(); }
public HTCProvider() { EyeTrackingData = new TobiiXR_EyeTrackingData(); _hmdToWorldTransformer = new HmdToWorldTransformer(historyCapacity: 11); EnsureHTCFrameworkRunning(); }