#!/usr/bin/env python # -*- coding: utf-8 -*- # ***************************************************************************** # This program is free software; you can redistribute it and/or modify it under # the terms of the GNU General Public License as published by the Free Software # Foundation; either version 2 of the License, or (at your option) any later # version. # # This program is distributed in the hope that it will be useful, but WITHOUT # ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS # FOR A PARTICULAR PURPOSE. See the GNU General Public License for more # details. # # You should have received a copy of the GNU General Public License along with # this program; if not, write to the Free Software Foundation, Inc., # 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA # # Module authors: # Markus Zolliker # ***************************************************************************** """Nanovoltmeter Keithley 2182A""" import time from frappy.core import FloatRange, HasIO, Module, Parameter, StringIO, Readable, Property, IntRange, Done class NanovIO(StringIO): channel = Parameter('active channel nr', IntRange(0, 16), default=0, readonly=False) _channel_index = -1 end_of_line = '\n' _last_change = 0 _channels = None pollinterval = 1 def earlyInit(self): super().earlyInit() self._channels = [] def register(self, channel): if channel not in self._channels: self._channels.append(channel) def doPoll(self): try: idx = self._channel_index channel = self._channels[idx] reply = float(self.communicate('FETCH?')) if abs(reply) > 1000: print('BAD', reply) return channel.value = float(reply) except IndexError: idx = -1 now = time.time() if now < self._last_change + 5 or (idx >= 0 and len(self._channels) == 1): return idx self._last_change = now self._channel_index = idx = (idx + 1) % len(self._channels) self.channel = self._channels[idx].channel result = self.communicate(';SENS:CHAN %i;:SENS:CHAN?' % self.channel) class Volt(HasIO, Readable): channel = Property('channel', datatype=IntRange(1, 16)) value = Parameter('Voltage1', FloatRange(unit='V')) ioClass = NanovIO def initModule(self): super().initModule() self.io.register(self) def read_value(self): if self.io.channel == self.channel: self.io.doPoll() # trigger read return Done