jelly |
06-09-2016 12:17 PM |
Dear Jeff,
I have some code below, which is also writing an output file. It only requires a sound .wav file as a cue, otherwise it should run on the spot and illustrate the issue.
When running it, you can see on the screen display that the sampling will freeze and skip seconds. Mostly it seems as if it balances itself out, meaning that if one second froze for too long, then another second at another time will be skipped.
Another thing I am thinking is (because my other colleagues also had similar problem when using sound) that maybe the sampling is faster than the sound and this interaction somehow causes some problems. But running the code with all the sound related things commented still has the problem...:confused:
Code:
import time
import viztask
import numpy as np
import random
import vizact
import itertools
viz.go()
###########################
## GENERAL SETUP
###########################
viz.MainView.setPosition(0,1.8,0)
viz.MainView.setEuler(0,0,0)
viz.mouse.setVisible(viz.OFF) #Stops the mouse appearing on the screen.
viz.mouse.setOverride(viz.ON) #Stops Vizard navigation using the mouse.
#Set background colour
viz.clearcolor(viz.BLACK) #Set background colour to black
ID = input('Participant ID: ') #This is the unique ID number to identify the participant.
suffix = input('Suffix: ') #This is the suffix to the participant's ID number, used for not overwriting data files.
#Create a data ID and data header for the participant:
dataID = str(ID) + '_' + str(suffix) #Adds a suffix to the session number so that files can't be overwritten.
#Create a first line to write to data files:
firstLine = 'Study Data \n'
####~~~~~~~Make Windows for Textures~~~~~~~####
#make box for clock
timeBox = viz.addText('', viz.SCREEN)
timeBox.setPosition(0.5,0.5)
timeBox.setScale([0.4, 0.4, 0.4])
timeBox.alignment(viz.ALIGN_CENTER_CENTER)
timeBox.color([1,1,1])
###########################
## OUTPUT FILE
###########################
####~~~~~~~OUTPUT~~~~~~~####
Data = open(str(dataID) + '_Data3.txt','w')
DataHeaders = 'ID\tPic\tTimeNow\tPicstate\tBeepstate\n'
Data.write(firstLine)
Data.close()
####~~~~~~~Create fuction for saving data~~~~~~~####
def saveData():
global picstateString, beepstateString, timeNow
Data = open(str(dataID) + '_Data3.txt','a', 1) # 'a' means append the file rather than overwrite
vars = "%s\t%s\t%s\t%s\t%s\n" %(
ID, hno, timeNow, picstateString, beepstateString)
Data.write(vars)
###########################
## STIMULI
###########################
### Cue sound
cue = viz.addAudio('cues\dong.wav')
cueDuration = cue.getDuration()
picList = np.arange(1, 59, 1) # this is in the real experiment an actual list of jpegs
### Timings ###
beeptimes = []
otimes2 = []
ctimes2 = []
otimes_short2 = []
otimes_long2 = []
ctimes_short2 = []
ctimes_long2 = []
def uniform_min_range(a, b, n, min_dist):
while True:
atimes = np.random.uniform(a, b, size=n)
np.sort(atimes)
if np.all(np.diff(atimes) >= min_dist):
return atimes
def timings():
global condition, beeptimes, otimes, ctimes, otimes2, ctimes2, otimes_short2, otimes_long2, ctimes_short2, ctimes_long2, ctimes2String, otimes2String, beeptimesString
beeptimes = uniform_min_range(0, 20, 5, 1.0)
print 'beep times: ', beeptimes
beeptimesString = 'BeepTimes: '+','.join(map(str,beeptimes)) + '\n'
num_to_select = 4
otimes = random.sample(beeptimes, num_to_select)
ctimes = list(set(beeptimes) - set(otimes))
otimes1 = [oo + 0.8 for oo in otimes]
otimes2 = np.sort(otimes1)
print 'otimes short', otimes2
ctimes2 = [ctimes[0] + 0.8]
print 'ctimes short', ctimes2
otimes2String = 'S1 Times: ' + ',' .join(map(str,otimes2)) +'\n'
ctimes2String = 'S2 Times: ' + ','.join(map(str,ctimes2)) +'\n'
### Picture state
hno = 30
def setup_pics(): # at 0 nothing happens; at 1 (or -1) something happens (a beep, a pic) --> this sets it up
global tt, picstate, beepstate, picstateString, beepstateString, beeptimesString, otimes2String, ctimes2String
global beeptimes, otimes, ctimes, otimes_short2, otimes_long2, ctimes_short2, ctimes_long2
timings()
Data = open(str(dataID) + '_Data3.txt','a',1)
Data.write(beeptimesString)
Data.write(otimes2String)
Data.write(ctimes2String)
Data.write(DataHeaders)
tt =[]
dt = 0.04 #seconds for increment
tt.append(0) #first elem in tt is 0
picstate = []
picstate.append(0) #first elem in picstate is 0
beepstate = []
beepstate.append(0)
n=0
done = 0
while not done: #keep adding elements to the picstate list
n=n+1 #elem by elem
picstate.append(0)
beepstate.append(0)
tt.append(tt[n-1]+dt) #keep adding time elements to time list, by adding dt = 0.04 s to the one b4
for oo in otimes2: # for each elem in the otimes
if (oo - tt[n]<0.5 and oo-tt[n]>0): #if the element in the otimes minus the current element in tt is lower than 0.5 and bigger than 0 (basically between 0 and 0,5) than choose action 1
picstate[n] = 1
for pp in ctimes2: #if the element in the closing times minus the current element in tt is lower than 0.5 and bigger than 0 (basically between 0 and 0,5) than choose action 2
if (pp - tt[n]<0.5 and pp-tt[n]>0):
picstate[n] = -1
for bs in beeptimes:
if (bs - tt[n]<0.5 and bs-tt[n]>0):
beepstate[n] = 1
if tt[n] > 25: # if the current element in tt is bigger than 20 then stop the loop to add to the list, it's over
done = 1
print 'tt', tt
print 'picstate', picstate
print 'beepstate', beepstate
def choose_pic():
global picstate, beepstate, picstateString, beepstateString, timeNow
global hno
global tt, start, ntt
ntt = viz.tick()-start # get time NOW since start of trial (can be made to be since start of experiment)
nn = np.searchsorted(tt,ntt,side='left')
thispic = picstate[nn]
thisbeep = beepstate[nn]
if thisbeep == 1 and thisbeep-1 == 0:
def cueplay():
cue.play()
#yield viztask.waitTime(cueDuration)
#cue.stop()
cueplay()
picstateString = str(picstate[nn])
beepstateString = str(beepstate[nn])
timeNow = str(round(ntt,2)) # string of time Now ntt (rounded) to print in output file
### DEFAULT - random walk
if thispic==0:
prob = [0.05, 0.95] # Probability to move up or down
rr = np.random.random(1)
if hno<27:
hno = hno+2
elif hno>35:
hno = hno-2
else:
if rr < prob[0] and hno>27:
hno = hno-1
elif rr > prob[1] and hno<35:
hno = hno+1
### STATE1
elif thispic==1: ## state for triggering action 1
if hno<54:
hno = hno+5
### STATE2
elif thispic==-1: ## state for triggering action 1
if hno>4:
hno = hno-5
##save stuff
saveData()
## DISPLAY
time_left = round(20-ntt,0)
timeBox.message('Time: '+str(int(round(ntt)))+' - '+'PictureNo: '+ str(picstate[nn])+ ' - '+ 'Beep: '+str(beepstate[nn])+' - ' + str(nn))
###########################
## TRIAL
###########################
def mainTrial():
global start, nn
nn = 1
setup_pics()
start = viz.tick()
vizact.ontimer2(0.035,500,choose_pic)
yield viztask.waitTime(25)
viztask.schedule(mainTrial())
The problem with the tracker may be more complex but it is possible that not the tracker is the problem after all. The code I have embedded below, ignores the motion tracker altogether and still I have some timing issues. I guess it is better to understand/solve these first, before moving on.
Any help or ideas are very welcome and I would be very grateful for them!
|