aboutsummaryrefslogtreecommitdiff
path: root/src/argaze.test/GazeAnalysis
diff options
context:
space:
mode:
authorThéo de la Hogue2023-05-31 16:02:47 +0200
committerThéo de la Hogue2023-05-31 16:02:47 +0200
commitf861c25ed56bf3204188ecc9170feb21e613794e (patch)
treeee33496bca71bcc0d6ba669c1175b0c0505fefc2 /src/argaze.test/GazeAnalysis
parente35e90d161ffb9202459631a0049448cde905b3c (diff)
downloadargaze-f861c25ed56bf3204188ecc9170feb21e613794e.zip
argaze-f861c25ed56bf3204188ecc9170feb21e613794e.tar.gz
argaze-f861c25ed56bf3204188ecc9170feb21e613794e.tar.bz2
argaze-f861c25ed56bf3204188ecc9170feb21e613794e.tar.xz
Don't ignore last movement on invalid gaze position.
Diffstat (limited to 'src/argaze.test/GazeAnalysis')
-rw-r--r--src/argaze.test/GazeAnalysis/DispersionThresholdIdentification.py79
1 files changed, 41 insertions, 38 deletions
diff --git a/src/argaze.test/GazeAnalysis/DispersionThresholdIdentification.py b/src/argaze.test/GazeAnalysis/DispersionThresholdIdentification.py
index dc4284c..712308a 100644
--- a/src/argaze.test/GazeAnalysis/DispersionThresholdIdentification.py
+++ b/src/argaze.test/GazeAnalysis/DispersionThresholdIdentification.py
@@ -16,13 +16,15 @@ from argaze.GazeAnalysis import DispersionThresholdIdentification
import numpy
-def build_gaze_fixation(size: int, center: tuple, deviation_max: float, start_time: float, min_time: float, max_time: float, validity: list = []):
+def build_gaze_fixation(size: int, center: tuple, deviation_max: float, min_time: float, max_time: float, start_ts: float = 0., validity: list = []):
""" Generate N TimeStampedGazePsoitions dispersed around a center point for testing purpose.
Timestamps are current time after random sleep (second).
GazePositions are random values.
"""
ts_gaze_positions = GazeFeatures.TimeStampedGazePositions()
+ start_time = time.time()
+
for i in range(0, size):
# Check position validity
@@ -43,7 +45,7 @@ def build_gaze_fixation(size: int, center: tuple, deviation_max: float, start_ti
gaze_position = GazeFeatures.UnvalidGazePosition()
# Store gaze position
- ts = time.time() - start_time
+ ts = time.time() - start_time + start_ts
ts_gaze_positions[ts] = gaze_position
# Sleep a random time
@@ -52,13 +54,15 @@ def build_gaze_fixation(size: int, center: tuple, deviation_max: float, start_ti
return ts_gaze_positions
-def build_gaze_saccade(size: int, center_A: tuple, center_B: tuple, start_time: float, min_time: float, max_time: float, validity: list = []):
+def build_gaze_saccade(size: int, center_A: tuple, center_B: tuple, min_time: float, max_time: float, start_ts: float = 0., validity: list = []):
""" Generate N TimeStampedGazePsoitions between 2 center points for testing purpose.
Timestamps are current time after random sleep (second).
GazePositions are random values.
"""
ts_gaze_positions = GazeFeatures.TimeStampedGazePositions()
+ start_time = time.time()
+
for i in range(0, size):
# Check position validity
@@ -79,7 +83,7 @@ def build_gaze_saccade(size: int, center_A: tuple, center_B: tuple, start_time:
gaze_position = GazeFeatures.UnvalidGazePosition()
# Store gaze position
- ts = time.time() - start_time
+ ts = time.time() - start_time + start_ts
ts_gaze_positions[ts] = gaze_position
# Sleep a random time
@@ -97,11 +101,10 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
size = 10
center = (0, 0)
deviation_max = 10
- start_time = time.time()
min_time = 0.01
max_time = 0.1
- ts_gaze_positions = build_gaze_fixation(size, center, deviation_max, start_time, min_time, max_time)
+ ts_gaze_positions = build_gaze_fixation(size, center, deviation_max, min_time, max_time)
gaze_movement_identifier = DispersionThresholdIdentification.GazeMovementIdentifier(deviation_max_threshold=deviation_max, duration_min_threshold=max_time*2)
ts_fixations, ts_saccades, ts_status = gaze_movement_identifier.browse(ts_gaze_positions)
@@ -125,12 +128,11 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
center_A = (0, 0)
center_B = (50, 50)
deviation_max = 10
- start_time = time.time()
min_time = 0.01
max_time = 0.1
- ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, start_time, min_time, max_time)
- ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, start_time, min_time, max_time)
+ ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, min_time, max_time)
+ ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, min_time, max_time, start_ts=ts_gaze_positions_A.last[0])
ts_gaze_positions = ts_gaze_positions_A.append(ts_gaze_positions_B)
@@ -164,7 +166,7 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
self.assertLessEqual(fixation.deviation_max, deviation_max)
self.assertGreaterEqual(fixation.duration, size * min_time)
self.assertLessEqual(fixation.duration, size * max_time)
- '''
+
def test_fixation_and_short_saccade_identification(self):
"""Test DispersionThresholdIdentification fixation and saccade identification."""
@@ -174,15 +176,12 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
out_A = (20, 20)
center_B = (50, 50)
deviation_max = 10
- start_time = time.time()
min_time = 0.01
max_time = 0.1
- ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, start_time, min_time, max_time)
- ts_move_positions = build_gaze_saccade(move, out_A, center_B, start_time, min_time, min_time)
- ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, start_time, min_time, max_time)
-
- print(ts_move_positions)
+ ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, min_time, max_time)
+ ts_move_positions = build_gaze_saccade(move, out_A, center_B, min_time, min_time, start_ts=ts_gaze_positions_A.last[0])
+ ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, min_time, max_time, start_ts=ts_move_positions.last[0])
ts_gaze_positions = ts_gaze_positions_A.append(ts_move_positions).append(ts_gaze_positions_B)
@@ -197,7 +196,7 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
# Check first fixation
ts, fixation = ts_fixations.pop_first()
- self.assertEqual(len(fixation.positions.keys()), size-1)
+ self.assertEqual(len(fixation.positions.keys()), size)
self.assertLessEqual(fixation.deviation_max, deviation_max)
self.assertGreaterEqual(fixation.duration, size * min_time)
self.assertLessEqual(fixation.duration, size * max_time)
@@ -205,48 +204,54 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
# Check first saccade
ts, saccade = ts_saccades.pop_first()
- self.assertEqual(len(saccade.positions.keys()), move + 2)
+ self.assertEqual(len(saccade.positions.keys()), move)
self.assertGreaterEqual(saccade.duration, min_time)
self.assertLessEqual(saccade.duration, max_time)
# Check second fixation
ts, fixation = ts_fixations.pop_first()
- self.assertEqual(len(fixation.positions.keys()), size-1)
+ self.assertEqual(len(fixation.positions.keys()), size)
self.assertLessEqual(fixation.deviation_max, deviation_max)
self.assertGreaterEqual(fixation.duration, size * min_time)
self.assertLessEqual(fixation.duration, size * max_time)
- '''
+
def test_invalid_gaze_position(self):
"""Test DispersionThresholdIdentification fixation and saccade identification with invalid gaze position."""
size = 15
center = (0, 0)
deviation_max = 10
- start_time = time.time()
- min_time = 0.01
+ min_time = 0.05
max_time = 0.1
- validity = [True, True, True, True, False, True, True, True, False, False, True, True, True, True, True]
+ validity = [True, True, True, True, True, True, True, False, False, False, True, True, True, True, True]
- ts_gaze_positions = build_gaze_fixation(size, center, deviation_max, start_time, min_time, max_time, validity)
+ ts_gaze_positions = build_gaze_fixation(size, center, deviation_max, min_time, max_time, validity=validity)
gaze_movement_identifier = DispersionThresholdIdentification.GazeMovementIdentifier(deviation_max_threshold=deviation_max, duration_min_threshold=max_time*2)
ts_fixations, ts_saccades, ts_status = gaze_movement_identifier.browse(ts_gaze_positions)
# Check result size
- self.assertEqual(len(ts_fixations), 1)
+ self.assertEqual(len(ts_fixations), 2)
self.assertEqual(len(ts_saccades), 0)
self.assertEqual(len(ts_status), size-3)
- # Check fixation
+ # Check first fixation
ts, fixation = ts_fixations.pop_first()
- self.assertEqual(len(fixation.positions.keys()), size-3)
+ self.assertEqual(len(fixation.positions.keys()), 7)
self.assertLessEqual(fixation.deviation_max, deviation_max)
- self.assertGreaterEqual(fixation.duration, size * min_time)
- self.assertLessEqual(fixation.duration, size * max_time)
+ self.assertGreaterEqual(fixation.duration, 7 * min_time)
+ self.assertLessEqual(fixation.duration, 7 * max_time)
+
+ # Check seconde fixation
+ ts, fixation = ts_fixations.pop_first()
+
+ self.assertEqual(len(fixation.positions.keys()), 5)
+ self.assertLessEqual(fixation.deviation_max, deviation_max)
+ self.assertGreaterEqual(fixation.duration, 5 * min_time)
+ self.assertLessEqual(fixation.duration, 5 * max_time)
- @unittest.skip("Fixation overlapping is broken.")
def test_fixation_overlapping(self):
"""Test Fixation overlap function."""
@@ -255,13 +260,12 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
center_B = (50, 50)
center_C = (55, 55)
deviation_max = 10
- start_time = time.time()
min_time = 0.01
max_time = 0.1
- ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, start_time, min_time, max_time)
- ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, start_time, min_time, max_time)
- ts_gaze_positions_C = build_gaze_fixation(size, center_C, deviation_max, start_time, min_time, max_time)
+ ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, min_time, max_time)
+ ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, min_time, max_time, start_ts=ts_gaze_positions_A.last[0])
+ ts_gaze_positions_C = build_gaze_fixation(size, center_C, deviation_max, min_time, max_time, start_ts=ts_gaze_positions_B.last[0])
fixation_A = DispersionThresholdIdentification.Fixation(ts_gaze_positions_A)
fixation_B = DispersionThresholdIdentification.Fixation(ts_gaze_positions_B)
@@ -275,7 +279,7 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
self.assertTrue(fixation_B.overlap(fixation_C))
self.assertTrue(fixation_C.overlap(fixation_B))
- @unittest.skip("Fixation overlapping identification is broken.")
+ @unittest.skip("Fixation overlapping is not supported anymore.")
def test_fixation_overlapping_identification(self):
"""Test DispersionThresholdIdentification identification when fixations overlap."""
@@ -283,12 +287,11 @@ class TestDispersionThresholdIdentificationClass(unittest.TestCase):
center_A = (-5, 0)
center_B = (5, 0)
deviation_max = 15
- start_time = time.time()
min_time = 0.01
max_time = 0.1
- ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, start_time, min_time, max_time)
- ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, start_time, min_time, max_time)
+ ts_gaze_positions_A = build_gaze_fixation(size, center_A, deviation_max, min_time, max_time)
+ ts_gaze_positions_B = build_gaze_fixation(size, center_B, deviation_max, min_time, max_time, start_ts=ts_gaze_positions_A.last[0])
ts_gaze_positions = ts_gaze_positions_A.append(ts_gaze_positions_B)