Skip to content
Snippets Groups Projects
Select Git revision
  • a08cdf93ac31c13095a7bf5e1243ef25fcc75432
  • master default protected
  • ChangeBlindnessEEG
3 results

trial_runner.py

Blame
  • trial_runner.py 5.38 KiB
    from os.path import basename, splitext
    from random import randint
    from psychopy import core, event
    
    
    def start(win, fixation_screen, pause_screen, stim_list, stim_order, maker, data_file, hardware=None):
        # Set trial constants
        start_alpha = 1.0
        change_time = 6000  # milliseconds # TODO:change happens in 2 sec blocks
        change_rate = 1000 / 60.0
        change_value = change_time / change_rate
        constants = (start_alpha, change_time, change_rate, change_value)
        '''
        all_stim_list = []
        for i in xrange(len(stim_order) / len(stim_list)):
            shuffle(stim_list)
            all_stim_list.extend(stim_list)
        '''
        trial_clock = core.Clock()
    
        for trial_number, conditions in enumerate(stim_order):
            block_number = ((trial_number + 1) / len(stim_order)) + 1
    
            stim_pairs = stim_list[trial_number]
            # print stim_pairs
            stim_pair = select_stimuli(stim_pairs, conditions[0], conditions[1])
            # print stim_pair
            image_1 = basename(stim_pair[1])
            image_2 = basename(stim_pair[0])
            change_type = str(conditions[1])
            stimuli_number = image_1.split('_')[0]
            stimuli_orientation = image_1.split('_')[1]
            trial_info = {'img1': image_1, 'img2': image_2, 'trl-': trial_number, 'bloc': block_number,
                          'img#': stimuli_number, 'orie': stimuli_orientation, 'CTyp': change_type}
    
            stim_pair = (maker(win, stim_pair[0]), maker(win, stim_pair[1]))
    
            if hardware:
                hardware.sync()
            display_fixation(win, fixation_screen, 1000, 1500)
            if hardware:
                hardware.send_event(key='imag', label='ImageAppears', description='Image appeared on-screen',
                                    table=trial_info)
            trial(win, trial_clock, stim_pair, constants)
            # TODO:Move response to post-image so no motor artifact in trial. Include randomized response buttons for each
            # TODO: trial to avoid preparatory activity, indicate onscreen what each button represents for that trial (e.g. 1=change detected, 4=change not detected)
            pause, response, response_time = check_response(event.getKeys(timeStamped=trial_clock))
            if pause:
                escape = pause_screen.show()
                if escape:
                    break
            else:
                win.flip(clearBuffer=True)
            data_file.write_data([block_number,
                                  trial_number,# 'Cumulative_trial_number' \
                                  image_1,# 'Image_Start' \
                                  image_2,# 'Image_Finish' \
                                  stimuli_number,# 'Stimuli_Number' \
                                  stimuli_orientation,# 'Stimuli_Orientation' \
                                  change_type,# 'Change' \
                                  str(conditions[1] is not None),# 'Correct_Response' \
                                  str(response),# 'Response' \
                                  str(response and conditions[1]),# 'Correct' \
                                  str(response_time),# 'Response_Time' \
                                  str(trial_clock.getTime())# 'Trial_time'
                                  ])
    
    
    def trial(win, clock, stimuli, constants):
        ch_value = constants[3]
        win.callOnFlip(clock.reset)
        for j in xrange(0, len(stimuli), 2):
            stimuli[j].draw()
            stimuli[j + 1].draw()
            win.flip()
            for i in xrange(int(ch_value) - 1):
                stimuli[j].draw()
                if stimuli[j+1].opacity > 0.0:
                    stimuli[j + 1].opacity -= 1 / ch_value
                stimuli[j + 1].draw()
                win.flip()
    
    
    def select_stimuli(stim_list, orientation, abs_pres):
        """
    
        :param stim_list: list of 4 potential stimuli variants
        :param orientation: Which image orientation to use, left or right
        :param abs_pres: Which presentation style to perform, disappear or appear
        :return: list of stimuli in order of presentation style, 2nd image fades out while 1st image emerges.
        """
        return_list = [None, None]
        if abs_pres is 'present':
            alt_abs_pres = 'in'
        elif abs_pres is 'absent':
            alt_abs_pres = 'neither'
        else:
            alt_abs_pres = None
        for stim in stim_list:
            stim_split = splitext(stim.lower())[0].split('_')
            if orientation.lower() in stim_split:
                if abs_pres:
                    if abs_pres in stim_split or alt_abs_pres in stim_split:
                        return_list[0] = stim
                    else:
                        return_list[1] = stim
                elif 'present' in stim_split or 'in' in stim_split:
                    return_list = list((stim, stim))
                    return return_list
        return return_list
    
    
    def display_fixation(win, fixation_screen, ISI_min, ISI_max):
        fixation_screen.draw()
        win.flip()
        ISI = randint(ISI_min, ISI_max) / 1000.0
        core.wait(ISI)
        return ISI
    
    
    def check_response(keys_tuple):
        # # Checking for and clearing out all uses of 'esc' from the keys_tuple list
        #
        pause = False
        pop_list = []
        for index, key_tuple in enumerate(keys_tuple):
            if 'escape' in key_tuple:
                pop_list.insert(0, index)
                pause = True
        for popper in pop_list:
            keys_tuple.pop(popper)
    
        # # Check if there's any responses left, and if so, return the first one.
        #
        response, response_time = (None, None)
        if keys_tuple:
            response_tuple = keys_tuple[0]
            response, response_time = response_tuple
    
        return pause, response, response_time