def test_ProsthesisSystem_reshape_stim(rot, gtype, n_frames): implant = ProsthesisSystem(ElectrodeGrid((10, 10), 30, rot=rot, type=gtype)) # Smoke test the automatic reshaping: n_px = 21 implant.stim = ImageStimulus(np.ones((n_px, n_px, n_frames)).squeeze()) npt.assert_equal(implant.stim.data.shape, (implant.n_electrodes, 1)) npt.assert_equal(implant.stim.time, None) implant.stim = VideoStimulus(np.ones((n_px, n_px, 3 * n_frames)), time=2 * np.arange(3 * n_frames)) npt.assert_equal(implant.stim.data.shape, (implant.n_electrodes, 3 * n_frames)) npt.assert_equal(implant.stim.time, 2 * np.arange(3 * n_frames)) # Verify that a horizontal stimulus will always appear horizontally, even if # the device is rotated: data = np.zeros((50, 50)) data[20:-20, 10:-10] = 1 implant.stim = ImageStimulus(data) model = ScoreboardModel(xrange=(-1, 1), yrange=(-1, 1), rho=30, xystep=0.02) model.build() percept = label(model.predict_percept(implant).data.squeeze().T > 0.2) npt.assert_almost_equal(regionprops(percept)[0].orientation, 0, decimal=1)
def test_ProsthesisSystem(): # Invalid instantiations: with pytest.raises(ValueError): ProsthesisSystem(ElectrodeArray(PointSource(0, 0, 0)), eye='both') # Iterating over the electrode array: implant = ProsthesisSystem(PointSource(0, 0, 0)) npt.assert_equal(implant.n_electrodes, 1) npt.assert_equal(implant[0], implant.earray[0]) npt.assert_equal(implant.keys(), implant.earray.keys()) # Set a stimulus after the constructor: npt.assert_equal(implant.stim, None) implant.stim = 3 npt.assert_equal(isinstance(implant.stim, Stimulus), True) npt.assert_equal(implant.stim.shape, (1, 1)) npt.assert_equal(implant.stim.time, None) npt.assert_equal(implant.stim.electrodes, [0]) with pytest.raises(ValueError): # Wrong number of stimuli implant.stim = [1, 2] with pytest.raises(TypeError): # Invalid stim type: implant.stim = "stim"
def test_Horsager2009Temporal(): model = Horsager2009Temporal() # User can set their own params: model.dt = 0.1 npt.assert_equal(model.dt, 0.1) model.build(dt=1e-4) npt.assert_equal(model.dt, 1e-4) # User cannot add more model parameters: with pytest.raises(FreezeError): model.rho = 100 # Nothing in, None out: implant = ProsthesisSystem(PointSource(0, 0, 0)) npt.assert_equal(model.predict_percept(implant.stim), None) # Zero in = zero out: implant.stim = np.zeros((1, 6)) percept = model.predict_percept(implant.stim, t_percept=[0, 1, 2]) npt.assert_equal(isinstance(percept, Percept), True) npt.assert_equal(percept.shape, (1, 1, 3)) npt.assert_almost_equal(percept.data, 0) # Can't request the same time more than once (this would break the Cython # loop, because `idx_frame` is incremented after a write; also doesn't # make much sense): with pytest.raises(ValueError): implant.stim = np.ones((1, 100)) model.predict_percept(implant.stim, t_percept=[0.2, 0.2]) # Single-pulse brightness from Fig.3: model = Horsager2009Temporal().build() for amp, pdur in zip([188.077, 89.74, 10.55], [0.075, 0.15, 4.0]): stim = BiphasicPulse(amp, pdur, interphase_dur=pdur, stim_dur=200, cathodic_first=True) t_percept = np.arange(0, stim.time[-1] + model.dt / 2, model.dt) percept = model.predict_percept(stim, t_percept=t_percept) npt.assert_almost_equal(percept.data.max(), 110.3, decimal=2) # Fixed-duration brightness from Fig.4: model = Horsager2009Temporal().build() for amp, freq in zip([136.02, 120.35, 57.71], [5, 15, 225]): stim = BiphasicPulseTrain(freq, amp, 0.075, interphase_dur=0.075, stim_dur=200, cathodic_first=True) t_percept = np.arange(0, stim.time[-1] + model.dt / 2, model.dt) percept = model.predict_percept(stim, t_percept=t_percept) npt.assert_almost_equal(percept.data.max(), 36.3, decimal=2)
def test_ProsthesisSystem_stim(): implant = ProsthesisSystem(ElectrodeGrid((13, 13), 20)) stim = Stimulus(np.ones((13 * 13 + 1, 5))) with pytest.raises(ValueError): implant.stim = stim # Deactivated electrodes cannot receive stimuli: implant.deactivate('H4') npt.assert_equal(implant['H4'].activated, False) implant.stim = {'H4': 1} npt.assert_equal('H4' in implant.stim.electrodes, False) implant.deactivate('all') npt.assert_equal(not implant.stim.data, True) implant.activate('all') implant.stim = {'H4': 1} npt.assert_equal('H4' in implant.stim.electrodes, True)
def test_ProsthesisSystem_deactivate(): implant = ProsthesisSystem(ElectrodeGrid((10, 10), 30)) implant.stim = np.ones(implant.n_electrodes) electrode = 'A3' npt.assert_equal(electrode in implant.stim.electrodes, True) implant.deactivate(electrode) npt.assert_equal(implant[electrode].activated, False) npt.assert_equal(electrode in implant.stim.electrodes, False)
def test_ProsthesisSystem(): # Invalid instantiations: with pytest.raises(ValueError): ProsthesisSystem(ElectrodeArray(PointSource(0, 0, 0)), eye='both') with pytest.raises(TypeError): ProsthesisSystem(Stimulus) # Iterating over the electrode array: implant = ProsthesisSystem(PointSource(0, 0, 0)) npt.assert_equal(implant.n_electrodes, 1) npt.assert_equal(implant[0], implant.earray[0]) npt.assert_equal(implant.keys(), implant.earray.keys()) for i, e in zip(implant, implant.earray): npt.assert_equal(i, e) # Set a stimulus after the constructor: npt.assert_equal(implant.stim, None) implant.stim = 3 npt.assert_equal(isinstance(implant.stim, Stimulus), True) npt.assert_equal(implant.stim.shape, (1, 1)) npt.assert_equal(implant.stim.time, None) npt.assert_equal(implant.stim.electrodes, [0]) ax = implant.plot() npt.assert_equal(len(ax.texts), 0) npt.assert_equal(len(ax.patches), 1) npt.assert_equal(isinstance(ax.patches[0], Circle), True) with pytest.raises(ValueError): # Wrong number of stimuli implant.stim = [1, 2] with pytest.raises(TypeError): # Invalid stim type: implant.stim = "stim" # Invalid electrode names: with pytest.raises(ValueError): implant.stim = {'A1': 1} with pytest.raises(ValueError): implant.stim = Stimulus({'A1': 1}) # Slots: npt.assert_equal(hasattr(implant, '__slots__'), True) npt.assert_equal(hasattr(implant, '__dict__'), False)
def test_ProsthesisSystem_stim(): implant = ProsthesisSystem(ElectrodeGrid((13, 13), 20)) stim = Stimulus(np.ones((13 * 13 + 1, 5))) with pytest.raises(ValueError): implant.stim = stim # color mapping stim = np.zeros((13 * 13, 5)) stim[84, 0] = 1 stim[98, 2] = 2 implant.stim = stim plt.cla() ax = implant.plot(stim_cmap='hsv') plt.colorbar() npt.assert_equal(len(ax.collections), 1) npt.assert_equal(ax.collections[0].colorbar.vmax, 2) npt.assert_equal(ax.collections[0].cmap(ax.collections[0].norm(1)), (0.0, 1.0, 0.9647031631761764, 1)) # make sure default behaviour unchanged plt.cla() ax = implant.plot() plt.colorbar() npt.assert_equal(len(ax.collections), 1) npt.assert_equal(ax.collections[0].colorbar.vmax, 1) npt.assert_equal(ax.collections[0].cmap(ax.collections[0].norm(1)), (0.993248, 0.906157, 0.143936, 1)) # Deactivated electrodes cannot receive stimuli: implant.deactivate('H4') npt.assert_equal(implant['H4'].activated, False) implant.stim = {'H4': 1} npt.assert_equal('H4' in implant.stim.electrodes, False) implant.deactivate('all') npt.assert_equal(not implant.stim.data, True) implant.activate('all') implant.stim = {'H4': 1} npt.assert_equal('H4' in implant.stim.electrodes, True)
# # To study these effects, we will apply the model to a number of amplitudes and # frequencies: # Use the following pulse duration (ms): pdur = 0.45 # Generate values in the range [0, 50] uA with a step size of 5 uA or smaller: amps = np.linspace(0, 50, 11) # Initialize an empty list that will contain the predicted brightness values: bright_amp = [] for amp in amps: # For each value in the `amps` vector, now stored as `amp`, do the # following: # 1. Generate a pulse train with amplitude `amp`, 20 Hz frequency, 0.5 s # duration, pulse duration `pdur`, and interphase gap `pdur`: implant.stim = BiphasicPulseTrain(20, amp, pdur, interphase_dur=pdur, stim_dur=stim_dur) # 2. Run the temporal model: percept = model.predict_percept(implant) # 3. Find the largest value in percept, this will be the predicted # brightness: bright_pred = percept.data.max() # 4. Append this value to `bright_amp`: bright_amp.append(bright_pred) ############################################################################### # We then repeat the procedure for a whole range of frequencies: # Generate values in the range [0, 100] Hz with a step size of 10 Hz or # smaller: freqs = np.linspace(0, 100, 11) # Initialize an empty list that will contain the predicted brightness values: