예제 #1
0
def changeColor(node):
    lastColor = random.randint(0, 2)
    while True:
        node.color(Color[lastColor])
        d = yield viztask.waitDraw()
        data = '  ,' + str(lastColor) + ',' + str(d.time)
        sub_rt.write('\n' + data)
        tmp_color = [0, 1, 2]
        tmp_color.remove(lastColor)
        lastColor = random.choice(tmp_color)
        yield viztask.waitTime(0.75)
예제 #2
0
def changeColor2(target=Target2):
    lastColor = random.randint(0, 2)
    i = 1
    while True:
        target.color(tg2Colors[lastColor])
        d = yield viztask.waitDraw()
        data = str(i) + ',' + str(lastColor) + ',' + str(d.time)
        sub_rt.write('\n' + data)
        tmp = [0, 1, 2]
        tmp.remove(lastColor)
        lastColor = random.choice(tmp)
        i += 1
        yield viztask.waitTime(0.75)
예제 #3
0
def refreshing(clouds):
    index = 0
    while True:
        clouds[index].remove()
        pos = np.random.uniform(low=-6, high=6, size=(cloudFreq / freq, 3))
        pos[:, 1] = pos[:, 1] / 2
        pos[:, 2] = pos[:, 2] - 5
        viz.startLayer(viz.POINTS)
        viz.pointSize(2)
        for n in range(cloudFreq / freq):
            viz.vertex(pos[n, 0], pos[n, 1], pos[n, 2])
        single_cloud = viz.endLayer()
        single_cloud.disable(viz.CULLING)
        single_cloud.setParent(Target)
        clouds.append(single_cloud)
        index += 1
        yield viztask.waitDraw()
예제 #4
0
def cross_trial(start_time, wait_time, rt_deadline, remove, 
					message="",training=False):
	""" Implements a single trial
	Parameters
	==========
	start_time:float
	  IF start_time == 0, wait for the next trigger pulse. Else,
	  wait until start_time to begin the trial.
	wait_time:float
	  time to wait until the cross should remove one of its lines
	rt_deadline:float
	  if the subject did not respond more quickly than the deadline,
	  tell them they blew it
	remove:str
	  The portion of the cross to remove. Either "hbar" or "vbar".
	"""
	descr = {"onset":start_time,
			 "duration":wait_time,
			 "crossbar":remove}
	new_texture = hbar if remove == "vbar" else vbar
	if start_time == 0:
		yield vizact.waitsignal(TRIGGER_EVENT)
	else:
		while viz.tick() < start_time:
			yield viz.waitTime(0.01)
			
	# ---- If there's a message, display it for MESSAGE_TIME
	#block_text.message(message)
	#vizact.ontimer2(rate=MESSAGE_TIME, repeats=0,func=clear_text)
	
	# ---- Flash the cue
	quad.texture(cue)
	yield viztask.waitTime(0.5)
	quad.texture(cross)
	
	# ---- Wait the required time
	yield viztask.waitTime(wait_time)
	
	# ---- Set the new texture
	quad.texture(new_texture)
	#Wait for next frame to be drawn to screen
	d = yield viztask.waitDraw()

	#Save display time
	displayTime = d.time

	#Wait for a reaction
	reaction = yield viztask.waitAny( 
		[HBAR_RESPONSE,
		 VBAR_RESPONSE] )
	time_at_response, = reaction.data.data[0]

	# How did they do??
	# -> Hbar remains
	if reaction.condition is HBAR_RESPONSE:
		descr["acc_success"] = remove == "vbar"
		response = "hbar"
	# -> vbar remains
	if reaction.condition is VBAR_RESPONSE:
		descr["acc_success"] = remove == "hbar"
		response = "vbar"
		
	# print "removed:", remove,"responded:",response
	# Calculate reaction time
	reactionTime = time_at_response - displayTime
	descr["speed_success"] = reactionTime < rt_deadline
	success = descr["speed_success"] and descr["acc_success"]
	# What sort of feedback to give?
	#if training:
		# In training blocks, show the rt
		#yield training_display(reactionTime,descr["acc_success"])
	#else:
	if success:
		yield success_display(reactionTime)
	else:
		failtype = "WRONG" if descr["speed_success"] else "TIMEOUT"
		yield fail_display(failtype, reactionTime)
	
	quad.texture(cross)
	descr["response"]   = response
	descr["success"]    = success
	descr["rt"]         = reactionTime
	descr["rt_deadline"]= rt_deadline
	descr["changetime"] = d.time
	viztask.returnValue(descr)
def TrackTask():
    prevPos = None
    allData = []
    tRegained = 0
    stage = 0  # 0: wait for track loss, 1: wait for track regained, 2: wait for trigger pull, 3: trigger pulled. check optical heading position ok, 4: trigger released, ready for next trigger pull that will start actual data collection
    t = 0.
    opticalHeadScrewed = False
    tCount = -1
    while True:
        # wait for track regained
        stage = 0
        while True:
            pos = setup.trackerDataFun()
            if prevPos is not None and pos['vive'] == prevPos['vive']:
                # position didn't change at all, not tracking
                if stage is not 1:
                    setup.sounds.trialStart.play()
                    print 'track lost'
                    stage = 1
            else:
                # get here only once vive position/orientation starts changing again
                if stage == 1:
                    setup.sounds.trialCompleted.play()
                    print 'track regained'
                    tRegained = t
                    stage = 2 if qCheckOptHeading else 4  # if not qCheckOptHeading, skip the check

                if stage == 2 and t - tRegained > nSecWait and (
                        steamvr.getControllerList()[0].isButtonDown(2)
                        or viz.key.isDown('c', immediate=True)):
                    # first press, check if optical heading position is ok
                    stage = 3

                if stage == 3 and not (
                        steamvr.getControllerList()[0].isButtonDown(2)
                        or viz.key.isDown('c', immediate=True)):
                    # button/trigger released
                    stage = 4

                if stage == 4 and (
                        steamvr.getControllerList()[0].isButtonDown(2)
                        or viz.key.isDown('c', immediate=True)):
                    # second press: time to record some data
                    tCount += 1
                    break
            prevPos = pos

            # check position of optical heading markers is within expected range. Otherwise markers probably switched
            if qCheckOptHeading and stage in [3, 4] and any([
                    abs(p - m) > l for p, m, l in zip(
                        pos['optical_heading'][:3], optHeadingPos, optHeadLims)
            ]):
                # optical markers screwed, notify
                if not opticalHeadScrewed:
                    print 'optical heading error. current pose: ' + str(
                        pos['optical_heading'])
                    setup.sounds.alarm.play()
                    opticalHeadScrewed = True
            else:
                opticalHeadScrewed = False

            # limit to update rate
            d = yield viztask.waitDraw()
            t = d.time

        # report position
        print 'capturing track data'
        setup.sounds.trialStart.play()
        count = 0
        data = []
        while count < trackRate * nSec:
            ti = setup.trackerDataFun()
            ti['timeStamp'] = d.time
            data.append(ti)
            count += 1

            d = yield viztask.waitDraw()

        # store for later
        allData.append(data)
        setup.sounds.trialCompleted.play()

        # make filename
        if tCount + 1 == nTrial:
            time = datetime.datetime.now()
            fname = ''.join(
                (str(time.year) + str(time.month).zfill(2) +
                 str(time.day).zfill(2) + str(time.hour).zfill(2) +
                 str(time.minute).zfill(2) + str(time.second).zfill(2)))

            saveData = {}
            saveData['data'] = allData
            scio.savemat('data/' + fname,
                         saveData,
                         long_field_names=True,
                         do_compression=True,
                         oned_as='column')

            # done
            viz.quit()
예제 #6
0
def TrackTask():
    prevPos = None
    tracking = False
    allData = []
    tCount = -1
    # run until number of trials finished, or forever
    while True:
        # wait for trigger press
        while not (steamvr.getControllerList()[0].isButtonDown(2)
                   or viz.key.isDown('c', immediate=True)):
            pos = setup.trackerDataFun()
            if prevPos is not None and pos['vive'] == prevPos['vive']:
                # position didn't change at all, not tracking
                if tracking:
                    print 'track lost'
                    setup.sounds.trialStart.play()
                tracking = False
            else:
                if not tracking:
                    print 'track regained'
                tracking = True
            prevPos = pos

            # store data upon keypress, or upon requested number of trials reached
            if (viz.key.isDown(viz.KEY_CONTROL_L, immediate=True)
                    and viz.key.isDown('s', immediate=True)
                    and len(allData) > 0) or (nTrial is not None
                                              and tCount == nTrial):
                # make filename
                time = datetime.datetime.now()
                fname = ''.join(
                    (str(time.year) + str(time.month).zfill(2) +
                     str(time.day).zfill(2) + str(time.hour).zfill(2) +
                     str(time.minute).zfill(2) + str(time.second).zfill(2)))

                saveData = {}
                saveData['data'] = allData
                scio.savemat('data/' + fname,
                             saveData,
                             long_field_names=True,
                             do_compression=True,
                             oned_as='column')

                # done, either quit or notify and clear data store
                if nTrial is not None:
                    viz.quit()
                else:
                    setup.sounds.trialStart.play()
                    allData = []

            # limit to update rate
            d = yield viztask.waitDraw()

        # report position
        print 'capturing track data'
        tCount += 1
        count = 0
        data = []
        while count < trackRate * nSec:
            ti = setup.trackerDataFun()
            ti['timeStamp'] = d.time
            data.append(ti)
            count += 1

            d = yield viztask.waitDraw()

        # store for later
        allData.append(data)
        setup.sounds.trialCompleted.play()

        # Wait for trigger to release if still down
        if steamvr.getControllerList()[0].isButtonDown(2):
            yield viztask.waitSensorUp(steamvr.getControllerList()[0],
                                       steamvr.BUTTON_TRIGGER)
def TrackTask():
    prevPos = None
    tracking = True
    allData = []
    tRegained = 0.
    waitingForTrack = True
    t = 0.
    while True:
        # wait for trigger press
        while not (steamvr.getControllerList()[0].isButtonDown(2)
                   or viz.key.isDown('c', immediate=True)):
            # limit to update rate
            d = yield viztask.waitDraw()

        # record n seconds of data
        tRegained = d.time
        while True:
            pos = setup.trackerDataFun()
            if prevPos is not None and pos['vive'] == prevPos['vive']:
                # position didn't change at all, not tracking
                if tracking:
                    print 'track lost'
                    allData = []
                    waitingForTrack = True
                tracking = False
            else:
                # get here only once vive position/orientation starts changing again
                if not tracking:
                    print 'track regained'
                    tRegained = t
                tracking = True
                if waitingForTrack and t - tRegained > nSecWait:
                    # time to record some data
                    waitingForTrack = False
                    break

            pos['timeStamp'] = d.time
            prevPos = pos
            allData.append(pos)

            # limit to update rate
            d = yield viztask.waitDraw()
            t = d.time

        # calculate mean and SD for each variable of Vive
        means = [0.] * 6
        SDs = [0.] * 6
        for dat in allData:
            for i, e in enumerate(dat['vive']):
                means[i] += e
        N = len(allData)
        means = [x / N for x in means]
        # now SD
        for dat in allData:
            for i, e in enumerate(dat['vive']):
                SDs[i] += (e - means[i])**2
        SDs = [math.sqrt(x) / (N - 1) for x in SDs]

        # NB: for analysis of simulataneous data, can just do it qualitative. plot position/orientation over time for both vive and
        # other source. see offset in time between curves, that gives you differential latency.

        # wait for threshold exceeded, until controller trigger pulled that stops things
        setup.sounds.trialStart.play()
        exceeded = []
        d = yield viztask.waitDraw()
        visible = True
        while not (steamvr.getControllerList()[0].isButtonDown(2)
                   or viz.key.isDown('c', immediate=True)):
            pos = setup.trackerDataFun()
            pos['timeStamp'] = d.time
            allData.append(pos)

            # check threshold
            qThresh = [
                abs(x - m) > s * multiplier
                for x, m, s in zip(pos['vive'], means, SDs)
            ]
            if any(qThresh) and visible:
                for v in setup.visuals:
                    v.visible(viz.OFF)
                visible = False
                exceeded.append(
                    len(allData))  # store at which sample this happened

            # limit to screen update rate
            d = yield viztask.waitDraw()

        # save data and exit
        setup.sounds.trialCompleted.play()

        time = datetime.datetime.now()
        fname = ''.join(
            (str(time.year) + str(time.month).zfill(2) +
             str(time.day).zfill(2) + str(time.hour).zfill(2) +
             str(time.minute).zfill(2) + str(time.second).zfill(2)))

        saveData = {}
        saveData['data'] = allData
        saveData['means'] = means
        saveData['SDs'] = SDs
        saveData['multiplier'] = multiplier
        saveData['exceeded'] = exceeded
        scio.savemat('data/' + fname,
                     saveData,
                     long_field_names=True,
                     do_compression=True,
                     oned_as='column')

        # done
        viz.quit()