Bits

class psychopy_crs.bits.BitsPlusPlus(win, contrast=1.0, gamma=None, nEntries=256, mode='bits++', rampType='configFile', frameRate=None)[source]

The main class to control a Bits++ box. This is usually a class added within the window object and is typically accessed from there. e.g.:

from psychopy import visual
from psychopy.hardware import crs
win = visual.Window([800,600])
bits = crs.BitsPlusPlus(win, mode='bits++')
# use bits++ to reduce the whole screen contrast by 50%:
bits.setContrast(0.5)
getPackets()[source]

Returns the number of packets available for trigger pulses.

primeClock()[source]

Primes the clock to reset at the next screen flip - note only 1 clock reset signal will be issued but if the frame(s) after the reset frame is dropped the reset will be re-issued thus keeping timing good.

Resets continute to be issued on each video frame until the next win.flip so you need to have regular win.flips for this function to work properly.

Example:

bits.primeClock()
drawImage
while not response
    #do some processing
    bits.win.flip()

Will get a clock reset signal ready but won’t issue it until the first win.flip in the loop.

reset()[source]

Deprecated: This was used on the old Bits++ to power-cycle the box. It required the compiled dll, which only worked on windows and doesn’t work with Bits# or Display++.

resetClock()[source]

Issues a clock reset code using 1 screen flip if the next frame(s) is dropped the reset will be re-issued thus keeping timing good.

Resets continue to be issued on each video frame until the next win.flip so you need to have regular win.flips for this function to work properly.

Example

bits.resetClock() drawImage() bits.win.flip()

Will issue clock resets while the image is being drawn then display the image and allow the clock to continue from the same frame.

Example

bits.resetClock() bits.RTBoxWait() bits.win.flip()

Will issue clock resets until a button is pressed.

sendTrigger(triggers=0, onTime=0, duration=0, mask=65535)[source]

Sends a single trigger using up 1 win.flip. The trigger will be sent on the following frame.

The triggers will continue until after the next win.flip.

Actions are always 1 frame after the request.

May do odd things if Goggles and Analog are also in use.

Example:

bits.sendTrigger(0b0000000010, 2.0, 4.0)
bits.win.flip()

Will send a 4ms puilse on DOUT1 2ms after the start of the frame. Due to the following win.flip() the pulse should last for 1 frame only.

Triggers will continue until stopTrigger is called.

setContrast(contrast, LUTrange=1.0, gammaCorrect=None)[source]

Set the contrast of the LUT for ‘bits++’ mode only :Parameters:

contrastfloat in the range 0:1

The contrast for the range being set

LUTrangefloat or array

If a float is given then this is the fraction of the LUT to be used. If an array of floats is given, these will specify the start / stop points as fractions of the LUT. If an array of ints (0-255) is given these determine the start stop indices of the LUT

Examples

  • setContrast(1.0,0.5) to set the central 50% of the LUT so that a stimulus with

    contr=0.5 will actually be drawn with contrast 1.0

  • setContrast(1.0,[0.25,0.5])

  • or setContrast(1.0,[63,127]) to set the lower-middle quarter of the LUT

    (which might be useful in LUT animation paradigms)

setGamma(newGamma)[source]

Set the LUT to have the requested gamma value Currently also resets the LUT to be a linear contrast ramp spanning its full range. May change this to read the current LUT, undo previous gamma and then apply new one?

setLUT(newLUT=None, gammaCorrect=True, LUTrange=1.0)[source]

Sets the LUT to a specific range of values in ‘bits++’ mode only Note that, if you leave gammaCorrect=True then any LUT values you supply will automatically be gamma corrected. The LUT will take effect on the next Window.flip()

Examples:

  • bitsBox.setLUT() to build a LUT using bitsBox.contrast and bitsBox.gamma

  • bitsBox.setLUT(newLUT=some256x1array) (NB array should be float 0.0:1.0) Builds a luminance LUT using newLUT for each gun (actually array can be 256x1 or 1x256)

  • bitsBox.setLUT(newLUT=some256x3array) (NB array should be float 0.0:1.0) Allows you to use a different LUT on each gun

(NB by using BitsBox.setContr() and BitsBox.setGamma() users may not need this function)

setTrigger(triggers=0, onTime=0, duration=0, mask=65535)[source]

Quick way to set up triggers.

Triggers is a binary word that determines which triggers will be turned on.

onTime specifies the start time of the trigger within the frame (in S with 100uS resolution)

Duration specifies how long the trigger will last. (in S with 100uS resolution).

Note that mask only protects the digital output lines set by other activities in the Bits. Not other triggers.

Example::

bits.setTrigger(0b0000000010, 2.0, 4.0, 0b0111111111) bits.startTrigger()

Will issue a 4ms long high-going pulse, 2ms after the start of each frame on DOUT1 while protecting the value of DOUT 9.

setTriggerList(triggerList=None, mask=65535)[source]

Sets up Trigger pulses in Bits++ using the fine grained method that can control every trigger line at 100uS intervals.

TriggerList should contain 1 entry for every 100uS packet (see getPackets) the binary word in each entry specifies which trigger line will be active during that time slot.

Note that mask only protects the digital output lines set by other activities in the Bits. Not other triggers.

Example:

packet = [0]*self._NumberPackets
packet[0] = 0b0000000010
bits.setTriggerList(packet)

Will sens a 100us pulse on DOUT1 at the start of the frame.

Example 2:

packet = [0]*self._NumberPackets
packet[10] = 0b0000000010
packet[20] = 0b0000000001
bits.setTriggerList(packet)
bits.startTrigger()

Will sens a 100us pulse on DOUT1 1000us after the start of the frame and a second 100us pusle on DOUT0 2000us after the start of the frame.

Triggers will continue until stopTrigger is called.

startGoggles(left=0, right=1)[source]

Starts CRS stereo goggles. Note if you are using FE-1 goggles you should start this before connecting the goggles.

Left is the state of the left shutter on the first frame to be presented 0, False or ‘closed’=closed; 1, True or ‘open’ = open,

right is the state of the right shutter on the first frame to be presented 0, False or ‘closed’=closed; 1, True or ‘open’ = open

Note you can set the goggles to be both open or both closed on the same frame.

The system will always toggle the state of each lens so as to not damage FE-1 goggles.

Example:

bits.startGoggles(0,1)
bits.win.flip()
while not response
    bits.win.flip()
    #do some processing
bits.stopGoggles()
bits.win.flip()

Starts toggling the goggles with the right eye open in sync with the first win.flip() within the loop. The open eye will alternate.

Example:

bits.startGoggles(1,1)
bits.win.flip()
while not response:
    bits.win.flip()
    #do some processing
bits.stopGoggles()
bits.win.flip()

Starts toggling the goggle with both eyes open in sync with the first win.flip() within the loop. Eyes will alternate between both open and both closed.

Note it is safe to leave the goggles toggling forever, ie to never call stopGoggles().

startTrigger()[source]

Start sending triggers on the next win flip and continue until stopped by stopTrigger Triggers start 1 frame after the frame on which the first trigger is sent.

Example:

bits.setTrigger(0b0000000010, 2.0, 4.0, 0b0111111111)
bits.startTrigger()
while imageOn:
    #do some processing
    continue
bits.stopTrigger()
bits.win.flip()
stopGoggles()[source]

Stop the stereo goggles from toggling

Example:

bits.startGoggles(0,1)
bits.win.flip()
while not response:
    bits.win.flip()
    #do some processing
bits.stopGoggles()
bits.win.flip()

Starts toggling the goggles with the right eye open in sync with the first win.flip(0) within the loop. The open eye will alternate.

Note it is safer to leave the goggles toggling forever, ie to never call stopGoggles().

stopTrigger()[source]

Stop sending triggers at the next win flip

Example:

bits.setTrigger(0b0000000010, 2.0, 4.0, 0b0111111111)
bits.startTrigger()
while imageOn:
    #do some processing
    continue
bits.stopTrigger()
bits.win.flip()
syncClocks(t)[source]

Synchronise the Bits/RTBox Clock with the host clock Given by t.

class psychopy_crs.bits.BitsSharp(*args, **kwargs)[source]

A class to support functions of the Bits# (and most Display++ functions This device uses the CDC (serial port) connection to the Bits box. To use it you must have followed the instructions from CRS Ltd. to get your box into the CDC communication mode. Typical usage (also see demo in Coder view demos>hardware>BitsBox ):

from psychopy import visual
from psychopy.hardware import crs
# we need to be rendering to framebuffer
win = visual.Window([1024,768], useFBO=True)
bits = crs.BitsSharp(win, mode = 'mono++')
# You can continue using your window as normal and OpenGL shaders
# will convert the output as needed
print(bits.info)
if not bits.OK:
    print('failed to connect to Bits box')
    core.quit()
core.wait(0.1)
# now, you can change modes using
bits.mode = 'mono++' # 'color++', 'mono++', 'bits++', 'status'

Note that the firmware in Bits# boxes varies over time and some features of this class may not work for all firmware versions. Also Bits# boxes can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

RTBox commands that reset the key mapping have been found not to work one some firmware

RTBoxAddKeys(map)[source]

Add key mappings to an existing map. RTBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, triggers and CB6 IR input channels. The format for map is a list of tuples with each tuple containing the name of the RTBox button to be mapped and its source eg (‘btn1’,’Din1’) maps physical input Din1 to logical button btn1. RTBox has four logical buttons (btn1-4) and three auxiliary events (light, pulse and trigger) Buttons/events can be mapped to multiple physical inputs and stay mapped until reset.

Example:

bits.RTBoxSetKeys([('btn1','Din0),('btn2','Din1')])
bits.RTBoxAddKeys([('btn1','IRButtonA'),(('btn2','IRButtonB')])

Will link Din0 to button 1 and Din1 to button 2. Then adds IRButtonA and IRButtonB alongside the original mappings.

Now both hard wired and IR inputs will - emulating the same logical button press.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

RTBoxCalibrate(N=1)[source]

Used to assess error between host clock and Bits# button press time stamps.

Prints each sample provided and returns the mean error.

The clock willnever be completely in sync but the aim is that there should be that the difference between them should not grow over a serise of button presses.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

RTBoxClear()[source]

Flushes the serial input buffer. Its good to do this before and after data collection. This just calls flush() so is a wrapper for RTBox.

RTBoxDisable()[source]

Disables the detection of RTBox events. This is useful to stop the Bits# from reporting key presses When you no longer need them. Nad must be done before using any other data logging methods.

It undoes any button - input mappings.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

The ability to reset keys mappings has been found not to work on some Bits# firmware.

RTBoxEnable(mode=None, map=None)[source]

Sets up the RTBox with preset or bespoke mappings and enables event detection.

RTBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, tigers and CB6 IR input channels.

Mode is a list of strings. Preset mappings provided via mode:

  • CB6 for the CRS CB6 IR response box.

  • IO for a three button box connected to Din0-2

  • IO6 for a six button box connected to Din0-5

If mode = None or is not set then the value of self.RTBoxMode is used.

Bespoke Mappings over write preset ones.

The format for map is a list of tuples with each tuple containing the name of the RT Box button to be mapped and its source eg (‘btn1’,’Din0’) maps physical input Din0 to logical button btn1.

Note the lowest number button event is Btn1

RTBox has four logical buttons (btn1-4) and three auxiliary events (light, pulse and trigger) Buttons/events can be mapped to multiple physical inputs and stay mapped until reset.

Mode is a list of string or list of strings that contains keywords to determine present mappings and modes for RTBox.

  • If mode includes ‘Down’ button events will be detected when pressed.

  • If mode includes ‘Up’ button events will be detected when released.

You can detect both types of event but note that pulse, light and trigger events don’t have an ‘Up’ mode.

If Trigger is included in mode the trigger event will be mapped to the trigIn connector.

Example: .. code-block:: python

bits.RTBoxEnable(mode = [‘Down’]), map = [(‘btn1’,’Din0’), (‘btn2’,’Din1’)]

enables the RTBox emulation to detect Down events on buttons 1 and 2 where they are mapped to DIN0 and DIN1.

Example: .. code-block:: python

bits.RTBoxEnable(mode = [‘Down’,’CB6’])

enables the RTBox emulation to detect Down events on the standard CB6 IR response box keys.

If no key direction has been set (mode does not contain ‘Up’ or ‘Down’) the default is ‘Down’.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

The ability to reset keys mappings has been found not to work on some Bits# firmware.

RTBoxKeysPressed(N=1)[source]

Check to see if (at least) the appropriate number of RTBox style key presses have been made.

Example

bits.RTBoxKeysPressed(5)

will return false until 5 button presses have been recorded.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

RTBoxResetKeys()[source]

Resets the key mappings to no mapping. Has the effect of disabling RTBox input.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

The ability to reset keys mappings has been found not to work on some Bits# firmware.

RTBoxSetKeys(map)[source]

Set key mappings: first resets existing then adds new ones. Does not reset any event that is not in the new list. RTBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, triggers and CB6 IR input channels. The format for map is a list of tuples with each tuple containing the name of the RTBox button to be mapped and its source eg (‘btn1’,’Din1’) maps physical input Din1 to logical button btn1.

RTBox has four logical buttons (btn1-4) and three auxiliary events (light, pulse and trigger) Buttons/events can be mapped to multiple physical inputs and stay mapped until reset.

Example

bits.RTBoxSetKeys([(‘btn1’,’Din0),(‘light’,’Din9’)])

Will link Din0 to button 1 and Din9 to the the light input emulation.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

RTBoxWait()[source]

Waits until (at least) one of RTBox style key presses have been made Pauses program execution in mean time.

Example

res = bits.RTBoxWait()

will suspend all other activity until 1 button press has been recorded and will then return a dict / structure containing results.

Results can be accessed as follows:

structure

res.dir, res.button, res.time

or dictionary

res[‘dir’], res[‘button’], res[‘time’]

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

RTBoxWaitN(N=1)[source]

Waits until (at least) the appropriate number of RTBox style key presses have been made Pauses program execution in mean time.

Example

res = bits.RTBoxWaitN(5)

will suspend all other activity until 5 button presses have been recorded and will then return a list of Dicts containing the 5 results.

Results can be accessed as follows:

structure

res[0].dir, res[0].button, res[0].time

or dictionary

res[0][‘dir’], res[0][‘button’], res[0][‘time’]

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

beep(freq=800, dur=1)[source]

Make a beep of a given frequency and duration

checkConfig(level=1, demoMode=False, logFile='')[source]

Checks whether there is a configuration for this device and whether it’s correct

Parameters:

level (integer) –

  • 0: do nothing

  • 1: check that we have a config file and that the graphics

    card and operating system match that specified in the file. Then assume identity LUT is correct

  • 2: switch the box to status mode and check that the

    identity LUT is currently working

  • 3: force a fresh search for the identity LUT

clock()[source]

Reads the internal clock of the Bits box via the RTBox fortmat but note there will be a delay in reading the value back. The fortmat for the return values is the same as for button box presses. The return value for button will be 9 and the return value for event will be time. The return value for time will be the time of the clock at the moment of the request.

Example

res = bits.clock() print(res.time) print(res[‘time’])

flush()[source]

Flushes the serial input buffer Its good to do this before and after data collection, And generally quite often.

property gammaCorrectFile

Get / set the gamma correction file to be used (as stored on the device)

getAllRTBoxResponses()[source]

Read all of the RTBox style key presses on the input buffer. Returns a list of dict like objects with three members ‘button’, ‘dir’ and ‘time’

‘button’ is a number from 1 to 9 to indicate the event that was detected. 1-4 are the ‘btn1-btn4’ events, 5 and 6 are the ‘light’ and ‘pulse’ events, 7 is the ‘trigger’ event, 9 is a requested timestamp event (see Clock()).

‘dir’ is the direction of the event eg ‘up’ or ‘down’, trigger is described as ‘on’ when low.

‘dir’ is set to ‘time’ if a requested timestamp event has been detected.

‘time’ is the timestamp associated with the event.

Values can be read as a structure eg:

res = getAllRTBoxResponses()
res[0].dir, res[0].button, res[0].time

or dictionary:

res[0]['dir'], res[0]['button'], res[0]['time']

Note even if only 1 key press was found a list of dict / objects is returned

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

getAllStatusBoxResponses()[source]

Read all of the statusBox style key presses on the input buffer. Returns a list of dict like objects with three members ‘button’, ‘dir’ and ‘time’

‘button’ is a number from 1 to 9 to indicate the event that was detected. 1-17 are the ‘btn1-btn17’ events.

‘dir’ is the direction of the event eg ‘up’ or ‘down’, trigger is described as ‘on’ when low.

‘dir’ is set to ‘time’ if a requested timestamp event has been detected.

‘time’ is the timestamp associated with the event.

Values can be read as a structure eg:

res= getAllStatusBoxResponses()
res[0].dir, res[0].button, res[0].time

or dictionary:

res[0]['dir'], res[0]['button'], res[0]['time']

Note even if only 1 key press was found a list of dict / objects is returned.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getAllStatusEvents()[source]

Returns the whole status event list

Returns a list of dictionary like objects with the following entries source, input, direction, time.

source = the general source of the event - e.g. DIN for Digital input, IR for CB6 IR response box events

input = the individual input in the source. direction = ‘up’ or ‘down’ time = time stamp.

All sourses are numbered from zero. Din 0 … 9 IR 0 … 5 ADC 0 … 5

mode specifies which directions of events are captured. e.g ‘up’ will only report up events.

The data can be accessed as value[i][‘time’] or value[i].time

Example:

bits.startStatusLog()
while not event
    #do some processing
    continue
bits.stopStatusLog()
res=getAllStatusEvents()
print(bits.res[0].time)

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getAllStatusValues()[source]

Returns the whole status values list.

Returns a list of dict like objects with the following entries sample, time, trigIn, DIN[10], DWORD, IR[6], ADC[6] sample is the sample ID number. time is the time stamp. trigIn is the value of the trigger input. DIN is a list of 10 digital input values. DWORD represents the digital inputs as a single decimal value. IR is a list of 10 infra-red (IR) input values. ADC is a list of 6 analog input values. These can be accessed as value[i][‘sample’] or value[i].sample, values[i].ADC[j].

All sourses are numbered from zero. Din 0 … 9 IR 0 … 5 ADC 0 … 5

Example:

bits.startStatusLog()
while not event
    #do some processing
    continue
bits.stopStatusLog()
res=getAllStatusValues()
print(bits.res[0].time)

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getAnalog(N=0)[source]

Pulls out the values of the analog inputs for the Nth status entry.

Returns a dictionary with a list of 6 floats (ADC) and a time stamp (time).

All sourses are numbered from zero. ADC 0 … 5

Example

bits.pollStatus() res=bits.getAnalog() print(res[‘ADC’])

will poll the status display the values of the ADC inputs in the first status entry returned.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getDigital(N=0)[source]

Pulls out the values of the digital inputs for the Nth status entry.

Returns a dictionary with a list of 10 ints that are 1 or 0 (DIN) and a time stamp (time)

ll sourses are numbered from zero. Din 0 … 9

Example

bits.pollStatus() res=bits.getAnalog() print(res[‘DIN’])

will poll the status display the value of the digital inputs in the first status entry returned.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also DBits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getDigitalWord(N=0)[source]

Pulls out the values of the digital inputs for the Nth status entry.

Returns a dictionary with a 10 bit word representing the binary values of those inputs (DWORD) and a time stamp (time).

Example

bits.pollStatus() res=bits.getAnalog() print(res[‘DWORD’])

will poll the status display the value of the digital inputs as a decimal number.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getIRBox(N=0)[source]

Pulls out the values of the CB6 IR response box inputs for the Nth status entry.

Returns a dictionary with a list of 6 ints that are 1 or 0 (IRBox) and a time stamp (time).

ll sourses are numbered from zero. IR 0 … 5

Example

bits.pollStatus() res=bits.getAnalog() print(res.[‘IRBox’])

will poll the status display the values of the IR box buttons in the first status entry returned.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getInfo()[source]

Returns a python dictionary of info about the Bits Sharp box

Example::

info=bits.getInfo print(info[‘ProductType’])

getRTBoxResponse()[source]

checks for one RTBox style key presses on the input buffer then reads it. Returns a dict like object with three members ‘button’, ‘dir’ and ‘time’

‘button’ is a number from 1 to 9 to indicate the event that was detected. 1-4 are the ‘btn1-btn4’ events, 5 and 6 are the ‘light’ and ‘pulse’ events, 7 is the ‘trigger’ event, 9 is a requested timestamp event (see Clock()).

‘dir’ is the direction of the event eg ‘up’ or ‘down’, trigger is described as ‘on’ when low.

‘dir’ is set to ‘time’ if a requested timestamp event has been detected.

‘time’ is the timestamp associated with the event.

Value can be read as a structure, eg:

res= getRTBoxResponse() res.dir, res.button, res.time

or dictionary

res[‘dir’], res[‘button’], res[‘time’]

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

getRTBoxResponses(N=1)[source]

checks for (at least) an appropriate number of RTBox style key presses on the input buffer then reads them. Returns a list of dict like objects with three members ‘button’, ‘dir’ and ‘time’

‘button’ is a number from 1 to 9 to indicate the event that was detected. 1-4 are the ‘btn1-btn4’ events, 5 and 6 are the ‘light’ and ‘pulse’ events, 7 is the ‘trigger’ event, 9 is a requested timestamp event (see Clock()).

‘dir’ is the direction of the event eg ‘up’ or ‘down’, trigger is described as ‘on’ when low.

‘dir’ is set to ‘time’ if a requested timestamp event has been detected.

‘time’ is the timestamp associated with the event.

Values can be read as a list of structures eg:

res = getRTBoxResponses(3)
res[0].dir, res[0].button, res[0].time

or dictionaries:

res[0]['dir'], res[0]['button'], res[0]['time']

Note even if only 1 key press was requested a list of dict / objects is returned.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. Such variations may affect key mappings for RTBox commands.

getStatus(N=0)[source]

Pulls out the Nth entry in the statusValues list.

Returns a dict like object with the following entries sample, time, trigIn, DIN[10], DWORD, IR[6], ADC[6]

sample is the sample ID number. time is the time stamp. trigIn is the value of the trigger input. DIN is a list of 10 digital input values. DWORD represents the digital inputs as a single decimal value. IR is a list of 10 infra-red (IR) input values. ADC is a list of 6 analog input values. These can be accessed as value[‘sample’] or value.sample, values.ADC[j].

All sourses are numbered from zero. Din 0 … 9 IR 0 … 5 ADC 0 … 5

Example:

bits.startStatusLog()
while not event
    #do some processing
    continue
bits.stopStatusLog()
res=getStatus(20)
print(bits.res.time)

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getStatusBoxResponse()[source]

checks for one statusBox style key presses on the input buffer then reads it. Returns a dict like object with three members ‘button’, ‘dir’ and ‘time’

‘button’ is a number from 1 to 9 to indicate the event that was detected. 1-17 are the ‘btn1-btn17’ events.

‘dir’ is the direction of the event eg ‘up’ or ‘down’, trigger is described as ‘on’ when low.

‘dir’ is set to ‘time’ if a requested timestamp event has been detected.

‘time’ is the timestamp associated with the event.

Value can be read as a structure, eg:

res= getRTBoxResponse() res.dir, res.button, res.time

or dictionary

res[‘dir’], res[‘button’], res[‘time’]

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getStatusBoxResponses(N=1)[source]

checks for (at least) an appropriate number of RTBox style key presses on the input buffer then reads them. Returns a list of dict like objects with three members ‘button’, ‘dir’ and ‘time’

‘button’ is a number from 1 to 9 to indicate the event that was detected. 1-4 are the ‘btn1-btn4’ events, 5 and 6 are the ‘light’ and ‘pulse’ events, 7 is the ‘trigger’ event, 9 is a requested timestamp event (see Clock()).

‘dir’ is the direction of the event eg ‘up’ or ‘down’, trigger is described as ‘on’ when low.

‘dir’ is set to ‘time’ if a requested timestamp event has been detected.

‘time’ is the timestamp associated with the event.

Values can be read as a list of structures eg:

res = getRTBoxResponses(3)
print(res[0].dir, res[0].button, res[0].time)

or dictionaries:

print(res[0]['dir'], res[0]['button'], res[0]['time'])

Note even if only 1 key press was requested a list of dict / objects is returned.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getStatusEvent(N=0)[source]

pulls out the Nth event from the status event list

Returns a dictionary like object with the following entries source, input, direction, time.

source = the general source of the event - e.g. DIN for Digital input, IR for IT response box.

input = the individual input in the source. direction = ‘up’ or ‘down’ time = time stamp.

All sourses are numbered from zero. Din 0 … 9 IR 0 … 5 ADC 0 … 5

mode specifies which directions of events are captured, e.g ‘up’ will only report up events.

The data can be accessed as value[‘time’] or value.time

Example:

bits.startStatusLog()
while not event
    #do some processing
    continue
bits.stopStatusLog()
res=getAllStatusEvents(20)
print(bits.res.time)

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getTrigIn(N=0)[source]

Pulls out the values of the trigger input for the Nth status entry.

Returns dictionary with a 0 or 1 (trigIn) and a time stamp (time)

Example

bits.pollStatus() res=bits.getAnalog() print(res[‘trigIn’])

will poll the status display the value of the trigger input.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

getVideoLine(lineN, nPixels, timeout=10.0, nAttempts=10)[source]

Return the r,g,b values for a number of pixels on a particular video line

Parameters:
  • lineN – the line number you want to read

  • nPixels – the number of pixels you want to read

  • nAttempts – the first time you call this function it has to get to status mode. In this case it sometimes takes a few attempts to make the call work

Returns:

an Nx3 numpy array of uint8 values

isAwake()[source]

Test whether we have an active connection on the virtual serial port

property mode

Get/set the mode of the BitsSharp to one of: “bits++” “mono++” “color++” “status” “storage” “auto”

property monitorEDID

Get / set the EDID file for the monitor. The edid files will be located in the EDID subdirectory of the flash disk. The file automatic.edid will be the file read from the connected monitor.

pollStatus(t=0.0001)[source]

Reads the status reports from the Bits# for the specified usually short time period t. The script will wait for this time to lapse so not ideal for time critical applications.

If t is less than 0.01 polling will continue until at least 1 data entry has been recorded.

If you don’t want to wait while this does its job use startStatusLog and stopStatusLog instead.

Fills the statusValues list with all the status values read during the time period.

Fills the statusEvents list with just those status values that are likely to be meaningful events.

the members statusValues and statusEvents will end up containing dict like objects of the following style: sample, time, trigIn, DIN[10], DWORD, IR[6], ADC[6]

They can be accessed as statusValues[i][‘sample’] or stautsValues[i].sample, statusValues[x].ADC[j].

Example:

bits.pollStatus()
print(bits.statusValues[0].IR[0])

will display the value of the IR InputA in the first sample recorded.

Note: Starts and stops logging for itself.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

read(timeout=0.1)[source]

Get the current waiting characters from the serial port if there are any.

Mostly used internally but may be needed by user. Note the return message depends on what state the device is in and will need to be decoded. See the Bits# manual but also the other functions herein that do the decoding for you.

Example

message = bits.read()

sendAnalog(AOUT1=0, AOUT2=0)[source]

sends a single analog output pulse uses up 1 win flip. pulse will continue until next win flip called. Actions are always 1 frame behind the request.

May conflict with trigger and goggle settings.

Example

bits.sendAnalog(4.5,-2.0) bits.win.flip()

setAnalog(AOUT1=0, AOUT2=0)[source]

Sets up Analog outputs in Bits# AOUT1 and AOUT2 are the two analog values required in volts. Analog commands are issued at the next win.flip() and actioned 1 video frame later.

Example

bits.set Analog(4.5,-2.2) bits.startAnalog() bits.win.flip()

setLUT(newLUT=None, gammaCorrect=False, LUTrange=1.0, contrast=None)[source]

SetLUT is only really needed for bits++ mode of bits# to set the look-up table (256 values with 14bits each). For the BitsPlusPlus device the default is to perform gamma correction here but on the BitsSharp it seems better to have the device perform that itself as the last step so gamma correction is off here by default. If no contrast has yet been set (it isn’t needed for other modes) then it will be set to 1 here.

setRTBoxMode(mode=['CB6', 'Down', 'Trigger'])[source]

Sets the RTBox mode data member - does not actually set the RTBox into this mode.

Example

bits.setRTBoxMode([‘CB6’,’Down’]) # set the mode bits.RTBoxEnable() # Enable RTBox emulation with # the preset mode.

sets the RTBox mode settings for a CRS CB6 button box. and for detection of ‘Down’ events only.

setStatusBoxMode(mode=['CB6', 'Down', 'Trigger', 'Analog'])[source]

Sets the statusBox mode data member - does not actually set the statusBox into this mode.

Example

bits.setStatusBoxMode([‘CB6’,’Down’]) # set the mode bits.statusBoxEnable() # Enable status Box emulation with # the preset mode.

sets the statusBox mode settings for a CRS CB6 button box. and for detection of ‘Down’ events only.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

setStatusBoxThreshold(threshold=None)[source]

Sets the threshold by which analog inputs must change to trigger a button press event. If None the threshold will be set very high so that no such events are triggered.

Can be used to change the threshold for analog events without having to re enable the status box system as a whole.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

setStatusEventParams(DINBase=1023, IRBase=63, TrigInBase=0, ADCBase=0, threshold=9999.99, mode=['up', 'down'])[source]

Sets the parameters used to determine if a status value represents a reportable event.

DIN_base = a 10 bit binary word specifying the expected starting values of the 10 digital input lines

IR_base = a 6 bit binary word specifying the expected starting values of the 6 CB6 IR buttons

Trig_base = the starting value of the Trigger input

mode = a list of event types to monitor can be ‘up’ or ‘down’ typically ‘down’ corresponds to a button press or when the input is being pulled down to zero volts.

Example:

bits.setStatusEventParams(DINBase=0b1111111111,
                          IRBase=0b111111,
                          TrigInBase=0,
                          ADCBase=0,
                          threshold = 3.4,
                          mode = ['down'])
bits.startStatusLog()
while not event
    #do some processing
    continue
bits.stopStatusLog()
res=getAllStatusEvents(0)
print(bits.res.time)

This ill start the event extraction process as if DINs and IRs are all ‘1’, Trigger is ‘0’ ADCs = 0 with an ADC threshold for change of 3.4 volts, and will only register ‘down’ events. Here we display the time stamp of the first event.

Note that the firmware in Display++ units varies over time and some features of this class may not work for all firmware versions. Also Display++ units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

setTrigger(triggers=0, onTime=0, duration=0, mask=65535)[source]

Quick way to set up triggers.

Triggers is a binary word that determines which triggers will be turned on.

onTime specifies the start time of the trigger within the frame (in S with 100uS resolution)

Duration specifies how long the trigger will last. (in S with 100uS resolution).

Note that mask only protects the digital output lines set by other activities in the Bits. Not other triggers.

Example:

` bits.setTrigger(0b0000000010, 2.0, 4.0, 0b0111111111) bits.startTrigger() `

Will issue a 4ms long high-going pulse, 2ms after the start of each frame on DOUT1 while protecting the value of DOUT 9.

setTriggerList(triggerList=None, mask=65535)[source]

Overaload of Bits# and Display++ Sets up Trigger pulses via the list method while preserving the analog output settings.

Sets up Trigger pulses in Bist++ using the fine grained method that can control every trigger line at 100uS intervals.

TriggerList should contain 1 entry for every 100uS packet (see getPackets) the binary word in each entry specifies which trigger line will be active during that time slot.

Note that mask only protects the digital output lines set by other activities in the Bits. Not other triggers.

Example

packet = [0]*self._NumberPackets packet[0] = 0b0000000010 bits.setTriggerList(packet)

Will sens a 100us pulse on DOUT1 at the start of the frame.

Example 2:

packet = [0]*self._NumberPackets packet[10] = 0b0000000010 packet[20] = 0b0000000001 bits.setTriggerList(packet) bits.statrtTrigger()

Will sens a 100us pulse on DOUT1 1000us after the start of the frame and a second 100us pusle on DOUT0 2000us after the start of the frame.

Triggers will continue until stopTrigger is called.

start()[source]

[Not currently implemented] Used to begin event collection by the device.

Not really needed as other members now do this.

startAnalog()[source]

will start sending analog signals on the next win flip and continue until stopped.

Example

bits.set Analog(4.5,-2.2) bits.startAnalog() bits.win.flip()

startStatusLog(t=60)[source]

Start logging data from the Bits#

Starts data logging in its own thread.

Will run for t seconds, defrault 60 or until stopStatusLog() is called.

Example:

bits.startStatusLog()
while not event
    #do some processing
    continue
bits.stopStatusLog()

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

statusBoxAddKeys(map)[source]

Add key mappings to an existing map. statusBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, triggers and CB6 IR input channels. The format for map is a list of tuples with each tuple containing the name of the RTBox button to be mapped and its source eg (‘btn1’,’Din1’) maps physical input Din1 to logical button btn1. statusBox has 23 logical buttons (btn1-23). Unlike RTBox buttons/events can only be partially mapped to multiple physical inputs. That is a logical button can be mapped to more than 1 physical input but a physical input can onloy be mapped to 1 logical button. So, this function over write any existing mappings if the physical input is the same.

Example:

bits.RTBoxSetKeys([('btn1','Din0),('btn2','Din1')])
bits.RTBoxAddKeys([('btn1','IRButtonA'),(('btn2','IRButtonB')])

Will link Din0 to button 1 and Din1 to button 2. Then adds IRButtonA and IRButtonB alongside the original mappings.

Now both hard wired and IR inputs will emulate the same logical button press.

To match with the CRS hardware description inputs are labelled as follows.

TrigIn, Din0 … Din9, IRButtonA … IRButtonF, AnalogIn1 … AnalogIn6

Logical buttons are numbered from 1 to 23.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

statusBoxDisable()[source]

Disables the detection of statusBox events. This is useful to stop the Bits# from reporting key presses When you no longer need them. And must be done before using any other data logging methods.

It undoes any button - input mappings

statusBoxEnable(mode=None, map=None, threshold=None)[source]

Sets up the stautsBox with preset or bespoke mappings and enables event detection.

stautsBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, tigers and CB6 IR input channels.

mode is a list of strings. Preset mappings provided via mode:

  • CB6 for the CRS CB6 IR response box connected mapped to btn1-6

  • IO for a three button box connected to Din0-2 mapped to btn1-3

  • IO6 for a six button box connected to Din0-5 mapped to btn1-6

  • IO10 for a ten button box connected to Din0-9 mapped to btn1-10

  • Trigger maps the trigIn to btn17

  • Analog maps the 6 analog inputs on a Bits# to btn18-23

If CB6 and IOx are used together the Dins are mapped from btn7 onwards.

If mode = None or is not set then the value of self.statusBoxMode is used.

Bespoke Mappings overwrite preset ones.

The format for map is a list of tuples with each tuple containing the name of the button to be mapped and its source eg (‘btn1’,’Din0’) maps physical input Din0 to logical button btn1.

Note the lowest number button event is Btn1

statusBox has 23 logical buttons (btn1-123). Buttons/events can be mapped to multiple physical inputs and stay mapped until reset.

mode is a string or list of strings that contains keywords to determine present mappings and modes for statusBox.

If mode includes ‘Down’ button events will be detected when pressed. If mode includes ‘Up’ button events will be detected when released. You can detect both types of event noting that the event detector will look for transitions and ignorewhat it sees as the starting state.

To match with the CRS hardware description inputs are labelled as follows.

TrigIn, Din0 … Din9, IRButtonA … IRButtonF, AnalogIn1 … AnalogIn6

Logical buttons are numbered from 1 to 23.

threshold sets the threshold by which analog inputs must change to trigger a button press event. If None the threshold will be set very high so that no such events are triggered. Analog inputs must cycle up and down by threshold to be detected as separate events. So if only ‘Up’ events are detected the input must go up by threshold, then come down again and then go back up to register 2 up events.

Example:

bits.statusBoxEnable(mode = 'Down'), map = [('btn1','Din0'), ('btn2','Din1')]

enables the stautsBox to detect Down events on buttons 1 and 2 where they are mapped to DIN0 and DIN1.

Example:

bits.statusBoxEnable(mode = ['Down','CB6'])

enables the status Box emulation to detect Down events on the standard CB6 IR response box keys.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

statusBoxKeysPressed(N=1)[source]

Check to see if (at least) the appropriate number of RTBox style key presses have been made.

Example

bits.statusBoxKeysPressed(5)

will return false until 5 button presses have been recorded.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

statusBoxSetKeys(map)[source]

Set key mappings: first resets existing then adds new ones. Does not reset any event that is not in the new list. statusBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, triggers and CB6 IR input channels. The format for map is a list of tuples with each tuple containing the name of the RTBox button to be mapped and its source eg (‘btn1’,’Din1’) maps physical input Din1 to logical button btn1.

statusBox has 17 logical buttons (btn1-17) Buttons/events can be mapped to multiple physical inputs and stay mapped until reset.

Example

bits.RTBoxSetKeys([(‘btn1’,’Din0),(‘btn2’,’IRButtonA’)])

Will link physical Din0 to logical button 1 and IRButtonA to button 2.

To match with the CRS hardware description inputs are labelled as follows.

TrigIn, Din0 … Din9, IRButtonA … IRButtonF, AnalogIn1 … AnalogIn6

Logical buttons are numbered from 1 to 23.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

statusBoxWait()[source]

Waits until (at least) one of RTBox style key presses have been made Pauses program execution in mean time.

Example

res = bits.statusBoxWait()

will suspend all other activity until 1 button press has been recorded and will then return a dict / structure containing results.

Results can be accessed as follows:

structure

res.dir, res.button, res.time

or dictionary

res[‘dir’], res[‘button’], res[‘time’]

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also DBits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

statusBoxWaitN(N=1)[source]

Waits until (at least) the appropriate number of RTBox style key presses have been made Pauses program execution in mean time.

Example

res = bits.statusBoxWaitN(5)

will suspend all other activity until 5 button presses have been recorded and will then return a list of Dicts containing the 5 results.

Results can be accessed as follows:

structure:

res[0].dir, res[0].button, res[0].time

or dictionary:

res[0]['dir'], res[0]['button'], res[0]['time']

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

stop()[source]

[Not currently implemented] Used to stop event collection by the device.

Not really needed as other members now do this.

stopAnalog()[source]

will stop sending analogs signals at the next win flip.

Example:

bits.set Analog(4.5,-2.2)
bits.startAnalog()
bits.win.flip()
while not response:
    #do some processing.
    bits.win.flip()
bits.stopAnalog()
bits.win.flip()
stopGoggles()[source]

Stop the stereo goggles from toggling

Example:

bits.startGoggles(0,1)
bits.win.flip()
while not response
    bits.win.flip()
    #do some processing
bits.stopGoggles()
bits.win.flip()

Starts toggling the goggles with the right eye open in sync with the first win.flip(0) within the loop. The open eye will alternate.

Note it is safer to leave the goggles toggling forever, ie to never call stopGoggles().

stopStatusLog()[source]
Stop logging data from the Bits#

and extracts the raw status values and significant events and puts them in statusValues and statusEvents.

statusValues will end up containing dict like objects of the following style: sample, time, trigIn, DIN[10], DWORD, IR[6], ADC[6]

They can be accessed as statusValues[i][‘sample’] or statusValues[i].sample, statusValues[x].ADC[j].

StatusEvents will end up containing dict like objects of the following style: source, input, direction, time

The data can be accessed as statusEvents[i][‘time’] or statusEvents[i].time

Waits for _statusLog to finish properly so can introduce a timing delay.

Example:

bits.startStatusLog()
while not event
    #do some processing
    continue
bits.stopStatusLog()
print(bits.statusValues[0].time)
print(bits.statusEvents[0].time)

Will display the time stamps of the first starus value recorded and the first meaningful event.

Note that the firmware in Bits# units varies over time and some features of this class may not work for all firmware versions. Also Bits# units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

stopTrigger()[source]

Stop sending triggers at the next win flip.

Example:

bits.setTrigger(0b0000000010, 2.0, 4.0, 0b0111111111)
bits.startTrigger()
while imageOn:
    #do some processing
    continue
bits.stopTrigger()
bits.win.flip()
property temporalDithering

Temporal dithering can be set to True or False

property win

The window that this box is attached to

class psychopy_crs.bits.DisplayPlusPlus(*args, **kwargs)[source]

A Display++ is Bits# box inside and LCD monitor so this class is just a wrapper that reminds people with a Display++ that they are using it. However unlike the Bits# you may not have any analog connections on a Display++ unless you purchased that option.

Everything in the Bits# class should work but any analog values sent or read will be spurious unless you have the analog hardware installed.

Note that the firmware in Display++ units varies over time and some features of this class may not work for all firmware versions. Also Display++ units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particualar it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

RTBox commands that reset the key mapping have been found not to work one some firmware.

class psychopy_crs.bits.DisplayPlusPlusTouch(*args, **kwargs)[source]

A Display++ is Bits# box inside and LCD monitor but its also possible to add a touch screen option to Display++ and this class will give access to that.

Otherwise this class is just a wrapper to the Bits# class. However unlike the Bits# you may not have any analog connections on a Display++ unless you purchased that option.

Everything in the Bits# class should work but any analog values sent or read will be spurious unless you have the analog hardware installed.

Note that the firmware in Display++ units varies over time and some features of this class may not work for all firmware versions. Also Display++ units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

RTBox commands that reset the key mapping have been found not to work one some firmware.

RTBoxEnable(mode=('CB6', 'Down', 'Trigger'), map=None)[source]

Overaload RTBoxEnable for Display++ with touch screen. Sets up the RTBox with preset or bespoke mappings and enables event detection.

RTBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, tigers and CB6 IR input channels.

Mode is a list of strings. Preset mappings provided via mode:

CB6 for the CRS CB6 IR response box. IO for a three button box connected to Din0-2 IO6 for a six button box connected to Din0-5

If mode = None or is not set then the value of self.RTBoxMode is used.

Bespoke Mappings over write preset ones.

The format for map is a list of tuples with each tuple containing the name of the RT Box button to be mapped and its source eg (‘btn1’,’Din0’) maps physical input Din0 to logical button btn1.

Note the lowest number button event is Btn1

RTBox has four logical buttons (btn1-4) and three auxiliary events (light, pulse and trigger) Buttons/events can be mapped to multiple physical inputs and stay mapped until reset.

Mode is a list of string or list of strings that contains keywords to determine present mappings and modes for RTBox.

If mode includes ‘Down’ button events will be detected when pressed. If mode includes ‘Up’ button events will be detected when released. You can detect both types of event but note that pulse, light and trigger events dont have an ‘Up’ mode.

If Trigger is included in mode the trigger

event will be mapped to the trigIn connector.

Example

bits.RTBoxEnable(mode = ‘Down’), map = [(‘btn1’,’Din0’), (‘btn2’,’Din1’)]

enable the RTBox emulation to detect Down events on buttons 1 and 2 where they are mapped to DIN0 and DIN1.

Example

bits.RTBoxEnable(mode = [‘Down’,’CB6’])

enable the RTBox emulation to detect Down events on the standard CB6 IR response box keys.

getAllTouchResponses()[source]

get all the touch screen presses from the events on the input buffer then reads them. Returns a list of dict like objects with four members ‘x’,’y’,’dir’ and ‘time’ ‘x and y’ are the x and y coordinates pressed. ‘dir’ is the direction of the event

eg ‘touched’ for presses and ‘relased’ for releases.

‘time’ is the timestamp associated with the event. these values can be read as a structure:

res=getAllTouchResponses() res[0].dir, res[0].x, rest[0].time

or dirctionary

res[0][‘dir’], res[0][‘x’], res[0][‘time’]

Note even if only 1 response is requested the result is

a 1 item long list of dict like objects.

Note in theory this could be used to get multiple responses

but in practice the touch screen reports every slight movement so the Logging methods are better.

Note this function does not start touch screen

recording so should only be called when there appears to be data waiting. So you need to call touchEnable() before and touchDisable after this function

Example

bits.touchEnable() while not event:

# do some processing continue

bits.touchDisable() res=getAllTouchResponses(3) print(res[0].time)

Will put the touch screen into continuous reading while doing some task and at the end get all the tocuhes are display the timestamp of the first one.

getTouchEvent(N=0, distance=None, t=None, type=None)[source]
Scans the touch log to return the Nth touch event.

You need to run getTouchLog before you run this function.

Returns as list of Dict like structures with members

time, x, y, and dir

time is the time stamp of the event. x and y are the x and y locations of the event. direction is the type of event: ‘touched’, ‘released’

These values can be read as a structure: res=getTouchResponses(3) res[0].dir, res[0].x, res[0].time or dictionary res[0][‘dir’], res[0][‘x’], res[0][‘time’]

Example

bits.startTouchLog() while not event:

#do some processing continue

bits.stopTouchLog() bits.getTouchLog() res=bits.getTouchEvent(N=10, distance=20, time=0.001, type=’touched’) print(res.time)

Will extract the 10th touch events (ingnoreing releases) that are 20 pixels and 1 ms apart.

getTouchEvents(distance=None, t=None, type=None)[source]
Scans the touch log to extract touch events.

You need to run getTouchLog before you run this function.

Returns as list of Dict like structures with members time, x, y, and dir

time is the time stamp of the event. x and y are the x and y locations of the event. direction is the type of event: ‘touched’, ‘released’

These values can be read as a structure: res=getTouchResponses(3) res[0].dir, res[0].x, res[0].time or dictionary res[0][‘dir’], res[0][‘x’], res[0][‘time’]

Example

bits.startTouchLog() while not event:

#do some processing continue

bits.stopTouchLog() bits.getTouchLog() res=bits.getTouchEvents(distance=20, t=0.001, type=’touched’) print(res[0][‘time’]

Will extract touch events (not releases) that are 20 pixels and 1 ms apart.

getTouchLog(caution=True, checkTime=None)[source]

Reads out the touch screen cue and checks for a known error Returns a list of dict like objects with four members ‘x’,’y’,’dir’ and ‘time’ ‘x and y’ are the x and y coordinates pressed. ‘dir’ is the direction of the event

eg ‘touched’ for presses and ‘released’ for releases.

‘time’ is the timestamp associated with the event. these values can be read as a structure:

res=getTouchResponses(3) res[0].dir, res[0].x, res[0].time

or dictionary

res[0][‘dir’], res[0][‘x’], res[0][‘time’]

Note even if only 1 response is requested the result is

a 1 item long list of dict like objects.

Note in theory this could be used to get multiple responses

but in practice the touch screen reports every slight movements so the Logging methods, getTouchResponse or getAllTouchResponses are better.

Note this function does not start touch screen

recording so should only be called when there appears to be data waiting. So you need to call touchEnable() before and touchDisable after this function.

checkTime specifies a time between the first and second touches after which a warning of a possible error will be issued and the error may be corrected.

caution: If True tell the function to check for a known Display++ error if you don’t have that error or you don’t care about it you should set this to False.

Example

bits.startTouchLog() while not event:

#do some processing continue

bits.stopTouchLog() res=bits.getTouchLog(caution = False)

Will get all the screen touches without checking for errors.

getTouchResponse()[source]

checks for (at least) one touch screen press on the input buffer then reads it. Returns a dict like object with four members ‘x’,’y’,’dir’ and ‘time’ ‘x and y’ are the x and y coordinates pressed. ‘dir’ is the direction of the event

eg ‘touched’ for presses and ‘relased’ for releases.

‘time’ is the timestamp associated with the event. these values can be read as a structure:

res=getTouchGetResponse() res.dir, res.x, rest.time

or dirctionary

res[‘dir’], res[‘x’], res[‘time’]

Note this function does not start touch screen

recording so should only be called when there appears to be data waiting. So you need to call touchEnable() before and touchDisable after this function.

Example

bits.touchEnable() while not event:

# do some processing continue

bits.touchDisable() res=getTouchResponse() print(res.time)

Will put the touch screen into continuous reading while doing some task and at the end get all the tocuhes are display the timestamp of the first one.

getTouchResponses(N=1)[source]

checks for (at least) an appropriate number of touch screen presses on the input buffer then reads them. Returns a list of dict like objects with four members ‘x’,’y’,’dir’ and ‘time’ ‘x and y’ are the x and y coordinates pressed. ‘dir’ is the direction of the event

eg ‘touched’ for presses and ‘released’ for releases.

‘time’ is the timestamp associated with the event. these values can be read as a structure:

res=getTouchResponses(3) res[0].dir, res[0].x, res[0].time

or dictionary

res[0][‘dir’], res[0][‘x’], res[0][‘time’]

Note even if only 1 response is requested the result is

a 1 item long list of dict like objects.

Note in theory this could be used to get multiple responses

but in practice the touch screen reports every slight movements so the Logging methods, getTouchResponse or getAllTouchResponses are better.

Note this function does not start touch screen

recording so should only be called when there appears to be data waiting. So you need to call touchEnable() before and touchDisable after this function.

Example

bits.touchEnable() while not event:

# do some processing continue

bits.touchDisable() res=getTouchResponses(3) print(res[0].time)

Will put the touch screen into continuous reading while doing some task and at the end get the first 3 tocuhes are display the timestamp of the first one.

setTouchEventParams(distance=None, t=None, type=None)[source]
Sets the parameters for touch event detection.

Distance is how far the touch should move to count as a new touch. Time is how long should lapse between touches for the second one to count.

Example

bits.startTouchLog() while not event:

#do some processing continue

bits.stopTouchLog() res=bits.getTouchLog() bits.setTouchEventParams(distance=20, t=0.001, type=’touched’) events=bits.getTouchEvents()

Will extract touch events (not releases) that are 20 pixels and 1 ms apart.

startTouchLog(t=60)[source]

Start logging data from the touch screen. Turns on the touch screen.

Example

bits.startTouchLog() while not event:

#do some processing continue

bits.stopTouchLog() res=bits.getTouchLog()

statusBoxEnable(mode=None, map=None, threshold=None)[source]

Sets up the statusBox with preset or bespoke mappings and enables event detection.

stautsBox events can be mapped to a number of physical events on Bits# They can be mapped to digital input lines, tigers and CB6 IR input channels.

Mode is a list of strings. Preset mappings provided via mode:

CB6 for the CRS CB6 IR response box connected mapped to btn1-6 IO for a three button box connected to Din0-2 mapped to btn1-3 IO6 for a six button box connected to Din0-5 mapped to btn1-6 IO10 for a ten button box connected to Din0-9 mapped to btn1-10 Trigger maps the trigIn to btn17

if CB6 and IOx are used the Dins are mapped from btn7 onwards.

If mode = None or is not set then the value of self.statusBoxMode is used.

Bespoke Mappings over write preset ones.

The format for map is a list of tuples with each tuple containing the name of the

button to be mapped and its source

eg (‘btn1’,’Din0’) maps physical input Din0 to logical button btn1.

Note the lowest number button event is Btn1

statusBox has 17 logical buttons (btn1-17). Buttons/events can be mapped to multiple physical inputs and stay mapped until reset.

Mode is a string or list of strings that contains keywords to determine present mappings and modes for statusBox.

If mode includes ‘Down’ button events will be detected when pressed. If mode includes ‘Up’ button events will be detected when released. You can detect both types of event noting that the event detector will look for transitions and ignorewhat it sees as the starting state.

Example

bits.statusBoxEnable(mode = ‘Down’), map = [(‘btn1’,’Din0’), (‘btn2’,’Din1’)]

enable the stautsBox to detect Down events on buttons 1 and 2 where they are mapped to DIN0 and DIN1.

Example

bits.statusBoxEnable(mode = [‘Down’,’CB6’])

enable the statusBox emulation to detect Down events on the standard CB6 IR response box keys.

Note that the firmware in Display++ units varies over time and some features of this class may not work for all firmware versions. Also Display++ units can be configured in various ways via their config.xml file so this class makes certain assumptions about the configuration. In particular it is assumed that all digital inputs, triggers and analog inputs are reported as part of status updates. If some of these report are disabled in your config.xml file then ‘status’ and ‘event’ commands in this class may not work.

stopTouchLog()[source]

Stop logging data from the Bits# Waits for _getLog to finish properly so can introduce a timing delay.

Does not automatically extract the touch log.

Example

bits.startTouchLog() while not event:

#do some processing continue

bits.stopTouchLog() res=bits.getTouchLog()

touchDisable()[source]

Turns off the touch screen.

Example

bits.touchEnable() res = bits.touchWait() bits.touchDisable() print(res.time)

Enables touch screen, waits for a touch, disables touch screen and displays the timestamp of the touch.

touchEnable()[source]

Turns on the touch screen. Any presses will now be reported

Example

bits.touchEnable() res = bits.touchWait() bits.touchDisable() print(res.time)

Enables touch screen, waits for a touch, disables touch screen and displays the timestamp of the touch.

touchPressed(N=1)[source]

Check to see if (at least) the appropriate number of touch screen events have been made

Not accurate due to touch jitter creating extra events but can be used to detect first press.

Example

bits.touchEnable() while not bits.touchPressed(5):

# do some processing continue

bits.touchDisable()

Will do some processing until 5 screen couches are recorded.

touchWait()[source]

Waits until (at least) one touch screen event have been made. Then reports the response. Pauses programe execution in mean time.

Example

bits.touchEnable() bits.touchWait(): bits.touchDisable()

Will pause until 1 screen touch recorded.

touchWaitN(N=1)[source]

Waits until (at least) the appropriate number of touch screen events have been made then reports the responses. Pauses program execution in mean time.

Not every accurate due to touch jitter creating extra events.

Example

bits.touchEnable() bits.touchWaitN(5): bits.touchDisable()

Will pause until 5 screen touches are recorded.

class psychopy_crs.bits.button(direction='None', button=0, t=0)[source]

clever dict like object or object like dict for button presses

class psychopy_crs.bits.event(source='None', t=0, input=0, direction='None')[source]

clever dict like object or object like dict for Bits# status events

psychopy_crs.bits.init()[source]

DEPRECATED: we used to initialise Bits++ via the compiled dll This only ever worked on windows and BitsSharp doesn’t need it at all Note that, by default, Bits++ will perform gamma correction that you don’t want (unless you have the CRS calibration device) (Recommended that you use the BitsPlusPlus class rather than calling this directly)

psychopy_crs.bits.reset(noGamma=True)[source]

Reset the Bits++ box via the USB cable by initialising again Allows the option to turn off gamma correction

psychopy_crs.bits.setVideoMode(videoMode)[source]

Set the video mode of the Bits++ (win32 only) bits8BITPALETTEMODE = 0x00000001 # normal vsg mode NOGAMMACORRECT = 0x00004000 # No gamma correction mode GAMMACORRECT = 0x00008000 # Gamma correction mode VIDEOENCODEDCOMMS = 0x00080000 (Recommended that you use the BitsLUT class rather than calling this directly)

class psychopy_crs.bits.status(sample=0, t=0, trigIn=0, bitsvals=0, IR=0, ADCs=0.0)[source]

clever dict like object or object like dict for Bits# status messages

class psychopy_crs.bits.touch(t=0, x=0, y=0, direction='down')[source]

clever dict like object or object like dict for touch screen presses


Back to top