def prepare(self): item.item.prepare(self) self.EE = EvtExchanger() Device = self.EE.Select(self.var._productName) try: if Device is None: raise except: self.var._productName = u'DUMMY' self.Keyboard = Keyboard(self.experiment); if not type(self.var._responseTimeout) == int: self.var._responseTimeout = None oslogger.info("Cannot find ResponseBox: Using Keyboard instead") if not type(self.var._responseTimeout) == int and not type(self.var._responseTimeout) == float: self.var._responseTimeout = -1 # Recode Allowed buttons to AllowedEventLines self.var.AllowedEventLines = 0 try: AllowedList = self.var._allowedButtons.split(";") for x in AllowedList: self.var.AllowedEventLines += (1 << (int(x,10) -1)) except: x = self.var._allowedButtons self.var.AllowedEventLines = (1 << (x-1))
def Do_Shock_Run(self): try: self.experiment.get("ShockerCalibration") except: oslogger.error("No calibration step taken: First run a Shocker in calibration mode!") return if (self.var._productName == u"DUMMY"): oslogger.info("In (Dummy) Shock: shocking with value: " + str(self.var._value)) else: try: lst = self.experiment.get("lastShockTime") except: lst = 0; td = time.time() - lst # This line is to prevent the possibility to shock if the previous shock was less then the minimum time ago if (td > self.var._min_intershock_interval): oslogger.info("In (Hardware) Shock: shocking with value: " + str(math.floor((self.var._value/100.0) * self.experiment.get("ShockerCalibration")))) self.EE.SetLines(0) self.EE.PulseLines(math.floor((self.var._value/100.0) * self.experiment.get("ShockerCalibration")), self.var._duration) # TODO: mAh = round((self.var._value/100.0) * self.experiment.get("ShockermAhCalibration"),2) self.experiment.set("lastShockTime", time.time()) self.experiment.set("BinaryShockValue", math.floor((self.var._value/100.0) * self.experiment.get("ShockerCalibration"))) self.experiment.set("ShockPercValue", self.var._value) self.experiment.set("ShockMahValue", mAh) else: oslogger.warning("In Shock: the shock came too early: please don't give shocks in rapid succession!")
def _cmd(self, desc, fnc, url_suffix, data, on_error): t0 = time.time() response = fnc(self._base_url + url_suffix, json=data) if not response.ok: raise on_error(response.text) oslogger.info('{} {} ({:.3f}s)'.format(desc, url_suffix, time.time() - t0))
def _delete(self, url_suffix, on_error): t0 = time.time() response = requests.delete(self._base_url + url_suffix) if not response.ok: raise on_error() oslogger.info('delete {} ({:.3f}s)'.format(url_suffix, time.time() - t0))
def available(self): oslogger.info('check server at {}'.format('healthz')) try: response = requests.get(self._base_url + 'healthz', timeout=TIMEOUT_AVAILABLE) except requests.exceptions.ConnectionError: return False return response.ok
def prepare(self): item.item.prepare(self) self.EE = EvtExchanger() Device = self.EE.Select(self.var._productName) try: if Device is None: raise except: self.var._productName = u'DUMMY' oslogger.info("Cannot find eventexchanger: code to debugwindow")
def prepare(self): """The preparation phase of the plug-in goes here.""" item.prepare(self) # Checking the excistence of the VAS elements is only possible in the runphase # as only then the full canvas is availeable self.c = Canvas(self.experiment) self.slmouse = Mouse(self.experiment, timeout=20, visible=True) self.slmouse.show_cursor(True) self.slmouse.set_pos(pos=(0, 0)) my_canvas = self.experiment.items[self.var.VAS_CANVAS_NAME].canvas try: if my_canvas[self.var.VAS_BODY_NAME] == None or my_canvas[ self.var.VAS_EXITBUTTON_NAME] == None: oslogger.info("Should not occur") except Exception as e: raise osexception( u"Prepare: READ the VAS manual:\n\rNo VAS elements found on the named canvas" ) self.useLabels = True try: if my_canvas[self.var.VAS_MAXLABEL_NAME] == None or my_canvas[ self.var.VAS_MAXLABEL_NAME] == None: oslogger.info("Should not occur") except Exception as e: self.uselabels = False self.c = self.experiment.items[self.var.VAS_CANVAS_NAME].canvas self.ypos = -1 # is the vasbody a line or a rect? if hasattr(self.c[self.var.VAS_BODY_NAME], 'ex') and hasattr( self.c[self.var.VAS_BODY_NAME], 'sx'): self.VASLENGTH = self.c[self.var.VAS_BODY_NAME].ex - self.c[ self.var.VAS_BODY_NAME].sx self.ypos = (self.c[self.var.VAS_BODY_NAME].sy + self.c[self.var.VAS_BODY_NAME].ey) / 2 self.sx = self.c[self.var.VAS_BODY_NAME].sx if hasattr(self.c[self.var.VAS_BODY_NAME], 'w') and hasattr( self.c[self.var.VAS_BODY_NAME], 'y') and hasattr( self.c[self.var.VAS_BODY_NAME], 'h'): self.VASLENGTH = self.c[self.var.VAS_BODY_NAME].w self.ypos = self.c[self.var.VAS_BODY_NAME].y + ( self.c[self.var.VAS_BODY_NAME].h / 2) self.sx = self.c[self.var.VAS_BODY_NAME].x if self.ypos == -1: raise TypeError("VasBody should be a line or a Rect")
def _get(self, url_suffix, on_error, data=None): t0 = time.time() response = requests.get(self._base_url + url_suffix, json=data) if not response.ok: raise on_error() json = response.json() if not isinstance(json, dict) or 'data' not in json: raise InvalidJSON(safe_decode(json)) if self.verbose: oslogger.info(json) oslogger.info('get {} ({:.3f}s)'.format(url_suffix, time.time() - t0)) return json['data']
def prepare(self): """The preparation phase of the plug-in goes here.""" item.prepare(self) self.EE = EvtExchanger() Devices = self.EE.Select(self.var.VAS_ENCODER_ID) try: self.EE.RENC_SetUp(1024, 0, int(1024*(self.var.VAS_CURSOR_STARTPOSITION/100.0)), 1, 1) if Devices[0] is None: raise except: self.var.VAS_ENCODER_ID = u"MOUSE" oslogger.info("Cannot find encoder input device: Using mouse") # Checking the excistence of the VAS elements is only possible in the runphase # as only then the full canvas is availeable self.c = Canvas(self.experiment) self._Keyboard = Keyboard(self.experiment, timeout = 0); self._Mouse = Mouse(self.experiment) my_canvas = self.experiment.items[self.var.VAS_CANVAS_NAME].canvas try: if my_canvas[self.var.VAS_CURSOR_NAME] == None or my_canvas[self.var.VAS_BODY_NAME] == None: oslogger.info("Should not occur") except Exception as e: raise osexception(u"Prepare: READ the VAS manual:\n\rNo VAS elements found on the named canvas") self.c = self.experiment.items[self.var.VAS_CANVAS_NAME].canvas self.c[self.var.VAS_CURSOR_NAME].sx = (self.c[self.var.VAS_BODY_NAME].sx+self.c[self.var.VAS_BODY_NAME].ex) / 2.0 self.c[self.var.VAS_CURSOR_NAME].ex = self.c[self.var.VAS_CURSOR_NAME].sx self.VASLENGTH = self.c[self.var.VAS_BODY_NAME].ex - self.c[self.var.VAS_BODY_NAME].sx self.SHOWTIMER = False if self.var.VAS_EXIT_METHOD == 'TIME': if my_canvas[self.var.VAS_CURSOR_NAME] != None: self.SHOWTIMER = True self.w = self.c[self.var.VAS_TIMER_NAME].ex - self.c[self.var.VAS_TIMER_NAME].sx self.h = self.c[self.var.VAS_TIMER_NAME].ey - self.c[self.var.VAS_TIMER_NAME].sy self.TIMER_DIR = 'vert' self.TIMERSIZE = self.h if (abs(self.w) > abs(self.h)): self.TIMER_DIR = 'horiz' self.TIMERSIZE = self.w
def _init_conditioner(self): if hasattr(self, '_conditioner'): return if 'omm_conditioner' in self.python_workspace: self._conditioner = self.python_workspace['omm_conditioner'] oslogger.info('reusing conditioner') return oslogger.info('initializing conditioner') cls = getattr(conditioners, self.var.conditioner) self._conditioner = cls(experiment=self.experiment, port=self.var.serial_port) self.python_workspace['omm_conditioner'] = self._conditioner self.experiment.cleanup_functions.append(self._close_conditioner)
def run(self): self.set_item_onset() #self.EE.Select(self.PATH) if self.var._productName == u'DUMMY': oslogger.info('dummy code: {} for {} ms'.format( self.var._value, self.var._duration)) else: if self.var._outputMode == u'Set Output Lines': self.EE.SetLines(self.var._value) elif self.var._outputMode == u'Pulse Output Lines': # make sure that the code starts at, and returns to zero. self.EE.SetLines(0) self.EE.PulseLines(self.var._value, self.var._duration) return True
def run(self): self.set_item_onset() if self.var._productName == u"DUMMY": if self.var._calibrate == u"Shock": oslogger.info('dummy shock: {} for {} ms'.format(self.var._value, self.var._duration) ) else: self.Calibrate_Run() else: #self.EE.Select(self.PATH) if self.var._calibrate == u"Calibrate": self.Calibrate_Run() elif self.var._calibrate == u"Shock": self.Do_Shock_Run() return True
def prepare(self): BaseOMMPlugin.prepare(self) if not self._openmonkeymind.connected: oslogger.info('running in test mode') self._prepare_test() return current_job_index = self._openmonkeymind.get_current_job_index() if self.var.block_select == 'no': self.experiment.var.omm_job_index = current_job_index self.experiment.var.omm_block_index = None self.experiment.var.omm_job_index_in_block = None job = self._openmonkeymind.request_job() else: # To randomly select a job from the current block, we: # - Get the index of the next job # - Determine the block number based on this index # - Determine the minimum and maximum index of the block that # contains this index # - Get all jobs within this range # - Shuffle these jobs, and then get the first non-finished job if (not isinstance(self.var.block_size, int) or self.var.block_size <= 1): raise ValueError( 'block size should be an integer value larget than 1') block_index = (current_job_index - 1) // self.var.block_size + 1 min_job_index = (block_index - 1) * self.var.block_size + 1 max_job_index = block_index * self.var.block_size + 1 jobs = self._openmonkeymind.get_jobs(min_job_index, max_job_index) unfished_job_indices = [ job_index + min_job_index for job_index, job in enumerate(jobs) if not job.finished ] job_index = random.choice(unfished_job_indices) job_index_in_block = \ self.var.block_size - len(unfished_job_indices) + 1 oslogger.info( 'global job index: {}, job index in block: {}, block index {}'. format(job_index, job_index_in_block, block_index)) job = self._openmonkeymind.request_job(job_index) self.experiment.var.omm_job_index = job_index self.experiment.var.omm_block_index = block_index self.experiment.var.omm_job_index_in_block = job_index_in_block self.experiment.var.omm_job_id = job.id_ self.experiment.var.omm_job_count = self._openmonkeymind.job_count for key, val in job: self._set_variable(key, val) InlineScript.prepare(self)
def open(self, path): if self._log is not None: self.close() # If only a filename is present, we interpret this filename as relative # to the experiment folder, instead of relative to the current working # directory. if ( os.path.basename(path) == path and self.experiment.experiment_path is not None ): self._path = os.path.join(self.experiment.experiment_path, path) else: self._path = path # Open the logfile self.experiment.var.logfile = self._path if self._path not in self.experiment.data_files: self.experiment.data_files.append(self._path) oslogger.info('appending to {}'.format(self._path)) self._log = safe_open(self._path, u'a')
def _get_osexp(self, json): t0 = time.time() for f in json['files']: if not f['type'] == 'experiment': continue path = f['path'] updated_at = f['updated_at'] size = f['size'] break else: raise InvalidJSON(safe_decode(json)) cache_path = os.path.join( tempfile.gettempdir(), hashlib.md5(safe_encode(path + updated_at)).hexdigest() + '.osexp') # If a cached file that matches in name and size exists, we re-use it. # The file name also includes the updated_at fields, and thus # re-uploading a new experiment with the same size will still refresh # the cache. if os.path.exists(cache_path) and os.path.getsize(cache_path) == size: oslogger.info('using cached {}'.format(cache_path)) else: response = requests.get(self._osexp_url + path) if not response.ok: raise FailedToDownloadExperiment() with open(cache_path, 'wb') as fd: fd.write(response.content) oslogger.info('caching {} to {}'.format(path, cache_path)) self._experiment = experiment(string=cache_path) oslogger.info('building experiment ({:.3f} s)'.format(time.time() - t0)) return self._experiment
def announce(self, participant): json = self._get('participants/{}/canonical'.format(participant), ParticipantNotFound) if not json['identifier']: raise ParticipantNotFound() if json['identifier'] != participant: participant = json['identifier'] oslogger.info('using canonical id {}'.format(participant)) json = self._get('participants/{}/announce'.format(participant), NoJobsForParticipant) if not json['active']: raise NoJobsForParticipant() self._participant = participant self._study = json['id'] self._job_count = json['jobs_count'] # The participant metadata is optional, and is None if no metadata has # been specified. metadata = json['participants'][0]['meta'] if metadata is None: self._participant_metadata = {} else: self._participant_metadata = metadata return self._get_osexp(json)
def sound_both(self): oslogger.info('sound both')
def sound_right(self): oslogger.info('sound right')
def sound_left(self): oslogger.info('sound left')
def activate(self): if not hasattr(self, '_qdm'): oslogger.info('ignoring activate until after startup') return self._set_visible(not cfg.workspace_visible)
def _run_keypress(self): key, timestamp = self._keyboard.get_key() oslogger.info('identifier: {}'.format(key)) self.experiment.var.set(self.var.participant_variable, '/{}/'.format(key))
def __init__(self): try: EvtExchanger.Attached() oslogger.info("EventExchanger Initialized") except Exception as e: raise Exception('EventExchanger (LibUSB) Initialisation Error')
def sound_off(self): oslogger.info('sound off')
def reward(self): oslogger.info('reward')
def _close_conditioner(self): oslogger.info('closing conditioner') self._conditioner.close()