๐ describe#
Analyze EDF Trials and Extract Statistics#
The describe() function allows users to analyze eye-tracking trial data from an EDF (Eye Data Format) file. It computes key statistics for a given trial or all trials, including:
Total duration of the trial
Number of fixations, saccades, and blinks
Average fixation duration
Average saccade amplitude
This function is useful for summarizing eye movement behavior from recorded trials.
describe
can directly work with EDF file or you can first Convert data using export function and then import files and use describe
function.
import etformat as et
et.describe(r"D:\Github_web_page_website\test.EDF")
๐ etformat 1.1.1 - For Documentation, visit: https://ahsankhodami.github.io/etformat/intro.html
---------------------------------------------------------------------------
KeyboardInterrupt Traceback (most recent call last)
Cell In[1], line 2
1 import etformat as et
----> 2 et.describe(r"D:\Github_web_page_website\test.EDF")
File ~\AppData\Local\Programs\Python\Python312\Lib\site-packages\etformat\describe.py:34, in describe(data_source, trial_number)
31 return None
33 # Load EDF file
---> 34 edf = EDFFile(edf_file_path, loadevents=True, loadsamples=True)
36 if edf.samples is None or edf.events is None:
37 print("โ ๏ธ No valid sample or event data found in the EDF file.")
File ~\AppData\Local\Programs\Python\Python312\Lib\site-packages\etformat\edffile.py:103, in EDFFile.__init__(self, filename, consistency, loadevents, loadsamples, sample_fields, start_marker_string, end_marker_string, parse_events, wide_variables, trigger_marker, verbose, libpath)
101 data_type = self._edfapi.edf_get_next_data(self._file)
102 while data_type != EDF_NO_PENDING_ITEMS:
--> 103 allf_data_ptr = self._edfapi.edf_get_float_data(self._file)
104 if data_type in EDF_EVENT_CODES.keys():
105 # trial start
106 if data_type == EDF_EVENTS["MESSAGEEVENT"] and \
107 allf_data_ptr.contents.fe["message"].startswith(start_marker_string):
KeyboardInterrupt:
Note
As and Per quesitons, the reason you see a NaN is because some meta data from binary files are reproduced which includes the calibration and other detail, that is why you need to use clean
code to clean your data and remove the unneccessary row
Warning
if you see an error here regarding file is because of compiler error due to jupyter-book` code works in natural environment.
if you have already exported data there are two seperate files after conversion which are EDFfilename_events.csv
and EDFfilename_samples.csv
which can be used to analyze data.
# Load CSV files
samples = pd.read_csv(r"D:\Github_web_page_website\test_samples.csv")
events = pd.read_csv(r"D:\Github_web_page_website\test_events.csv")
et.clean(samples, events, copy = False)
๐งน Starting data cleaning for eye-tracking data
๐ Samples: DataFrame with shape (1520309, 56)
๐ Events: DataFrame with shape (18261, 38)
============================================================
๐ Processing SAMPLES data...
Original samples shape: (1520309, 56)
Columns: 56
โ Removed 2522 rows with NaN trials
โ Removed 15 columns:
โข time_rel (all_nan)
โข pxL (all_nan)
โข pyL (all_nan)
โข hxL (all_nan)
โข hyL (all_nan)
โข paL (all_nan)
โข gxL (all_nan)
โข gyL (all_nan)
โข hdata1 (all_zero)
โข hdata6 (all_zero)
โข hdata7 (all_zero)
โข input (all_zero)
โข buttons (all_zero)
โข htype (all_nan)
โข errors (all_zero)
โ
Samples cleaned: (1520309, 56) โ (1517787, 41)
๐ Processing EVENTS data...
Original events shape: (18261, 38)
Columns: 38
โ Removed 83 rows with NaN trials
โ Removed 7 columns:
โข time (all_zero)
โข sttime_rel (all_nan)
โข entime_rel (all_nan)
โข status (all_zero)
โข flags (all_zero)
โข input (all_zero)
โข buttons (all_zero)
โ
Events cleaned: (18261, 38) โ (18178, 31)
============================================================
๐ Cleaning completed!
( trial time pxR pyR hxR hyR paR gxR gyR \
2522 1.0 392207 -3860.0 -2051.0 342.0 479.0 5275.0 1382.7 839.0
2523 1.0 392208 -3862.0 -2048.0 341.0 481.0 5275.0 1382.3 839.7
2524 1.0 392209 -3867.0 -2044.0 338.0 484.0 5276.0 1381.4 840.5
2525 1.0 392210 -3873.0 -2042.0 334.0 486.0 5276.0 1380.2 841.1
2526 1.0 392211 -3885.0 -2041.0 327.0 486.0 5276.0 1378.1 841.2
... ... ... ... ... ... ... ... ... ...
1520304 480.0 1909989 -4790.0 -3160.0 -176.0 -336.0 4075.0 1226.6 594.4
1520305 480.0 1909990 -4790.0 -3155.0 -176.0 -332.0 4061.0 1226.6 595.5
1520306 480.0 1909991 -4794.0 -3135.0 -179.0 -317.0 4040.0 1225.7 599.9
1520307 480.0 1909992 -4799.0 -3115.0 -182.0 -303.0 4019.0 1224.8 604.3
1520308 480.0 1909993 -4803.0 -3095.0 -185.0 -288.0 3997.0 1224.0 608.7
rx ... frxvelL frxvelR fryvelL fryvelR \
2522 78.9 ... -2010.0 -5.617007e+00 6.570000e-43 1.985040e+01
2523 78.9 ... -2010.0 -3.629450e+01 6.570000e-43 2.028193e+01
2524 78.9 ... -2010.0 -6.049084e+01 6.570000e-43 2.028193e+01
2525 78.9 ... -2010.0 -7.518147e+01 6.570000e-43 2.071346e+01
2526 78.9 ... -2010.0 -8.123055e+01 6.570000e-43 2.157653e+01
... ... ... ... ... ... ...
1520304 78.5 ... 100000000.0 1.000000e+08 6.570000e-43 1.000000e+08
1520305 78.5 ... 100000000.0 1.000000e+08 6.570000e-43 1.000000e+08
1520306 78.5 ... 100000000.0 1.000000e+08 6.570000e-43 1.000000e+08
1520307 78.5 ... 100000000.0 1.000000e+08 6.570000e-43 1.000000e+08
1520308 78.5 ... 100000000.0 1.000000e+08 6.570000e-43 1.000000e+08
hdata0 hdata2 hdata3 hdata4 hdata5 flags
2522 469 -16 -1 -1 -1 24545
2523 469 -16 -1 -1 -1 24545
2524 469 -16 -1 -1 -1 24545
2525 469 -16 -1 -1 -1 24545
2526 469 -16 -1 -1 -1 24545
... ... ... ... ... ... ...
1520304 469 -16 -1 -1 -1 24545
1520305 469 -16 -1 -1 -1 24545
1520306 469 -16 -1 -1 -1 24545
1520307 469 -16 -1 -1 -1 24545
1520308 469 -16 -1 -1 -1 24545
[1517787 rows x 41 columns],
trial type read sttime entime hstx hsty gstx \
83 1.0 ENDFIX 7167 392195 392537 210.0 491.0 1342.9
84 1.0 MESSAGEEVENT 1 392207 0 0.0 0.0 0.0
85 1.0 MESSAGEEVENT 1 392207 0 0.0 0.0 0.0
86 1.0 ENDSACC 7007 392538 392558 307.0 483.0 1372.2
87 1.0 STARTSACC 6921 392538 0 307.0 483.0 1372.2
... ... ... ... ... ... ... ... ...
18256 480.0 MESSAGEEVENT 1 1909993 0 0.0 0.0 0.0
18257 480.0 ENDEVENTS 64 1909994 1909994 0.0 0.0 0.0
18258 480.0 ENDSAMPLES 64 1909994 1909994 0.0 0.0 0.0
18259 480.0 INPUTEVENT 1 1909994 0 0.0 0.0 0.0
18260 480.0 BUTTONEVENT 1 1909994 0 0.0 0.0 0.0
gsty sta ... pvel svel evel supd_x eupd_x supd_y eupd_y \
83 842.7 5268.0 ... 78.7 78.7 18.4 78.9 78.9 79.0 79.0
84 0.0 0.0 ... 0.0 0.0 0.0 0.0 0.0 0.0 0.0
85 0.0 0.0 ... 0.0 0.0 0.0 0.0 0.0 0.0 0.0
86 840.2 0.0 ... 93.8 28.6 39.5 78.9 78.7 79.0 78.7
87 840.2 0.0 ... 0.0 28.6 0.0 78.9 0.0 79.0 0.0
... ... ... ... ... ... ... ... ... ... ...
18256 0.0 0.0 ... 0.0 0.0 0.0 0.0 0.0 0.0 0.0
18257 0.0 0.0 ... 0.0 0.0 0.0 0.0 0.0 0.0 0.0
18258 0.0 0.0 ... 0.0 0.0 0.0 0.0 0.0 0.0 0.0
18259 0.0 0.0 ... 0.0 0.0 0.0 0.0 0.0 0.0 0.0
18260 0.0 0.0 ... 0.0 0.0 0.0 0.0 0.0 0.0 0.0
eye parsedby message
83 RIGHT 192 NaN
84 LEFT 0 Fixation Cross Shown
85 LEFT 0 TRIALID 1
86 RIGHT 192 NaN
87 RIGHT 192 NaN
... ... ... ...
18256 LEFT 0 Experiment ending, stopping eye tracker recording
18257 LEFT 192 NaN
18258 LEFT 0 NaN
18259 LEFT 0 NaN
18260 LEFT 0 NaN
[18178 rows x 31 columns])
# Describe trial #3 using CSV
trial_stats = et.describe((events, samples), trial_number=3)
trial_stats
{'Trial': 3.0,
'Total Duration (ms)': 2659.0,
'Total Samples': 2660.0,
'Number of Fixations': 5.0,
'Number of Saccades': 5.0,
'Number of Blinks': 0.0,
'Avg Fixation Duration (ms)': 531.8,
'Avg Saccade Amplitude': 1.6931468949603112}