%run ../check_config.py from psychopy import gui exp_name = 'Change Detection' exp_info = { 'participant': '', 'gender': ('male', 'female'), 'age':'', 'left-handed':False } dlg = gui.DlgFromDict(dictionary=exp_info, title=exp_name) print exp_info from psychopy import gui, core exp_name = 'Change Detection' exp_info = { 'participant': '', 'gender': ('male', 'female'), 'age':'', 'left-handed':False } dlg = gui.DlgFromDict(dictionary=exp_info, title=exp_name) if dlg.OK == False: core.quit() # user pressed cancel, so we quit exp_info['exp_name'] = exp_name from psychopy import data exp_info['date'] = data.getDateStr() # DON'T RUN THIS from psychopy import visual visual.Window() # don't run this line from psychopy import visual, core win = visual.Window() core.wait(3) # seconds win.close() win = visual.Window(size=(600,400), color='white') core.wait(3) win.close() win = visual.Window(fullscr=True) core.wait(3) win.close() from psychopy import visual, core win = visual.Window(size=(600,400), color='white', units='pix') bitmap = visual.ImageStim(win, 'images/1a.jpg', size=(600,400)) core.wait(3) win.close() win = visual.Window(size=(600,400), color='white', units='pix') bitmap = visual.ImageStim(win, 'images/1a.jpg', size=(600,400)) bitmap.draw() core.wait(3) win.close() win = visual.Window(size=(600,400), color='white', units='pix') bitmap = visual.ImageStim(win, 'images/1a.jpg', size=(600,400)) bitmap.draw() # draw bitmap on the window win.flip() # make bitmap visible core.wait(3) win.close() win = visual.Window(size=(600,400), color='white', units='pix') bubble = visual.Circle(win, fillColor='black', lineColor='black', radius=30) bubble.draw() win.flip() core.wait(3) # seconds win.close() win = visual.Window(size=(600,400), color='white', units='pix') text = visual.TextStim(win, text='Press spacebar to start the trial', color='red', height=20) text.draw() win.flip() core.wait(3) # seconds win.close() Before each trial we need to be able to update images and their orientations. This is generally done using `set` commands, such as `setImage` and `setOri` in our example: from psychopy import visual, core win = visual.Window(size=(600,400), color='white', units='pix') bitmap = visual.ImageStim(win, 'images/1a.jpg', size=(600,400)) bitmap.draw() # draw bitmap on the window win.flip() # make bitmap visible core.wait(3) bitmap.setImage('images/2a.jpg') bitmap.setOri(180) bitmap.draw() win.flip() core.wait(3) win.close() from psychopy import visual, core, event win = visual.Window(size=(600,400), color='white', units='pix') text = visual.TextStim(win, text='Press spacebar to start the trial', color='red', height=20) text.draw() win.flip() keys = event.waitKeys(keyList=['space', 'escape']) print keys if 'escape' in keys: win.close() else: print 'Start of the trial' win.close() from psychopy import visual, core win = visual.Window(size=(600,400), color='white', units='pix') bitmap = visual.ImageStim(win, 'images/1a.jpg', size=(600,400)) # define and start a clock rt_clock = core.Clock() rt_clock.reset() # this is equivallent to core.wait(3) while rt_clock.getTime() < 3: bitmap.draw() # draw bitmap on the window win.flip() # make bitmap visible win.close() from psychopy import visual, core nframes = 12 # will see stimulus for 12 frames, i.e., 200 ms on most monitors win = visual.Window(size=(600,400), color='white', units='pix') bitmap = visual.ImageStim(win, 'images/1a.jpg', size=(600,400)) core.wait(2) # blank screen initially for frame in range(nframes): bitmap.draw() # draw bitmap on the window win.flip() # make bitmap visible win.flip() core.wait(2) # blank screen afterwards win.close() from psychopy import visual, core scrsize = (600,400) win = visual.Window(size=scrsize, color='white', units='pix') bitmap1 = visual.ImageStim(win, 'images/1a.jpg', size=scrsize) bitmap2 = visual.ImageStim(win, 'images/1b.jpg', size=scrsize) for i in range(5): bitmap1.draw() # draw bitmap on the window win.flip() # make bitmap visible core.wait(.5) bitmap2.draw() win.flip() core.wait(.5) win.close() from psychopy import visual, core scrsize = (600,400) win = visual.Window(size=scrsize, color='white', units='pix') bitmap1 = visual.ImageStim(win, 'images/1a.jpg', size=scrsize) bitmap2 = visual.ImageStim(win, 'images/1b.jpg', size=scrsize) bitmap = bitmap1 for i in range(10): # note that we now need 10, not 5 iterations # change the bitmap if bitmap == bitmap1: bitmap = bitmap2 else: bitmap = bitmap1 bitmap.draw() win.flip() core.wait(.5) win.close() from psychopy import visual, core, event scrsize = (600,400) win = visual.Window(size=scrsize, color='white', units='pix') bitmap1 = visual.ImageStim(win, 'images/1a.jpg', size=scrsize) bitmap2 = visual.ImageStim(win, 'images/1b.jpg', size=scrsize) bitmap = bitmap1 # Initialize clock to register response time rt_clock = core.Clock() rt_clock.reset() # set rt clock to 0 done = False # Empty the keypresses list keys = None # Start the trial # Stop trial if spacebar or escape has been pressed, or if 30s have passed while keys is None and rt_clock.getTime() < 30: # Switch the image if bitmap == bitmap1: bitmap = bitmap2 else: bitmap = bitmap1 bitmap.draw() # Show the new screen we've drawn win.flip() # For 0.5s, listen for a spacebar or escape press keys = event.waitKeys(maxWait=.5, keyList=['space', 'escape'], timeStamped=rt_clock) print keys win.close() from psychopy import visual, core, event scrsize = (600,400) win = visual.Window(size=scrsize, color='white', units='pix') bitmap1 = visual.ImageStim(win, image='images/1a.jpg', size=scrsize) bitmap2 = visual.ImageStim(win, image='images/1b.jpg', size=scrsize) bitmap = bitmap1 # Initialize clock to register response time rt_clock = core.Clock() rt_clock.reset() # set rt clock to 0 # Initialize clock to control stimulus presentation time change_clock = core.Clock() # Empty the keypresses list keys = [] # Start the trial # Stop trial if spacebar or escape has been pressed, or if 30s have passed while len(keys) == 0 and rt_clock.getTime() < 30: # Switch the image if bitmap == bitmap1: bitmap = bitmap2 else: bitmap = bitmap1 bitmap.draw() # Show the new screen we've drawn win.flip() # For 0.5s, listen for a spacebar or escape press change_clock.reset() while change_clock.getTime() <=.5: keys = event.getKeys(keyList=['space', 'escape']) print keys if len(keys) > 0: rt = rt_clock.getTime() break print keys, rt win.close() # Draw bubbles of increasing radius at random positions for radius in range(n_bubbles): bubble.setRadius(radius/2.) bubble.setPos(((rnd.random()-.5) * scrsize[0], (rnd.random()-.5) * scrsize[1] )) bubble.draw() # Analyze the keypress if keys: if 'escape' in keys: # Escape press = quit the experiment break else: # Spacebar press = correct change detection; register response time acc = 1 rt = rt_clock.getTime() else: # No press = failed change detection; maximal response time acc = 0 rt = timelimit # Display the start message start_message.draw() win.flip() # Start the main loop that goes through all trials for trial in trials: # Wait for spacebar press to start (or escape to quit) keys = event.waitKeys(keyList=['space', 'escape']) # Set the images, set the orientation im_fname = os.path.join(impath, trial['im']) bitmap1.setImage(im_fname + asfx) bitmap1.setFlipHoriz(trial['ori']) bitmap2.setImage(im_fname + bsfx) bitmap2.setFlipHoriz(trial['ori']) # Show stimuli, collect responses # ... %load script_final.py #=============== # Import modules #=============== import os # for file/folder operations import numpy.random as rnd # for random number generators from psychopy import visual, event, core, gui, data #============================================== # Settings that we might want to tweak later on #============================================== datapath = 'data' # directory to save data in impath = 'images' # directory where images can be found imlist = ['1','2','3','4','5','6'] # image names without the suffixes asfx = 'a.jpg' # suffix for the first image bsfx = 'b.jpg' # suffix for the second image scrsize = (600,400) # screen size in pixels timelimit = 30 # image freezing time in seconds changetime = .5 # image changing time in seconds n_bubbles = 40 # number of bubbles overlayed on the image #======================================== # Store info about the experiment session #======================================== # Get subject name, gender, age, handedness through a dialog box exp_name = 'Change Detection' exp_info = { 'participant': '', 'gender': ('male', 'female'), 'age':'', 'left-handed':False } dlg = gui.DlgFromDict(dictionary=exp_info, title=exp_name) # If 'Cancel' is pressed, quit if dlg.OK == False: core.quit() # Get date and time exp_info['date'] = data.getDateStr() exp_info['exp_name'] = exp_name # Create a unique filename for the experiment data if not os.path.isdir(datapath): os.makedirs(datapath) data_fname = exp_info['participant'] + '_' + exp_info['date'] data_fname = os.path.join(datapath, data_fname) #======================== # Prepare condition lists #======================== # Check if all images exist for im in imlist: if (not os.path.exists(os.path.join(impath, im+asfx)) or not os.path.exists(os.path.join(impath, im+bsfx))): raise Exception('Image files not found in image folder: ' + str(im)) # Randomize the image order rnd.shuffle(imlist) # Create the orientations list: half upright, half inverted (rotated by 180 deg) orilist = [0,180]*(len(imlist)/2) # Randomize the orientation order rnd.shuffle(orilist) #=============================== # Creation of window and stimuli #=============================== # Open a window win = visual.Window(size=scrsize, color='white', units='pix', fullscr=False) # Define trial start text start_message = visual.TextStim(win, text="Press spacebar to start the trial. Hit spacebar again when you detect a change.", color='red', height=20) # Define bitmap stimulus (contents can still change) bitmap1 = visual.ImageStim(win, size=scrsize) bitmap2 = visual.ImageStim(win, size=scrsize) # Define a bubble (position and size can still change) bubble = visual.Circle(win, fillColor='black', lineColor='black') #========================== # Define the trial sequence #========================== # Define a list of trials with their properties: # - Which image (without the suffix) # - Which orientation stim_order = [] for im, ori in zip(imlist, orilist): stim_order.append({'im': im, 'ori': ori}) trials = data.TrialHandler(stim_order, nReps=1, extraInfo=exp_info, method='sequential', originPath=datapath) #===================== # Start the experiment #===================== # Initialize two clocks: # - for image change time # - for response time change_clock = core.Clock() rt_clock = core.Clock() # Run through the trials for trial in trials: # Display trial start text start_message.draw() win.flip() # Wait for a spacebar press to start the trial, or escape to quit keys = event.waitKeys(keyList=['space', 'escape']) # Set the images, set the orientation im_fname = os.path.join(impath, trial['im']) bitmap1.setImage(im_fname + asfx) bitmap1.setOri(trial['ori']) bitmap2.setImage(im_fname + bsfx) bitmap2.setOri(trial['ori']) bitmap = bitmap1 # Set the clocks to 0 change_clock.reset() rt_clock.reset() # Empty the keypresses list # Leave an 'escape' press in for immediate exit if 'space' in keys: keys = [] # Start the trial # Stop trial if spacebar or escape has been pressed, or if 30s have passed while not keys and rt_clock.getTime() < timelimit: # Switch the image if bitmap == bitmap1: bitmap = bitmap2 else: bitmap = bitmap1 bitmap.draw() # Draw bubbles of increasing radius at random positions for radius in range(n_bubbles): bubble.setRadius(radius/2.) bubble.setPos(((rnd.random()-.5) * scrsize[0], (rnd.random()-.5) * scrsize[1] )) bubble.draw() # Show the new screen we've drawn win.flip() # For the duration of 'changetime', # Listen for a spacebar or escape press change_clock.reset() while change_clock.getTime() <= changetime: keys = event.getKeys(keyList=['space','escape']) if keys: break # Analyze the keypress if keys: if 'escape' in keys: # Escape press = quit the experiment break else: # Spacebar press = correct change detection; register response time acc = 1 rt = rt_clock.getTime() else: # No press = failed change detection; maximal response time acc = 0 rt = timelimit # Add the current trial's data to the TrialHandler trials.addData('rt', rt) trials.addData('acc', acc) # Advance to the next trial #====================== # End of the experiment #====================== # Save all data to a file trials.saveAsWideText(data_fname + '.csv', delim=',') # Quit the experiment win.close() #=============== # Import modules #=============== import os # for file/folder operations import numpy.random as rnd # for random number generators from psychopy import visual, event, core, gui, data #============================================== # Settings that we might want to tweak later on #============================================== datapath = 'data' # directory to save data in impath = 'images' # directory where images can be found imlist = ['1','2','3','4','5','6'] # image names without the suffixes asfx = 'a.jpg' # suffix for the first image bsfx = 'b.jpg' # suffix for the second image scrsize = (600,400) # screen size in pixels timelimit = 30 # image freezing time in seconds changetime = .5 # image changing time in seconds n_bubbles = 40 # number of bubbles overlayed on the image #======================================== # Store info about the experiment session #======================================== # Get subject name, gender, age, handedness through a dialog box exp_name = 'Change Detection' exp_info = { 'participant': '', 'gender': ('male', 'female'), 'age':'', 'left-handed':False } dlg = gui.DlgFromDict(dictionary=exp_info, title=exp_name) # If 'Cancel' is pressed, quit if dlg.OK == False: core.quit() # Get date and time exp_info['date'] = data.getDateStr() exp_info['exp_name'] = exp_name # Create a unique filename for the experiment data if not os.path.isdir(datapath): os.makedirs(datapath) data_fname = exp_info['participant'] + '_' + exp_info['date'] data_fname = os.path.join(datapath, data_fname) #======================== # Prepare condition lists #======================== # Check if all images exist for im in imlist: if (not os.path.exists(os.path.join(impath, im+asfx)) or not os.path.exists(os.path.join(impath, im+bsfx))): raise Exception('Image files not found in image folder: ' + str(im)) # Randomize the image order rnd.shuffle(imlist) # Create the orientations list: half upright, half inverted (rotated by 180 deg) orilist = [0,180]*(len(imlist)/2) # Randomize the orientation order rnd.shuffle(orilist) #=============================== # Creation of window and stimuli #=============================== # Open a window win = visual.Window(size=scrsize, color='white', units='pix', fullscr=False) # Define trial start text start_message = visual.TextStim(win, text="Press spacebar to start the trial. Hit spacebar again when you detect a change.", color='red', height=20) # Define bitmap stimulus (contents can still change) bitmap1 = visual.ImageStim(win, size=scrsize) bitmap2 = visual.ImageStim(win, size=scrsize) # Define a bubble (position and size can still change) bubble = visual.Circle(win, fillColor='black', lineColor='black') #========================== # Define the trial sequence #========================== # Define a list of trials with their properties: # - Which image (without the suffix) # - Which orientation stim_order = [] for im, ori in zip(imlist, orilist): stim_order.append({'im': im, 'ori': ori}) trials = data.TrialHandler(stim_order, nReps=1, extraInfo=exp_info, method='sequential', originPath=datapath) #===================== # Start the experiment #===================== # Initialize two clocks: # - for image change time # - for response time change_clock = core.Clock() rt_clock = core.Clock() # Run through the trials for trial in trials: # Display trial start text start_message.draw() win.flip() # Wait for a spacebar press to start the trial, or escape to quit keys = event.waitKeys(keyList=['space', 'escape']) # Set the images, set the orientation im_fname = os.path.join(impath, trial['im']) bitmap1.setImage(im_fname + asfx) bitmap1.setOri(trial['ori']) bitmap2.setImage(im_fname + bsfx) bitmap2.setOri(trial['ori']) bitmap = bitmap1 # Set the clocks to 0 change_clock.reset() rt_clock.reset() # Empty the keypresses list # Leave an 'escape' press in for immediate exit if 'space' in keys: keys = [] # Start the trial # Stop trial if spacebar or escape has been pressed, or if 30s have passed while len(keys) == 0 and rt_clock.getTime() < timelimit: # Switch the image if bitmap == bitmap1: bitmap = bitmap2 else: bitmap = bitmap1 bitmap.draw() # Draw bubbles of increasing radius at random positions for radius in range(n_bubbles): bubble.setRadius(radius/2.) bubble.setPos(((rnd.random()-.5) * scrsize[0], (rnd.random()-.5) * scrsize[1] )) bubble.draw() # Show the new screen we've drawn win.flip() # For the duration of 'changetime', # Listen for a spacebar or escape press change_clock.reset() while change_clock.getTime() <= changetime: keys = event.getKeys(keyList=['space','escape']) if len(keys) > 0: break # Analyze the keypress if keys: if 'escape' in keys: # Escape press = quit the experiment break else: # Spacebar press = correct change detection; register response time acc = 1 rt = rt_clock.getTime() else: # No press = failed change detection; maximal response time acc = 0 rt = timelimit # Add the current trial's data to the TrialHandler trials.addData('rt', rt) trials.addData('acc', acc) # Advance to the next trial #====================== # End of the experiment #====================== # Save all data to a file trials.saveAsWideText(data_fname + '.csv', delim=',') # Quit the experiment win.close() import glob import pandas datafile = glob.glob('data/*.csv')[0] print datafile df = pandas.read_csv(datafile) df