def connect(self, physical_channel_name, **timing_args): """ Establish connection with NIDAQ apparatus. A virtual output channel and data stream writer are created. :param physical_channel_name: (str or list of str) name of output port on NIDAQ (to see available channel names, open NI MAX (software included with driver installation) and look under "Devices and Interfaces"). The name might look something like "cDAQ1Mod1/ao0". **timing_args : keyword arguments from nidqamx.task.timing.cfg_samp_clk_timing. :return: True if connection was successful, otherwise False. """ # check for multiple channels if isinstance(physical_channel_name, str): self.multiple_channels = False self.n_channels = 1 elif isinstance(physical_channel_name, list): self.multiple_channels = True self.n_channels = len(physical_channel_name) else: self.logger.error("GVS.connect: please specify a valid " "physical channel name.") try: if self.multiple_channels: # connect multiple analog output channels for chan_name in physical_channel_name: self.add_ao_channel(chan_name) # config timing if "rate" not in timing_args: rate = 1e3 self.task.timing.cfg_samp_clk_timing(rate, **timing_args) else: self.task.timing.cfg_samp_clk_timing(**timing_args) # create output stream writer self.writer = stream_writers.AnalogMultiChannelWriter( self.task.out_stream, auto_start=True) else: # connect single analog output channel self.add_ao_channel(physical_channel_name) # config timing if "rate" not in timing_args: rate = 1e3 self.task.timing.cfg_samp_clk_timing(rate, **timing_args) else: self.task.timing.cfg_samp_clk_timing(**timing_args) # create output stream writer self.writer = stream_writers.AnalogSingleChannelWriter( self.task.out_stream, auto_start=True) logging.info("GVS task and channel created") except nidaqmx.errors.DaqError as err: self.logger.error("DAQmx error: {0}".format(err)) return False self.logger.info("GVS task started") return True
def write_signal(self, mode='ao_waveform', sample_mode_key='continuous', waveform_type='sine', num_periods=6, amplitude=1, frequency=50, spike_amplitude=0, spike_duration=0, oversampling=100, offset=0): if not hasattr(self, 'task'): raise (AttributeError, 'AO task not active, unable to write signal') self.mode = mode self.sample_mode = self.sample_modes[sample_mode_key] self.num_periods = num_periods self.amplitude = amplitude self.waveform_type = waveform_type self.frequency = frequency self.rate = self.frequency * oversampling # if self.rate >= 250000: raise (ValueError, 'Frequency too high, unable to set NIDAQ analog output') self.offset = offset self.spike_duration = spike_duration self.spike_amplitude = spike_amplitude self.stop_task() if self.mode == "ao_voltage": self.task.write(self.amplitude, auto_start=True) elif self.mode == "ao_waveform": samples = self.generate_signal() num_samples = len( samples) # self.num_periods * int(self.rate/self.frequency) try: self.task.timing.cfg_samp_clk_timing( rate=self.rate, sample_mode=self.sample_mode, samps_per_chan=num_samples) writer = stream_writers.AnalogSingleChannelWriter( self.task.out_stream, auto_start=False) writer.write_many_sample(samples) except Exception as err: print( "Rate too low. Use a rate of at least twice the frequency", err)
def connect(self, physical_channel_name, **timing_args): """ Establish connection with NIDAQ apparatus. A virtual output channel and data stream writer are created. :param physical_channel_name: name of output port on NIDAQ (to see available channel names, open NI MAX (software included with driver installation) and look under "Devices and Interfaces"). The name might look something like "cDAQ1Mod1/ao0". :param sampling_rate: samples per second to generate per channel. Default is 10 kHz. **timing_args : keyword arguments from nidqamx.task.timing.cfg_samp_clk_timing. :return: True if connection was successful, otherwise False. """ try: # create virtual output channel self.task.ao_channels.add_ao_voltage_chan( physical_channel_name, name_to_assign_to_channel="GVSoutput", min_val=-self.max_voltage, max_val=self.max_voltage, units=constants.VoltageUnits.VOLTS ) # config timing self.task.timing.cfg_samp_clk_timing(**timing_args) # create output stream writer self.writer = stream_writers.AnalogSingleChannelWriter( self.task.out_stream, auto_start=True ) logging.info("GVS task and channel created") except nidaqmx.errors.DaqError as err: self.logger.error("DAQmx error: {0}".format(err)) return False self.logger.info("GVS task started") return True
'''El código es el mismo que el de DAQ modificado para que envíe y reciba sólo una señal y agregando el PID. Para entender mejor la comunicación con la DAQ correr el archivo "DAQ.py"''' #Settear los parámetros del PID Kp, Ki, Kd y setpoint el valor que se desea obtener pid = PID(Kp,Ki,Kd, setpoint= ) y = np.zeros(1) inicial = -0.625 #valor inicial del PID controles = [] tensiones = [] with nidaqmx.Task() as task_o: test_Task = nidaqmx.Task() '''para generar''' task_o.ao_channels.add_ao_voltage_chan('Dev8/ao0') test_Writer = stream_writers.AnalogSingleChannelWriter(task_o.out_stream, auto_start=True) tension = inicial test_Writer.write_one_sample(tension) time.sleep(1) with nidaqmx.Task() as task_i: '''para leer''' task_i.ai_channels.add_ai_voltage_chan('Dev8/ai1') test_Reader = stream_readers.AnalogSingleChannelReader(task_i.in_stream) '''comienza el PID:''' try: while True: # read from DAQ y = test_Reader.read_one_sample() # compute new ouput from the PID according to the systems current value