SpikeInterface / SpikeInterface/spikeinterface

Inconsistent handling of time offsets in plot_traces

Open
#3,324 6 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

widgets
Dominant language
Python
Stars
847
Forks
280
Avg merge
3d 9h
Merged PRs (30d)
29

Description

Hi all — I was doing some manual digging around to deal with artifacts caused by some custom lighting in our rigs, and I wanted to find the moment in the recording where the artifacts began. I noticed that depending on whether I used recording.time_slice() or recording.plot_traces, there are two different behaviors for dealing with the case where t0 != 0 (this is coming from open ephys, so it's often the case that the first timestamp isn't 0 in the recording).

Case 1: the "give me X many seconds into the recording" strategy. This appears to be used by recording.plot_traces, and I think is a bug.

Case 2: the "give me the data where the timestamps equal this value" strategy. This appears to be used by recording.time_slice, and I think is the correct way (?).

For example, here is the plot from plot_traces for the time range (25.5, 26.5): you can see the artifacts start ~halfway through the window.
image

Now if I run this code to try to show the same thing but with recording.time_slice(), we instead get a different moment:

tmp_rec = recording_car.time_slice(25.5, 26.5)
t = tmp_rec.get_traces(channel_ids=['CH40'])
plt.figure(figsize=(10,3))
plt.plot(t, lw=0.5)

image

If we adjust the time slicing to account for the inconsistent behavior, we recover the same moment in the data:

t0 = recording_car.get_times()[0]
tmp_rec = recording_car.time_slice(25.5 + t0, 26.5 + t0)  # this will get data from where the timestamp equals 25.5 + t0
t = tmp_rec.get_traces(channel_ids=['CH40'])
plt.figure(figsize=(10,3))
plt.plot(t, lw=0.5)

image

You can see the behavior in the code. time_slice ultimately relies on this logic (at least in my case, it seems that self.t_start is assigned automatically when reading from OE folders): sample_index = (time_s - self.t_start) * self.sampling_frequency, which means that, say, if t0 were 10, and the user requested t=20, the code would correctly give the user the data from 10 seconds into the recording.

However the plot/get_traces functions don't appear to do this correction, as seen here and down on L145 below that, and then the helper function just inherits that time range directly.

Hopefully fixing the behavior in plot_traces is easy enough and won't hurt anyone's workflow — I imagine that may be why the bug still exists :)

Contributor guide

No contributing guide indexed for this repository

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by reading src/spikeinterface/widgets/traces.py around lines 126, 145, and helper line 680, then compare its time-range handling with time_slice in src/spikeinterface/core/baserecording.py around line 865. Reproduce the examples using a recording with a nonzero t_start; done means plot_traces selects the same timestamp range as time_slice without requiring callers to offset the requested times.

Written by the indexing model from the issue text.

Assessment

Tech stack
python
Domain
data-visualization
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
48/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.