pulse2percept.implants
Different prosthetic implants, such as Argus II, Alpha-IMS, BVT-24, PRIMA, Cortivis, etc.
Cortical implants such as Orion, ICVP, and Neuralink |
|
|
See also
- class pulse2percept.implants.AlphaAMS(x=0, y=0, z=0, rot=0, eye='RE', stim=None, preprocess=True, safe_mode=False)[source]
Alpha-AMS
This class creates an Alpha-AMS array with 1600 photovoltaic pixels (each 30um in diameter) as described in [Stingl2017], and places it in the subretinal space, such that the center of the array is located at (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.The device consists of 1600 30um-wide round pixels, arranged on a 40x40 rectangular grid with 70um pixel pitch.
The array is oriented upright in the visual field, such that an array with center (0,0) has the top three rows lie in the lower retina (upper visual field), as shown below:
An electrode can be addressed by name, row/column index, or integer index (into the flattened array).
Note
Column order is reversed in a left-eye implant.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 1600 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
Examples
Create an AlphaAMS array centered on the fovea, at 100um distance from the retina, rotated counter-clockwise by 5 degrees:
>>> from pulse2percept.implants import AlphaAMS >>> AlphaAMS(x=0, y=0, z=100, rot=5) AlphaAMS(earray=ElectrodeGrid, eye='RE', preprocess=True, safe_mode=False, shape=(40, 40), stim=None)
Get access to the third electrode in the top row (by name or by row/column index):
>>> alpha_ims = AlphaAMS(x=0, y=0, z=100, rot=0) >>> alpha_ims['A3'] DiskElectrode(activated=True, name='A3', r=15.0, x=-1225.0, y=-1365.0, z=100.0) >>> alpha_ims[0, 2] DiskElectrode(activated=True, name='A3', r=15.0, x=-1225.0, y=-1365.0, z=100.0)
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.AlphaIMS(x=0, y=0, z=-100, rot=0, eye='RE', stim=None, preprocess=True, safe_mode=False)[source]
Alpha-IMS
This class creates an Alpha-IMS array with 1500 photovoltaic pixels (each 50um in diameter) as described in [Stingl2013], and places it in the subretinal space, such that the center of the array is located at (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.The device consists of 1500 50um-wide square pixels, arranged on a 39x39 rectangular grid with 72um pixel pitch.
The array is oriented upright in the visual field, such that an array with center (0,0) has the top three rows lie in the lower retina (upper visual field).
An electrode can be addressed by name, row/column index, or integer index (into the flattened array).
Note
Column order is reversed in a left-eye implant.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 1500 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
Examples
Create an Alpha-IMS array centered on the fovea, at 100um distance from the retina, rotated counter-clockwise by 5 degrees:
>>> from pulse2percept.implants import AlphaIMS >>> AlphaIMS(x=0, y=0, z=100, rot=5) AlphaIMS(earray=ElectrodeGrid, eye='RE', preprocess=True, safe_mode=False, shape=(39, 39), stim=None)
Get access to the third electrode in the top row (by name or by row/column index):
>>> alpha_ims = AlphaIMS(x=0, y=0, z=100, rot=0) >>> alpha_ims['A3'] SquareElectrode(a=50.0, activated=True, name='A3', x=-1224.0, y=-1368.0, z=100.0) >>> alpha_ims[0, 2] SquareElectrode(a=50.0, activated=True, name='A3', x=-1224.0, y=-1368.0, z=100.0)
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.ArgusI(x=0, y=0, z=0, rot=0, eye='RE', stim=None, preprocess=True, safe_mode=False, use_legacy_names=False)[source]
Create an Argus I array on the retina
This function creates an Argus I array and places it on the retina such that the center of the array is located at 3D location (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.Argus I is a modified cochlear implant containing 16 electrodes in a 4x4 array with a center-to-center separation of 800 um, and two electrode diameters (250 um and 500 um) arranged in a checkerboard pattern [Yue2020].
The array is oriented in the visual field as shown in Fig. 1 of [Horsager2009]; that is, if placed in (0,0), the top two rows will lie in the lower retina (upper visual field):
-->x A1 B1 C1 D1 260 520 260 520 | A2 B2 C2 D2 where electrode 520 260 520 260 v A3 B3 C3 D3 diameters are: 260 520 260 520 y A4 B4 C4 D4 520 260 520 260
Electrode order is: A1, B1, C1, D1, A2, B2, …, D4.
If
use_legacy_namesis True, electrode order is: L6, L2, M8, M4, …An electrode can be addressed by name, row/column index, or integer index (into the flattened array).
Note
Column order is reversed in a left-eye implant.
- Parameters:
x/y/z (double) – 3D location of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 16 entries or a scalar that is applied to all electrodes.rot (float, optional) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
use_legacy_names (bool, optional) – If True, uses L/M based electrode names from older papers (e.g., L6, L2) instead of A1-A16.
Examples
Create an Argus I array centered on the fovea, at 100um distance from the retina, rotated counter-clockwise by 5 degrees:
>>> from pulse2percept.implants import ArgusI >>> ArgusI(x=0, y=0, z=100, rot=5) ArgusI(earray=ElectrodeGrid, eye='RE', preprocess=True, safe_mode=False, shape=(4, 4), stim=None)
Get access to electrode ‘B1’, either by name or by row/column index:
>>> argus = ArgusI(x=0, y=0, z=100, rot=0) >>> argus['B1'] DiskElectrode(activated=True, name='B1', r=250.0, x=-400.0, y=-1200.0, z=100.0) >>> argus[0, 1] DiskElectrode(activated=True, name='B1', r=250.0, x=-400.0, y=-1200.0, z=100.0)
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.ArgusII(x=0, y=0, z=0, rot=0, eye='RE', stim=None, preprocess=True, safe_mode=False)[source]
Create an Argus II array on the retina
This function creates an Argus II array and places it on the retina such that the center of the array is located at (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.Argus II contains 60 electrodes of 225 um diameter arranged in a 6 x 10 grid (575 um center-to-center separation) [Yue2020].
The array is oriented upright in the visual field, such that an array with center (0,0) has the top three rows lie in the lower retina (upper visual field), as shown below:
A1 A2 A3 A4 A5 A6 A7 A8 A9 A10 -- x B1 B2 B3 B4 B5 B6 B7 B8 B9 B10 | C1 C2 C3 C4 C5 C6 C7 C8 C9 C10 v D1 D2 D3 D4 D5 D6 D7 D8 D9 D10 y E1 E2 E3 E4 E5 E6 E7 E8 E9 E10 F1 F2 F3 F4 F5 F6 F7 F8 F9 F10Electrode order is: A1, A2, …, A10, B1, B2, …, F10.
An electrode can be addressed by name, row/column index, or integer index (into the flattened array).
Note
Column order is reversed in a left-eye implant.
- Parameters:
x/y/z (double) – 3D location of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 60 entries or a scalar that is applied to all electrodes.rot (float) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
Examples
Create an ArgusII array centered on the fovea, at 100um distance from the retina, rotated counter-clockwise by 5 degrees:
>>> from pulse2percept.implants import ArgusII >>> ArgusII(x=0, y=0, z=100, rot=5) ArgusII(earray=ElectrodeGrid, eye='RE', preprocess=True, safe_mode=False, shape=(6, 10), stim=None)
Get access to electrode ‘E7’, either by name or by row/column index:
>>> argus = ArgusII(x=0, y=0, z=100, rot=0) >>> argus['E7'] DiskElectrode(activated=True, name='E7', r=112.5, x=862.5, y=862.5, z=100.0) >>> argus[4, 6] DiskElectrode(activated=True, name='E7', r=112.5, x=862.5, y=862.5, z=100.0)
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.BVT24(x=0, y=0, z=0, rot=0, eye='RE', stim=None, preprocess=False, safe_mode=False)[source]
24-channel suprachoroidal retinal prosthesis
This class creates a 24-channel suprachoroidal retinal prosthesis [Layton2014], which was developed by the Bionic Vision Australia Consortium and commercialized by Bionic Vision Technologies (BVT). The center of the array is located at (x,y,z), given in microns, and the array is rotated counter-clockwise by rotation angle
rot, given in degrees.The array consists of:
33 platinum stimulating electrodes:
30 electrodes with 600um diameter (Electrodes C1-20 (except C9, C17, C19) and Electrodes C21a-m),
3 electrodes with 400um diameter (Electrodes C9, C17, C19)
2 return electrodes with 2000um diameter (Electrodes R1, R2)
Electrodes C21a-m are typically being ganged to provide an external ring for common ground. The center of the array is assumed to lie between Electrodes C7, C8, C9, and C13.
Note
Column order for electrode numbering is reversed in a left-eye implant.
Added in version 0.6.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 35 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.BVT44(x=0, y=0, z=0, rot=0, eye='LE', stim=None, preprocess=False, safe_mode=False)[source]
44-channel suprachoroidal retinal prosthesis
This class creates a 44-channel suprachoroidal retinal prosthesis [Petoe2021], which was developed by the Bionic Vision Australia Consortium and commercialized by Bionic Vision Technologies (BVT).
The center of the array (x,y,z) is located at the center of electrodes D4, D5, C4, and E4, and the array is rotated counter-clockwise by rotation angle
rot, given in degrees.The array consists of:
44 platinum stimulating electrodes with 1000um exposed diameter
2 return electrodes with 2000um diameter (Electrodes R1, R2)
The position of each electrode is measured from Figure 7 in [Petoe2021].
Note
Column order for electrode numbering is reversed in a left-eye implant.
Added in version 0.8.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 35 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.CheckerboardRaster(implant, n_groups, balance=0.05, group_dur=None)[source]
Split electrodes into groups that are spread as far apart as possible
Implements a generalized form of the checkerboard raster pattern tested in [Kasowski2025], which found that scattering raster groups over the whole array beat horizontal, vertical, and random rasters at letter recognition and motion discrimination, and matched not rastering at all.
Mathematically speaking, a raster group is a coset of a sublattice of the electrode grid. Within a group, electrodes sit as far from one another as the electrode count allows. Each group is a coarser copy of the grid. Between groups, the order is chosen so the pattern doubles back rather than marching on (to reduce apparent motion). For example: Five groups on a square grid come out one over, two over, one back, two over, so that the percept steps right, down, left, down, and back rather than sliding across the array.
The grid does not have to be rectangular: hexagonal grids, rotated grids, grids with unequal row and column spacing, and grids with electrodes trimmed off are all handled, since the pattern is derived from where the electrodes actually are. Arrays whose electrodes do not lie on a grid at all raise
NotImplementedError.Note
Not every
n_groupsfits a given grid, and one that does not raises aValueErrorand specifies counts that do.Both halves of the pattern are searched for when the raster is built, and the order the groups fire in is settled exactly only up to eight groups; beyond that a heuristic stands in for it, and the search grows with the group count.
It is worth checking
min_spacingon the ones that do fit, because a count can be accepted and still leave neighbors in the same group. The standard example is two groups on a hex grid, which degenerates to a line raster. In other words, implants like PRIMA cannot be two-colored; they want 3, 4, or 7 raster groups instead.Added in version 0.10.0.
- Parameters:
implant (
ProsthesisSystem) – The implant to build the pattern for, or itsElectrodeArray. The electrodes have to lie on a grid, and their names are how the raster recognizes them later, so this has to be the implant the stimulus will be applied to.n_groups (int) – Number of groups to split the electrodes into.
balance (float, optional) – How much bigger the largest group may be than an even split would make it, as a fraction of it. The largest group is what sets the current the stimulator has to source, so this is the price being paid; what it buys is spacing, because the patterns that spread furthest do not always land evenly on a grid whose edges have been trimmed. Pass 0 to add no imbalance beyond the rounding an uneven electrode count forces anyway – 378 electrodes in 5 groups are 76, 76, 75, 75, 76 at
balance=0, never 76 apiece – and take whatever spacing comes with it.
Examples
Five groups of twelve on Argus II, as in [Kasowski2025]:
>>> from pulse2percept.implants import ArgusII, CheckerboardRaster >>> implant = ArgusII() >>> implant.raster = CheckerboardRaster(implant, 5) >>> implant.raster.n_groups 5
No two electrodes of a group are closer than sqrt(5) pitches, where a line raster would have them adjacent:
>>> round(implant.raster.min_spacing / 575, 3) # 575 um pitch 2.236
The pattern is easiest to check by eye (
plot()), and the electrodes that fire together aremembers():>>> implant.raster.members(implant.electrode_names, 0)[:4].tolist() ['A1', 'A6', 'B3', 'B8']
- property n_groups
Number of raster groups
- property min_spacing
Distance (um) between the closest two electrodes of a group
How much the checkerboard bought over a line raster, which leaves neighboring electrodes in the same group and so would report the electrode pitch. Measured between electrodes the implant actually has, so a small or trimmed array can come out better spaced than the pattern it was cut from. Infinite when no group holds more than one electrode, since then no two electrodes ever fire together.
- members(electrodes, group)[source]
The electrodes that take their turn together in one group
The inverse of
groups(), which says what group each electrode is in. This says which electrodes are in a group.- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
group (int) – Which group to look up, in
0..n_groups-1. Groups take their turns in index order, so group 0 is the one that goes first.
- Returns:
members – The entries of
electrodesbelonging togroup, in the order they were given: names in, names out.- Return type:
array
Examples
>>> from pulse2percept.implants import ArgusII, SequentialRaster >>> names = ArgusII().electrode_names >>> SequentialRaster(6).members(names, 0)[:4] array(['A1', 'A2', 'A3', 'A4'], dtype='<U3')
- offsets(electrodes, period)[source]
How far behind group 0 each electrode’s slot begins
- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
period (float) – The pulse period (ms) a sweep has to fit into.
- Returns:
offset – Time (ms) between the start of a sweep and the start of this electrode’s slot.
- Return type:
(n_electrodes,) float array
- plot(implant, annotate=None, ax=None, cmap='viridis', autoscale=True)[source]
Plot the electrode array, colored by raster group
What a raster does is spatial, so the quickest way to tell whether it does what was wanted is to look at it. Colors run in the order the groups take their turns, so the picture shows the schedule as well as the pattern: with
CheckerboardRastera group’s electrodes should be scattered over the whole array rather than gathered into a line, and neighboring colors should not lie next to one another in a consistent direction.- Parameters:
implant (
ProsthesisSystem) – The implant to draw, or itsElectrodeArray. Its electrodes are the ones the raster is asked about, so this has to be an implant the raster covers.annotate (bool, optional) – Whether to write the group index into each electrode. If None, they are written whenever there are few enough electrodes (at most 120) for the numbers to be readable.
ax (matplotlib.axes.Axes, optional) – Axes to draw on. If None, uses the current axes.
cmap (str, optional) – Matplotlib colormap the group colors are taken from, evenly spaced. A sequential map is the useful default, since the order the colors run in is the order the groups fire in.
autoscale (bool, optional) – Whether to fit the x/y limits to the implant.
- Returns:
ax – The axes drawn on.
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.CustomRaster(groups, group_dur=None)[source]
Assign electrodes to raster groups by name
Added in version 0.10.0.
- Parameters:
Examples
Fire the four corners of Argus II before everything else. Every other electrode has to be given a group too, or the current limit that the raster exists to respect could be violated without anyone noticing:
>>> from pulse2percept.implants import ArgusII, CustomRaster >>> corners = ['A1', 'A10', 'F1', 'F10'] >>> rest = [e for e in ArgusII().electrode_names if e not in corners] >>> raster = CustomRaster([corners, rest]) >>> raster.n_groups 2
- property n_groups
Number of raster groups
- members(electrodes, group)[source]
The electrodes that take their turn together in one group
The inverse of
groups(), which says what group each electrode is in. This says which electrodes are in a group.- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
group (int) – Which group to look up, in
0..n_groups-1. Groups take their turns in index order, so group 0 is the one that goes first.
- Returns:
members – The entries of
electrodesbelonging togroup, in the order they were given: names in, names out.- Return type:
array
Examples
>>> from pulse2percept.implants import ArgusII, SequentialRaster >>> names = ArgusII().electrode_names >>> SequentialRaster(6).members(names, 0)[:4] array(['A1', 'A2', 'A3', 'A4'], dtype='<U3')
- offsets(electrodes, period)[source]
How far behind group 0 each electrode’s slot begins
- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
period (float) – The pulse period (ms) a sweep has to fit into.
- Returns:
offset – Time (ms) between the start of a sweep and the start of this electrode’s slot.
- Return type:
(n_electrodes,) float array
- plot(implant, annotate=None, ax=None, cmap='viridis', autoscale=True)[source]
Plot the electrode array, colored by raster group
What a raster does is spatial, so the quickest way to tell whether it does what was wanted is to look at it. Colors run in the order the groups take their turns, so the picture shows the schedule as well as the pattern: with
CheckerboardRastera group’s electrodes should be scattered over the whole array rather than gathered into a line, and neighboring colors should not lie next to one another in a consistent direction.- Parameters:
implant (
ProsthesisSystem) – The implant to draw, or itsElectrodeArray. Its electrodes are the ones the raster is asked about, so this has to be an implant the raster covers.annotate (bool, optional) – Whether to write the group index into each electrode. If None, they are written whenever there are few enough electrodes (at most 120) for the numbers to be readable.
ax (matplotlib.axes.Axes, optional) – Axes to draw on. If None, uses the current axes.
cmap (str, optional) – Matplotlib colormap the group colors are taken from, evenly spaced. A sequential map is the useful default, since the order the colors run in is the order the groups fire in.
autoscale (bool, optional) – Whether to fit the x/y limits to the implant.
- Returns:
ax – The axes drawn on.
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.DiskElectrode(x, y, z, r, name=None, activated=True)[source]
Circular disk electrode
- Parameters:
x/y/z (double) – 3D location of the electrode. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).r (double) – Disk radius (um) in the x,y plane
name (str, optional) – Electrode name
activated (bool) – To deactivate, set to
False. Deactivated electrodes cannot receive stimuli.
Notes
Lengths may be given as plain numbers of microns or as unitful quantities (e.g.
DiskElectrode(1 * mm, 0, 0.1 * mm, 200 * um)). Seepulse2percept.units.
- electric_potential(x, y, z, v0)[source]
Calculate electric potential at (x, y, z)
- Parameters:
x/y/z (double) – 3D location (um) at which to evaluate the electric potential. May be given as a unitful quantity, e.g.
0.2 * mm.v0 (double) – The quasi-static disk potential relative to a ground electrode at infinity
- Returns:
pot – The electric potential at (x, y, z).
- Return type:
double
The electric potential \(V(r,z)\) of a disk electrode is given by [WileyWebster1982]:
\[V(r,z) = \sin^{-1} \bigg\{ \frac{2a}{\sqrt{(r-a)^2 + z^2} + \sqrt{(r+a)^2 + z^2}} \bigg\} \times \frac{2 V_0}{\pi},\]for \(z \neq 0\), where \(r\) and \(z\) are the radial and axial distances from the center of the disk, \(V_0\) is the disk potential, \(\sigma\) is the medium conductivity, and \(a\) is the disk radius.
- coordinate_unit = um[source]
The unit electrode coordinates are stored in. Electrodes hold plain numbers, which is what every kernel downstream of them expects; this says what those numbers mean.
- coordinates(unit=None)[source]
3D position of the electrode
Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the position in. If None, the position is returned as it is stored (microns).- Returns:
coords – An ordinary NumPy array
[x, y, z], never aQuantity.- Return type:
(3,) np.ndarray
Examples
>>> from pulse2percept.implants import DiskElectrode >>> from pulse2percept.units import mm >>> DiskElectrode(1000, 0, 100, 200).coordinates(mm) array([1. , 0. , 0.1])
- plot(autoscale=False, ax=None)[source]
Plot
- Parameters:
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None given, a new one will be created.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.Electrode[source]
Abstract base class for all electrodes.
- Parameters:
x/y/z (double) – 3D location of the electrode (um). The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the right visual field. Positiveyvalues move the electrode into the left visual field. Positivezvalues move the electrode either into the cortex or into the vitreos humor.name (str, optional) – Electrode name
activated (bool) – To deactivate, set to
False. Deactivated electrodes cannot receive stimuli.
Notes
Coordinates may be given as plain numbers of microns or as unitful quantities (e.g.
1.2 * mm), which are converted to microns. Seepulse2percept.units. Electrodes always store plain numbers in microns:x,yandzare ordinary floats, and so is everything downstream of them.
- coordinate_unit = um[source]
The unit electrode coordinates are stored in. Electrodes hold plain numbers, which is what every kernel downstream of them expects; this says what those numbers mean.
- coordinates(unit=None)[source]
3D position of the electrode
Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the position in. If None, the position is returned as it is stored (microns).- Returns:
coords – An ordinary NumPy array
[x, y, z], never aQuantity.- Return type:
(3,) np.ndarray
Examples
>>> from pulse2percept.implants import DiskElectrode >>> from pulse2percept.units import mm >>> DiskElectrode(1000, 0, 100, 200).coordinates(mm) array([1. , 0. , 0.1])
- plot(autoscale=False, ax=None)[source]
Plot
- Parameters:
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None given, a new one will be created.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.ElectrodeArray(electrodes)[source]
Electrode array
A collection of
Electrodeobjects.- Parameters:
electrodes (array-like) –
Either a single
Electrodeobject or a dict, list, or NumPy array thereof. The keys of the dict will serve as electrode names. Otherwise electrodes will be indexed 0..N.Note
If you pass multiple electrodes in a dictionary, the keys of the dictionary will automatically be sorted. Thus the original order of electrodes might not be preserved.
Examples
Electrode array made from a single DiskElectrode:
>>> from pulse2percept.implants import ElectrodeArray, DiskElectrode >>> earray = ElectrodeArray(DiskElectrode(0, 0, 0, 100)) >>> earray.electrodes OrderedDict([(0, DiskElectrode(activated=True, name=None, r=100..., x=0..., y=0..., z=0...))])
Electrode array made from a single DiskElectrode with name ‘A1’:
>>> from pulse2percept.implants import ElectrodeArray, DiskElectrode >>> earray = ElectrodeArray({'A1': DiskElectrode(0, 0, 0, 100)}) >>> earray.electrodes OrderedDict([('A1', DiskElectrode(activated=True, name=None, r=100..., x=0..., y=0..., z=0...))])
- coordinate_unit = um[source]
The unit electrode coordinates are stored in, i.e. what the plain numbers returned by
coordinates()mean by default.
- coordinates(unit=None, electrodes=None)[source]
Positions of the electrodes in the array
The one place to ask an implant where its electrodes are. Code that needs the coordinates in a particular unit says so here, instead of reading
electrode.xand knowing that electrodes happen to store microns.Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the coordinates in. If None, they are returned as they are stored (microns).electrodes (optional) –
Which electrodes to return. Three things name a single electrode, looked up as
earray[...]looks one up: a name, an index into the flattened array, and a(row, col)pair on anElectrodeGrid. Anything else iterable – a list, an array, or theElectrodeNamesa stimulus reports – is a collection, taken in the order given. If None, every electrode in the array, in array order.A model passes
stim.electrodeshere: a stimulus need not name every electrode of the implant, and need not name them in array order, so the coordinates it wants are a reordered subset.
- Returns:
coords – One
[x, y, z]row per electrode – always two-dimensional, so a single-electrode selection comes back as(1, 3). (For one electrode’s position as a flat triple, seecoordinates().) An ordinary NumPy array, never aQuantity: this is the boundary a numerical implementation should take the geometry across.- Return type:
(n_electrodes, 3) np.ndarray
Examples
>>> from pulse2percept.implants import ArgusII >>> from pulse2percept.units import mm >>> ArgusII().earray.coordinates(mm)[0] array([-2.5875, -1.4375, 0. ]) >>> ArgusII().earray.coordinates(electrodes=['F10', 'A1']) array([[ 2587.5, 1437.5, 0. ], [-2587.5, -1437.5, 0. ]])
- add_electrode(name, electrode)[source]
Add an electrode to the array
- Parameters:
electrode (implants.Electrode) – An Electrode object, such as a PointSource or a DiskElectrode.
- remove_electrode(name)[source]
Remove an electrode from the array
Parameter
- name: int|str|…
Electrode name or index
- plot(annotate=False, autoscale=True, ax=None, color_stim=None, cmap='OrRd')[source]
Plot the electrode array
- Parameters:
annotate (bool, optional) – Flag whether to label electrodes in the implant.
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
color_stim (
pulse2percept.stimuli.Stimulus, or None) – If provided, colors the earray based on the stimulus amplitudescmap (str) – Matplotlib colormap to use for stimulus coloring.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in earray.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the electrode array object, e.g.
earray['A1']orearray[0].
- property electrode_names
Return a list of all electrode names in the array
- property electrode_objects
Return a list of all electrode objects in the array
- class pulse2percept.implants.ElectrodeGrid(shape, spacing, x=0, y=0, z=0, rot=0, names=('A', '1'), type='rect', orientation='horizontal', etype=<class 'pulse2percept.implants.electrodes.PointSource'>, **kwargs)[source]
2D grid of electrodes
- Parameters:
shape ((rows, cols)) – A tuple containing the number of rows x columns in the grid
spacing (double or (x_spacing, y_spacing)) – Electrode-to-electrode spacing in microns. Must be either a tuple specifying the spacing in x and y directions or a float (assuming the same spacing in x and y). If a tuple is specified for a horizontal hex grid,
x_spacingwill define the electrode-to-electrode distance, andy_spacingwill define the vertical distance between adjacent hexagon centers. In a vertical hex grid, the order is reversed.type ({'rect', 'hex'}, optional) – Grid type (‘rect’: rectangular, ‘hex’: hexagonal).
orientation ({'horizontal', 'vertical'}, optional) – In a hex grid, ‘horizontal’ orientation will shift every other row to the right, whereas ‘vertical’ will shift every other column up.
x/y/z (double) – 3D location (um) of the center of the grid. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).rot (double, optional) – Rotation of the grid in degrees (positive angle: counter-clockwise rotation on the retinal surface). A plain angle, not a unitful one:
dvameans visual angle, which is a different thing.names ((name_rows, name_cols), each of which either 'A' or '1') –
Naming convention for rows and columns, respectively. If ‘A’, rows or columns will be labeled alphabetically: A-Z, AA-AZ, BA-BZ, CA-CZ, etc. ‘-A’ will reverse the order. If ‘1’, rows or columns will be labeled numerically. ‘-1’ will reverse. Letters will always precede numbers in electrode names. For example (‘1’, ‘A’) will number rows numerically and columns alphabetically; first row: ‘A1’, ‘B1’, ‘C1’, NOT ‘1A’, ‘1B’, ‘1C’.
The default,
('A', '1'), is the same convention thatElectrodeNamesuses to name the pixels of anImageStimulus, and is generated by it. The other combinations exist to reproduce the naming of specific published implants and are not otherwise recommended.Alternatively, pass a list or NumPy array with one name per electrode to name them all explicitly. On a grid with exactly two electrodes the two readings collide, and only something that could be a scheme is read as one:
names=('A', '1')gives ‘A1’, ‘A2’, whereasnames=('C1', '4')names the two electrodes ‘C1’ and ‘4’. Pass a list (names=['A', '1']) to name two electrodes ‘A’ and ‘1’.Changed in version 0.10.0: On a grid with exactly two electrodes,
('A', '1')now yields ‘A1’, ‘A2’ (was: ‘A’, ‘1’), consistent with every other shape.etype (
Electrode, optional) – A valid Electrode class. By default,PointSourceis used.**kwargs – Any additional arguments that should be passed to the
Electrodeconstructor, such as radiusrforDiskElectrode. See examples below.
Notes
spacing,x,y,zandrmay be given as plain numbers of microns or as unitful quantities, and may be mixed freely:spacing=(0.5 * mm, 600 * um)andz=[0 * um, 0.1 * mm, ...]both work. Any other electrode keyword is normalized by the electrode class it is passed to. Seepulse2percept.units.
Examples
A hexagonal electrode grid with 3 rows and 4 columns, made of disk electrodes with 10um radius spaced 20um apart, centered at (10, 20)um, and located 500um away from the retinal surface, with names like this:
A1 A2 A3 A4 B1 B2 B3 B4 C1 C2 C3 C4>>> from pulse2percept.implants import ElectrodeGrid, DiskElectrode >>> ElectrodeGrid((3, 4), 20, x=10, y=20, z=500, names=('A', '1'), r=10, ... type='hex', etype=DiskElectrode) ElectrodeGrid(rot=0, shape=(3, 4), spacing=20, type='hex')
A rectangular electrode grid with 2 rows and 4 columns, made of disk electrodes with 10um radius spaced 20um apart, centered at (10, 20)um, and located 500um away from the retinal surface, with names like this:
A1 A2 A3 A4 B1 B2 B3 B4>>> from pulse2percept.implants import ElectrodeGrid, DiskElectrode >>> ElectrodeGrid((2, 4), 20, x=10, y=20, z=500, names=('A', '1'), r=10, ... type='rect', etype=DiskElectrode) ElectrodeGrid(rot=0, shape=(2, 4), spacing=20, type='rect')
There are three ways to access (e.g.) the last electrode in the grid, either by name (
grid['C3']), by row/column index (grid[2, 2]), or by index into the flattened array (grid[8]):>>> from pulse2percept.implants import ElectrodeGrid >>> grid = ElectrodeGrid((3, 3), 20, names=('A', '1')) >>> grid['C3'] PointSource(activated=True, name='C3', x=20..., y=20..., z=0...) >>> grid['C3'] == grid[8] == grid[2, 2] True
You can also access multiple electrodes at the same time by passing a list of indices/names (it’s ok to mix-and-match):
>>> from pulse2percept.implants import ElectrodeGrid, DiskElectrode >>> grid = ElectrodeGrid((3, 3), 20, etype=DiskElectrode, r=10) >>> grid[['A1', 1, (0, 2)]] [DiskElectrode(activated=True, name='A1', r=10..., x=-20.0, y=-20.0, z=0...), DiskElectrode(activated=True, name='A2', r=10..., x=0.0, y=-20.0, z=0...), DiskElectrode(activated=True, name='A3', r=10..., x=20.0, y=-20.0, z=0...)]
- add_electrode(name, electrode)[source]
Add an electrode to the array
- Parameters:
electrode (implants.Electrode) – An Electrode object, such as a PointSource or a DiskElectrode.
- coordinate_unit = um[source]
The unit electrode coordinates are stored in, i.e. what the plain numbers returned by
coordinates()mean by default.
- coordinates(unit=None, electrodes=None)[source]
Positions of the electrodes in the array
The one place to ask an implant where its electrodes are. Code that needs the coordinates in a particular unit says so here, instead of reading
electrode.xand knowing that electrodes happen to store microns.Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the coordinates in. If None, they are returned as they are stored (microns).electrodes (optional) –
Which electrodes to return. Three things name a single electrode, looked up as
earray[...]looks one up: a name, an index into the flattened array, and a(row, col)pair on anElectrodeGrid. Anything else iterable – a list, an array, or theElectrodeNamesa stimulus reports – is a collection, taken in the order given. If None, every electrode in the array, in array order.A model passes
stim.electrodeshere: a stimulus need not name every electrode of the implant, and need not name them in array order, so the coordinates it wants are a reordered subset.
- Returns:
coords – One
[x, y, z]row per electrode – always two-dimensional, so a single-electrode selection comes back as(1, 3). (For one electrode’s position as a flat triple, seecoordinates().) An ordinary NumPy array, never aQuantity: this is the boundary a numerical implementation should take the geometry across.- Return type:
(n_electrodes, 3) np.ndarray
Examples
>>> from pulse2percept.implants import ArgusII >>> from pulse2percept.units import mm >>> ArgusII().earray.coordinates(mm)[0] array([-2.5875, -1.4375, 0. ]) >>> ArgusII().earray.coordinates(electrodes=['F10', 'A1']) array([[ 2587.5, 1437.5, 0. ], [-2587.5, -1437.5, 0. ]])
- property electrode_names
Return a list of all electrode names in the array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in earray.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the electrode array object, e.g.
earray['A1']orearray[0].
- plot(annotate=False, autoscale=True, ax=None, color_stim=None, cmap='OrRd')[source]
Plot the electrode array
- Parameters:
annotate (bool, optional) – Flag whether to label electrodes in the implant.
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
color_stim (
pulse2percept.stimuli.Stimulus, or None) – If provided, colors the earray based on the stimulus amplitudescmap (str) – Matplotlib colormap to use for stimulus coloring.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.EnsembleImplant(implants, stim=None, preprocess=False, safe_mode=False)[source]
- classmethod from_cortical_map(implant_type, vfmap, locs=None, xrange=None, yrange=None, xystep=None, region='v1')[source]
Create an ensemble implant from a cortical visual field map.
The implant will be created by creating an implant of type implant_type for each visual field location specified either by locs or by xrange, yrange, and xystep. Each implant will be centered at the given location.
- Parameters:
vfmap (p2p.topography.CorticalMap) – Visual field map to create implant from.
implant_type (type) – Type of implant to create for the ensemble. Must subclass p2p.implants.ProsthesisSystem
locs (np.ndarray with shape (n, 2), optional) – Array of visual field locations to create implants at (dva). Not needed if using xrange, yrange, and xystep.
xrange (tuple of floats, optional) – Range of x and y coordinates (dva) to create implants at.
yrange (tuple of floats, optional) – Range of x and y coordinates (dva) to create implants at.
xystep (float, optional) – Spacing (dva) between implant centers.
region (str, optional) – Region of cortex to create implant in.
- Returns:
ensemble – Ensemble implant created from the cortical visual field map.
- Return type:
p2p.implants.EnsembleImplant
Notes
These are visual field coordinates, so they may be given as plain numbers of degrees or as unitful quantities (e.g.
xrange=(-3 * dva, 3 * dva)). Contrastfrom_coords(), which places implants by their physical position in microns. Seepulse2percept.units.
- classmethod from_coords(implant_type, locs=None, xrange=None, yrange=None, xystep=None)[source]
Create an ensemble implant using physical (cortical or retinal) coordinates.
- Parameters:
implant_type (type) – The type of implant to create for the ensemble.
locs (np.ndarray with shape (n, 2), optional) – Array of physical locations (um) to create implants at. Not needed if using xrange, yrange, and xystep.
xrange (tuple of floats, optional) – Range of x and y coordinates (um) to create implants at. Required (together with
xystep) iflocsis not given.yrange (tuple of floats, optional) – Range of x and y coordinates (um) to create implants at. Required (together with
xystep) iflocsis not given.xystep (float, optional) – Spacing (um) between implant centers.
- Raises:
ValueError – If neither
locsnor all three ofxrange,yrangeandxystepare given.
Notes
Lengths may be given as plain numbers of microns or as unitful quantities (e.g.
xrange=(-1 * mm, 1 * mm)). Seepulse2percept.units.
Changed in version 0.10.0: The grid arguments no longer have defaults. They used to fall back on
(-3, 3)and1, which are the degrees of visual anglefrom_cortical_map()works in; here they are microns, so the default laid every implant out inside a 6 um square.
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property earray
Electrode array
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property implants
Dict of implants
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.HexElectrode(x, y, z, a, name=None, activated=True)[source]
Hexagonal electrode
Added in version 0.7.
- Parameters:
x/y/z (double) – 3D location of the electrode. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).a (double) – Length (um) of line drawn from the center of the hexagon to the midpoint of one of its sides.
name (str, optional) – Electrode name
activated (bool) – To deactivate, set to
False. Deactivated electrodes cannot receive stimuli.
Notes
Lengths may be given as plain numbers of microns or as unitful quantities (e.g.
50 * um). Seepulse2percept.units.
- coordinate_unit = um[source]
The unit electrode coordinates are stored in. Electrodes hold plain numbers, which is what every kernel downstream of them expects; this says what those numbers mean.
- coordinates(unit=None)[source]
3D position of the electrode
Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the position in. If None, the position is returned as it is stored (microns).- Returns:
coords – An ordinary NumPy array
[x, y, z], never aQuantity.- Return type:
(3,) np.ndarray
Examples
>>> from pulse2percept.implants import DiskElectrode >>> from pulse2percept.units import mm >>> DiskElectrode(1000, 0, 100, 200).coordinates(mm) array([1. , 0. , 0.1])
- plot(autoscale=False, ax=None)[source]
Plot
- Parameters:
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None given, a new one will be created.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.PhotovoltaicPixel(x, y, z, r, a, name=None, activated=True)[source]
Photovoltaic pixel
Added in version 0.7.
- Parameters:
x/y/z (double) – 3D location of the electrode. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).r (double) – Disk radius (um) in the x,y plane
a (double) – Length (um) of line drawn from the center of the hexagon to the midpoint of one of its sides.
activated (bool) – To deactivate, set to
False. Deactivated electrodes cannot receive stimuli.
Notes
Lengths may be given as plain numbers of microns or as unitful quantities (e.g.
14 * um). Seepulse2percept.units.
- coordinate_unit = um[source]
The unit electrode coordinates are stored in. Electrodes hold plain numbers, which is what every kernel downstream of them expects; this says what those numbers mean.
- coordinates(unit=None)[source]
3D position of the electrode
Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the position in. If None, the position is returned as it is stored (microns).- Returns:
coords – An ordinary NumPy array
[x, y, z], never aQuantity.- Return type:
(3,) np.ndarray
Examples
>>> from pulse2percept.implants import DiskElectrode >>> from pulse2percept.units import mm >>> DiskElectrode(1000, 0, 100, 200).coordinates(mm) array([1. , 0. , 0.1])
- plot(autoscale=False, ax=None)[source]
Plot
- Parameters:
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None given, a new one will be created.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.PointSource(x, y, z, name=None, activated=True)[source]
Idealized current point source
- Parameters:
x/y/z (double) – 3D location of the electrode. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).name (str, optional) – Electrode name
activated (bool) – To deactivate, set to
False. Deactivated electrodes cannot receive stimuli.
- electric_potential(x, y, z, amp, sigma)[source]
Calculate electric potential at (x, y, z)
- Parameters:
x/y/z (double) – 3D location (um) at which to evaluate the electric potential. May be given as a unitful quantity, e.g.
0.2 * mm.amp (double) – amplitude of the constant current pulse
sigma (double) – resistivity of the extracellular solution
- Returns:
pot (double) – The electric potential at (x, y, z)
The electric potential \(V(r)\) of a point source is given by
.. math:: – V(r) = frac{sigma I}{4 pi r},
where \(\sigma\) is the resistivity of the extracellular solution
(typically Ames medium, \(\sigma = 110 \Ohm cm\)),
\(I\) is the amplitude of the constant current pulse,
and \(r\) is the distance from the stimulating electrode to the
point at which the voltage is being computed.
- coordinate_unit = um[source]
The unit electrode coordinates are stored in. Electrodes hold plain numbers, which is what every kernel downstream of them expects; this says what those numbers mean.
- coordinates(unit=None)[source]
3D position of the electrode
Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the position in. If None, the position is returned as it is stored (microns).- Returns:
coords – An ordinary NumPy array
[x, y, z], never aQuantity.- Return type:
(3,) np.ndarray
Examples
>>> from pulse2percept.implants import DiskElectrode >>> from pulse2percept.units import mm >>> DiskElectrode(1000, 0, 100, 200).coordinates(mm) array([1. , 0. , 0.1])
- plot(autoscale=False, ax=None)[source]
Plot
- Parameters:
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None given, a new one will be created.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.PRIMA(x=0, y=0, z=-100, rot=0, eye='RE', stim=None, preprocess=False, safe_mode=False)[source]
Create a PRIMA-100 array on the retina
This class creates a PRIMA array with 378 photovoltaic pixels (each 100um in diameter) as used in the clinical trial [Palanker2020], and places it in the subretinal space such that the center of the array is located at 3D location (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.The device consists of 378 85um-wide pixels separated by 15um trenches, arranged in a 2-mm wide hexagonal pattern.
This corresponds to a 100um pitch, with adjacent rows separated by 87um. The active electrode is a disk with 28um diameter.
Added in version 0.7.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 378 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float, optional) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
Notes
The diameter of the active electrode and the trench width were estimated from Fig.1 in [Palanker2020].
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.PRIMA75(x=0, y=0, z=-100, rot=0, eye='RE', stim=None, preprocess=False, safe_mode=False)[source]
Create a PRIMA-75 array on the retina
This class creates a PRIMA array with 142 photovoltaic pixels (each 75um in diameter) as described in [Lorach2015], and places it in the subretinal space, such that that the center of the array is located at 3D location (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.The device consists of 142 70um-wide pixels separated by 5um trenches, arranged in a 1-mm wide hexagonal pattern.
This corresponds to a 75um pitch, with adjacent rows separated by 65um. The active electrode is a disk with 20um diameter.
Added in version 0.7.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 142 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float, optional) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.PRIMA55(x=0, y=0, z=-100, rot=0, eye='RE', stim=None, preprocess=False, safe_mode=False)[source]
Create a PRIMA-55 array on the retina
This class creates a PRIMA array with 273 photovoltaic pixels (each 55um in diameter), and places it in the subretinal space, such that that the center of the array is located at 3D location (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.The device consists of 273 50um-wide pixels separated by 5um trenches, arranged in a 1-mm wide hexagonal pattern.
This corresponds to a 55um pitch, with adjacent rows separated by 48um. The active electrode is a disk with 16um diameter.
Warning
The exact shape of the device has not been published yet. We assume the array fits on a circular 1mm-diameter substrate, which leaves us with 273 electrodes.
Added in version 0.7.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 378 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float, optional) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.PRIMA40(x=0, y=0, z=-100, rot=0, eye='RE', stim=None, preprocess=False, safe_mode=False)[source]
Create a PRIMA-40 array on the retina
This class creates a PRIMA array with 532 photovoltaic pixels (each 40um in diameter), and places it in the subretinal space, such that that the center of the array is located at 3D location (x,y,z), given in microns, and the array is rotated by rotation angle
rot, given in degrees.The device consists of 532 35um-wide pixels separated by 5um trenches, arranged in a 1-mm wide hexagonal pattern.
This corresponds to a 40um pitch, with adjacent rows separated by 48um. The active electrode is a disk with 16um diameter.
Important
The exact shape of the device has not been published yet. We assume the array fits on a circular 1mm-diameter substrate, which leaves us with 532 electrodes.
Added in version 0.7.
- Parameters:
x/y/z (double) – 3D location (um) of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 532 entries or a scalar that is applied to all electrodes. May be given as unitful quantities (e.g.z=100 * um); seepulse2percept.units.rot (float, optional) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'LE', 'RE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- class pulse2percept.implants.ProsthesisSystem(earray, stim=None, eye='RE', preprocess=False, safe_mode=False, raster=None, max_current=None)[source]
Visual prosthesis system
A visual prosthesis combines an electrode array and (optionally) a stimulus. This is the base class for prosthesis systems such as
ArgusIIandAlphaIMS.Added in version 0.6.
- Parameters:
earray (
ElectrodeArrayor) –ElectrodeThe electrode array used to deliver electrical stimuli to the retina.stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).eye ('LE' or 'RE') – A string indicating whether the system is implanted in the left (‘LE’) or right eye (‘RE’)
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed. Safety is an electrical property, so this also requires the stimulus to be measured in units of current.
raster (
Raster, optional) –How the stimulator takes turns between electrodes that it cannot drive at the same time. If None, every electrode may fire at once.
Added in version 0.10.0.
max_current (float, optional) –
The total current (uA) the stimulator can source at any one instant, summed over all electrodes. If given, assigning a stimulus that exceeds it raises. If None, no such check is performed.
May be given as a plain number of microamps or as a unitful quantity (e.g.
0.1 * mA); seepulse2percept.units.Added in version 0.10.0.
Examples
A system in the left eye made from a single
DiskElectrodewith radius r=100um sitting at x=200um, y=-50um, z=10um:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> implant = ProsthesisSystem(DiskElectrode(200, -50, 10, 100), eye='LE')
Note
A stimulus can also be assigned later (see
stim).- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- property max_current
Total instantaneous current (uA) the stimulator can source
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- class pulse2percept.implants.Raster(group_dur=None)[source]
Abstract base class for all raster patterns
A stimulator usually cannot drive every electrode at once, because the total current it can source at any instant is limited. Electrodes are therefore split into raster groups that take turns.
A raster is a scheduling constraint, not a hardware state machine. What it has to deliver is one property: no two groups are ever active at the same instant, so that the stimulator sources at most one group’s worth of current however the video is modulated. It is not a switch that cyclically enables group 0, then group 1, then group 0 again forever, and a group’s pulses do not have to land at the same phase of a repeating cycle.
Taking turns is described by a raster sweep: group g starts its pulse
g * group_durafter group 0 does, so a sweep spansn_groups * group_dur. Two things then keep groups apart for good (seeEncoder):A pulse has to be short enough to finish before the next group’s turn begins.
Electrodes on different pulse periods drift relative to one another, and would eventually collide however they started out. Their periods are therefore pinned to whole numbers of the sweep, which fixes their relative phase. Pinning rounds the period up, so multiplexing never drives an electrode faster – and so never delivers more charge – than asked.
Electrodes that share one period cannot drift in the first place: their onsets stay
group_durapart forever, whatever that period is. Nothing is quantized in that case and the requested rate is delivered exactly, even when the period is not a whole number of sweeps. This is the usual case under amplitude modulation, and it is why rastering costs no frequency there.So with two groups 1.5 ms apart on a common 10 ms period, group 0 pulses at 0, 10, 20, … and group 1 at 1.5, 11.5, 21.5, … – collision-free, but not a repeating 3 ms schedule, and the 10 ms period is left alone.
The sweep belongs to the stimulation schedule, not to the video: it is tied to the pulse period, not to the frame rate. Two rules settle how long it is and what it costs:
With
group_dur=Nonethe groups divide the shortest pulse period between them, so the sweep is exactly that period. Under frequency modulation that means the fastest electrode pulses once per sweep and slower ones every m-th sweep.With an explicit
group_durthe sweep isn_groups * group_durwhatever rate the electrodes run at – six groups of 1 ms sweep in 6 ms. It is then generally much shorter than a pulse period, so even the fastest electrode may pulse only every m-th sweep.
Either way, only periods that differ from one another are rounded up onto the sweep; a period they all share is delivered exactly, since fixed group offsets cannot drift into one another.
Subclasses only implement
groups.Added in version 0.10.0.
- Parameters:
group_dur (float, optional) –
Duration (ms) of a single group’s slot, and hence the spacing between one group’s turn and the next. If None, the groups are spread evenly over the pulse period, so that a sweep takes exactly one period to complete – which is what an encoder wants whenever every electrode pulses at the same rate.
Setting it explicitly makes the sweep
n_groups * group_durregardless of the pulse period, which is how you buy back frequency resolution under frequency modulation: a shorter slot means a shorter sweep, and the periods that have to be pinned are pinned onto a finer grid. It cannot be shorter than a single pulse.An encoder with a
clockrounds the slot onto it and rebuilds the sweep from the result, so every group keeps a turn of the same length.May be given as a plain number of milliseconds or as a unitful quantity (e.g.
1000 * us); the same goes for theperiodargument ofslot_dur()andoffsets(). Seepulse2percept.units.
- abstract property n_groups
Number of raster groups
- abstractmethod groups(electrodes)[source]
Assign each electrode to a raster group
- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
- Returns:
group – The group each electrode belongs to, in
0..n_groups-1.- Return type:
(n_electrodes,) int array
- members(electrodes, group)[source]
The electrodes that take their turn together in one group
The inverse of
groups(), which says what group each electrode is in. This says which electrodes are in a group.- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
group (int) – Which group to look up, in
0..n_groups-1. Groups take their turns in index order, so group 0 is the one that goes first.
- Returns:
members – The entries of
electrodesbelonging togroup, in the order they were given: names in, names out.- Return type:
array
Examples
>>> from pulse2percept.implants import ArgusII, SequentialRaster >>> names = ArgusII().electrode_names >>> SequentialRaster(6).members(names, 0)[:4] array(['A1', 'A2', 'A3', 'A4'], dtype='<U3')
- plot(implant, annotate=None, ax=None, cmap='viridis', autoscale=True)[source]
Plot the electrode array, colored by raster group
What a raster does is spatial, so the quickest way to tell whether it does what was wanted is to look at it. Colors run in the order the groups take their turns, so the picture shows the schedule as well as the pattern: with
CheckerboardRastera group’s electrodes should be scattered over the whole array rather than gathered into a line, and neighboring colors should not lie next to one another in a consistent direction.- Parameters:
implant (
ProsthesisSystem) – The implant to draw, or itsElectrodeArray. Its electrodes are the ones the raster is asked about, so this has to be an implant the raster covers.annotate (bool, optional) – Whether to write the group index into each electrode. If None, they are written whenever there are few enough electrodes (at most 120) for the numbers to be readable.
ax (matplotlib.axes.Axes, optional) – Axes to draw on. If None, uses the current axes.
cmap (str, optional) – Matplotlib colormap the group colors are taken from, evenly spaced. A sequential map is the useful default, since the order the colors run in is the order the groups fire in.
autoscale (bool, optional) – Whether to fit the x/y limits to the implant.
- Returns:
ax – The axes drawn on.
- Return type:
matplotlib.axes.Axes
- offsets(electrodes, period)[source]
How far behind group 0 each electrode’s slot begins
- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
period (float) – The pulse period (ms) a sweep has to fit into.
- Returns:
offset – Time (ms) between the start of a sweep and the start of this electrode’s slot.
- Return type:
(n_electrodes,) float array
- class pulse2percept.implants.RectangleImplant(x=0, y=0, z=0, rot=0, shape=(15, 15), r=75.0, spacing=400.0, eye='RE', stim=None, preprocess=True, safe_mode=False)[source]
A generic rectangular implant
- Parameters:
x (float, optional) – The x, y, z coordinates (um) of the center of the implant
y (float, optional) – The x, y, z coordinates (um) of the center of the implant
z (float, optional) – The x, y, z coordinates (um) of the center of the implant
rot (float, optional) – The rotation of the implant in degrees
shape (tuple, optional) – The number of rows and columns in the implant
r (float, optional) – The electrode radius (um)
spacing (float, optional) – The distance (um) between electrodes in the implant
eye (str, optional) – The eye in which the implant is implanted
stim (
Stimulussource type) – A valid source type for a stimuluspreprocess (bool, optional) – Whether to preprocess the stimulus
safe_mode (bool, optional) – Whether to enforce charge balance
Notes
Lengths may be given as plain numbers of microns or as unitful quantities (e.g.
spacing=0.4 * mm). Seepulse2percept.units.
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.
- property earray
Electrode array
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- class pulse2percept.implants.SequentialRaster(n_groups, interleave=False, group_dur=None)[source]
Split electrodes into groups that fire one after another
Electrodes are assigned to groups by their position in the stimulus, which for an
ElectrodeGridruns row by row. So on a 6x10 array such asArgusII,SequentialRaster(6)puts each row in its own group – a line raster.Added in version 0.10.0.
- Parameters:
n_groups (int) – Number of groups to split the electrodes into.
interleave (bool, optional) – If False (the default), each group is a contiguous block of electrodes. If True, groups are interleaved, so that consecutive electrodes end up in different groups. Interleaving spreads each group’s current further across the array.
Examples
A line raster for Argus II, one row of ten electrodes at a time:
>>> from pulse2percept.implants import ArgusII, SequentialRaster >>> implant = ArgusII() >>> implant.raster = SequentialRaster(6)
- property n_groups
Number of raster groups
- members(electrodes, group)[source]
The electrodes that take their turn together in one group
The inverse of
groups(), which says what group each electrode is in. This says which electrodes are in a group.- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
group (int) – Which group to look up, in
0..n_groups-1. Groups take their turns in index order, so group 0 is the one that goes first.
- Returns:
members – The entries of
electrodesbelonging togroup, in the order they were given: names in, names out.- Return type:
array
Examples
>>> from pulse2percept.implants import ArgusII, SequentialRaster >>> names = ArgusII().electrode_names >>> SequentialRaster(6).members(names, 0)[:4] array(['A1', 'A2', 'A3', 'A4'], dtype='<U3')
- offsets(electrodes, period)[source]
How far behind group 0 each electrode’s slot begins
- Parameters:
electrodes (array_like) – Electrode names, in the order they appear in the stimulus.
period (float) – The pulse period (ms) a sweep has to fit into.
- Returns:
offset – Time (ms) between the start of a sweep and the start of this electrode’s slot.
- Return type:
(n_electrodes,) float array
- plot(implant, annotate=None, ax=None, cmap='viridis', autoscale=True)[source]
Plot the electrode array, colored by raster group
What a raster does is spatial, so the quickest way to tell whether it does what was wanted is to look at it. Colors run in the order the groups take their turns, so the picture shows the schedule as well as the pattern: with
CheckerboardRastera group’s electrodes should be scattered over the whole array rather than gathered into a line, and neighboring colors should not lie next to one another in a consistent direction.- Parameters:
implant (
ProsthesisSystem) – The implant to draw, or itsElectrodeArray. Its electrodes are the ones the raster is asked about, so this has to be an implant the raster covers.annotate (bool, optional) – Whether to write the group index into each electrode. If None, they are written whenever there are few enough electrodes (at most 120) for the numbers to be readable.
ax (matplotlib.axes.Axes, optional) – Axes to draw on. If None, uses the current axes.
cmap (str, optional) – Matplotlib colormap the group colors are taken from, evenly spaced. A sequential map is the useful default, since the order the colors run in is the order the groups fire in.
autoscale (bool, optional) – Whether to fit the x/y limits to the implant.
- Returns:
ax – The axes drawn on.
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.SquareElectrode(x, y, z, a, name=None, activated=True)[source]
Square electrode
Added in version 0.7.
- Parameters:
x/y/z (double) – 3D location of the electrode. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).a (double) – Side length (um) of the square
name (str, optional) – Electrode name
activated (bool) – To deactivate, set to
False. Deactivated electrodes cannot receive stimuli.
Notes
Lengths may be given as plain numbers of microns or as unitful quantities (e.g.
50 * um). Seepulse2percept.units.
- coordinate_unit = um[source]
The unit electrode coordinates are stored in. Electrodes hold plain numbers, which is what every kernel downstream of them expects; this says what those numbers mean.
- coordinates(unit=None)[source]
3D position of the electrode
Added in version 0.10.0.
- Parameters:
unit (
Unit, optional) – Length unit to express the position in. If None, the position is returned as it is stored (microns).- Returns:
coords – An ordinary NumPy array
[x, y, z], never aQuantity.- Return type:
(3,) np.ndarray
Examples
>>> from pulse2percept.implants import DiskElectrode >>> from pulse2percept.units import mm >>> DiskElectrode(1000, 0, 100, 200).coordinates(mm) array([1. , 0. , 0.1])
- plot(autoscale=False, ax=None)[source]
Plot
- Parameters:
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None given, a new one will be created.
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- class pulse2percept.implants.IMIE(x=0, y=0, z=0, rot=0, eye='RE', stim=None, preprocess=True, safe_mode=False)[source]
The 256-channel epiretinal prosthesis system (IMIE 256)
This class implements a 256-channel Intelligent Micro Implant Eye epiretinal prosthesis system (IMIE 256) [Xu2021]. It was co-developed by Golden Eye Bionic, LLC (Pasadena CA) and IntelliMicro Medical Co., Ltd. (Changsha, Hunan Province, China) and is manufactured by IntelliMicro.
IMIE contains 248 large electrodes (210 µm in diameter) and 8 smaller electrodes (160 µm in diameter) arranged in a 4.75mm×6.50mm area.
The array is oriented upright in the visual field, such that an array with center (0,0) has the top three rows lie in the lower retina (upper visual field):
- Parameters:
x/y/z (double) – 3D location of the center of the electrode array. The coordinate system is centered over the fovea. Positive
xvalues move the electrode into the nasal retina. Positiveyvalues move the electrode into the superior retina. Positivezvalues move the electrode away from the retina into the vitreous humor (sometimes called electrode-retina distance).zcan either be a list with 35 entries or a scalar that is applied to all electrodes.rot (float) – Rotation angle of the array (deg). Positive values denote counter-clock-wise (CCW) rotations in the retinal coordinate system.
eye ({'RE', 'LE'}, optional) – Eye in which array is implanted.
preprocess (bool or callable, optional) – Either True/False to indicate whether to execute the implant’s default preprocessing method whenever a new stimulus is assigned, or a custom function (callable).
safe_mode (bool, optional) – If safe mode is enabled, only charge-balanced stimuli are allowed.
- property earray
Electrode array
- property eye
Implanted eye
A
ProsthesisSystemcan be implanted either in a left eye (‘LE’) or right eye (‘RE’). Models such asAxonMapModelwill treat left and right eyes differently (for example, adjusting the location of the optic disc).Examples
Implant Argus II in a left eye:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(eye='LE')
- property stim
Stimulus
A stimulus can be created from many source types, such as scalars, NumPy arrays, and dictionaries (see
Stimulusfor a complete list).A stimulus can be assigned either in the
ProsthesisSystemconstructor or later by assigning a value to stim.Note
Unless when using dictionary notation, the number of stimuli must equal the number of electrodes in
earray.Examples
Send a biphasic pulse (30uA, 0.45ms phase duration) to an implant made from a single
DiskElectrode:>>> from pulse2percept.implants import DiskElectrode, ProsthesisSystem >>> from pulse2percept.stimuli import BiphasicPulse >>> implant = ProsthesisSystem(DiskElectrode(0, 0, 0, 100)) >>> implant.stim = BiphasicPulse(30, 0.45)
Stimulate Electrode B7 in Argus II with 13 uA:
>>> from pulse2percept.implants import ArgusII >>> implant = ArgusII(stim={'B7': 13})
- check_stim(stim)[source]
Quality-check the stimulus
This method is executed every time a new value is assigned to
stim.If
safe_modeis set to True, this function will only allow stimuli that are charge-balanced. Ifmax_currentis set, it will only allow stimuli whose total instantaneous current stays within it.Both are questions about electricity, and neither can be answered about a stimulus that is not a current, so each raises a
DimensionMismatchErroron one. An implant that asks for neither does not run either check, which is why a dimensionless stimulus may still be assigned to one –preprocesshas already had its chance to turn it into current, and if it did not, no safety claim is being made about it either.The user can define their own checks in implants that inherit from
ProsthesisSystem.- Parameters:
stim (
Stimulussource type) – A valid source type for theStimulusobject (e.g., scalar, NumPy array, pulse train).- Raises:
DimensionMismatchError – If an electrical check was requested and
stimis not measured in units of current... versionchanged: – 0.10.0: The electrical checks verify that the stimulus really is electrical, instead of reading whatever numbers it holds as microamps.
- property electrode_names
Return a list of all electrode names in the electrode array
- property electrode_objects
Return a list of all electrode objects in the array
- property electrodes
Return all electrode names and objects in the electrode array
Internally, electrodes are stored in an ordered dictionary. You can iterate over different electrodes in the array as follows:
for name, electrode in implant.electrodes.items(): print(name, electrode)
You can access an individual electrode by indexing directly into the prosthesis system object, e.g.
implant['A1']orimplant[0].
- property max_current
Total instantaneous current (uA) the stimulator can source
- property n_electrodes
Number of electrodes in the array
This is equivalent to calling
earray.n_electrodes.
- plot(annotate=False, autoscale=True, ax=None, stim_cmap=False)[source]
Plot
- Parameters:
annotate (bool, optional) – Whether to scale the axes view to the data
autoscale (bool, optional) – Whether to adjust the x,y limits of the plot to fit the implant
ax (matplotlib.axes._subplots.AxesSubplot, optional) – A Matplotlib axes object. If None, will either use the current axes (if exists) or create a new Axes object.
stim_cmap (bool, str, or matplotlib colormap, optional) – If not false, the fill color of the plotted electrodes will vary based on maximum stimulus amplitude on each electrode. The chosen colormap will be used if provided
- Returns:
ax – Returns the axis object of the plot
- Return type:
matplotlib.axes.Axes
- preprocess_stim(stim)[source]
Preprocess the stimulus
This methods is executed every time a new value is assigned to
stim.No preprocessing is performed by default, but the user can define their own method in implants that inherit from return stim
ProsthesisSystem.A custom method must return a
Stimulusobject with the correct number of electrodes for the implant.
- property raster
Raster pattern
Most implants do not set this in their constructor, so the slot backing it may never have been written to; an unset raster means all electrodes may fire at once.