|
| 1 | +# |
| 2 | +# Copyright (C) 2018 Pico Technology Ltd. See LICENSE file for terms. |
| 3 | +# |
| 4 | +# PS3000A BLOCK MODE EXAMPLE |
| 5 | +# This example opens a 3000a driver device, sets up one channels and a trigger then collects a block of data. |
| 6 | +# This data is then plotted as mV against time in ns. |
| 7 | + |
| 8 | +import ctypes |
| 9 | +from picosdk.ps3000a import ps3000a as ps |
| 10 | +import numpy as np |
| 11 | +import matplotlib.pyplot as plt |
| 12 | +from picosdk.functions import adc2mV, mV2adc, assert_pico_ok |
| 13 | + |
| 14 | +# Create chandle and status ready for use |
| 15 | +status = {} |
| 16 | +chandle = ctypes.c_int16() |
| 17 | + |
| 18 | +# Opens the device/s |
| 19 | +status["openunit"] = ps.ps3000aOpenUnit(ctypes.byref(chandle), None) |
| 20 | + |
| 21 | +try: |
| 22 | + assert_pico_ok(status["openunit"]) |
| 23 | +except: |
| 24 | + |
| 25 | + # powerstate becomes the status number of openunit |
| 26 | + powerstate = status["openunit"] |
| 27 | + |
| 28 | + # If powerstate is the same as 282 then it will run this if statement |
| 29 | + if powerstate == 282: |
| 30 | + # Changes the power input to "PICO_POWER_SUPPLY_NOT_CONNECTED" |
| 31 | + status["ChangePowerSource"] = ps.ps3000aChangePowerSource(chandle, 282) |
| 32 | + # If the powerstate is the same as 286 then it will run this if statement |
| 33 | + elif powerstate == 286: |
| 34 | + # Changes the power input to "PICO_USB3_0_DEVICE_NON_USB3_0_PORT" |
| 35 | + status["ChangePowerSource"] = ps.ps3000aChangePowerSource(chandle, 286) |
| 36 | + else: |
| 37 | + raise |
| 38 | + |
| 39 | + assert_pico_ok(status["ChangePowerSource"]) |
| 40 | + |
| 41 | +# Set up channel A |
| 42 | +# handle = chandle |
| 43 | +# channel = PS3000A_CHANNEL_A = 0 |
| 44 | +# enabled = 1 |
| 45 | +# coupling type = PS3000A_DC = 1 |
| 46 | +# range = PS3000A_10V = 8 |
| 47 | +# analogue offset = 0 V |
| 48 | +chARange = 8 |
| 49 | +status["setChA"] = ps.ps3000aSetChannel(chandle, 0, 1, 1, chARange, 0) |
| 50 | +assert_pico_ok(status["setChA"]) |
| 51 | + |
| 52 | +# Finds the max ADC count |
| 53 | +# Handle = chandle |
| 54 | +# Value = ctypes.byref(maxADC) |
| 55 | +maxADC = ctypes.c_int16() |
| 56 | +status["maximumValue"] = ps.ps3000aMaximumValue(chandle, ctypes.byref(maxADC)) |
| 57 | +assert_pico_ok(status["maximumValue"]) |
| 58 | + |
| 59 | +# Set an advanced trigger |
| 60 | +adcTriggerLevel = mV2adc(500, chARange, maxADC) |
| 61 | + |
| 62 | +# set trigger channel properties |
| 63 | +# handle = chandle |
| 64 | +channelProperties = ps.PS3000A_TRIGGER_CHANNEL_PROPERTIES(adcTriggerLevel, |
| 65 | + 10, |
| 66 | + 0, |
| 67 | + 10, |
| 68 | + ps.PS3000A_CHANNEL["PS3000A_CHANNEL_A"]) |
| 69 | +nChannelProperties = 1 |
| 70 | +# auxOutputEnabled = 0 |
| 71 | +autoTriggerMilliseconds = 1000 |
| 72 | +status["setTrigProp"] = ps.ps3000aSetTriggerChannelProperties(chandle, ctypes.byref(channelProperties), nChannelProperties, 0, autoTriggerMilliseconds) |
| 73 | +assert_pico_ok(status["setTrigProp"]) |
| 74 | + |
| 75 | +# set trigger conditions V2 |
| 76 | +# chandle = handle |
| 77 | +conditions = ps.PS3000A_TRIGGER_CONDITIONS_V2(ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_TRUE"], |
| 78 | + ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_DONT_CARE"], |
| 79 | + ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_DONT_CARE"], |
| 80 | + ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_DONT_CARE"], |
| 81 | + ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_DONT_CARE"], |
| 82 | + ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_DONT_CARE"], |
| 83 | + ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_DONT_CARE"], |
| 84 | + ps.PS3000A_TRIGGER_STATE["PS3000A_CONDITION_DONT_CARE"]) |
| 85 | +nConditions = 1 |
| 86 | +status["setTrigCond"] = ps.ps3000aSetTriggerChannelConditionsV2(chandle, ctypes.byref(conditions), nConditions) |
| 87 | +assert_pico_ok(status["setTrigCond"]) |
| 88 | + |
| 89 | +# set trigger directions |
| 90 | +# handle = chandle |
| 91 | +channelADirection = ps.PS3000A_THRESHOLD_DIRECTION["PS3000A_RISING"] |
| 92 | +channelBDirection = ps.PS3000A_THRESHOLD_DIRECTION["PS3000A_NONE"] |
| 93 | +channelCDirection = ps.PS3000A_THRESHOLD_DIRECTION["PS3000A_NONE"] |
| 94 | +channelDDirection = ps.PS3000A_THRESHOLD_DIRECTION["PS3000A_NONE"] |
| 95 | +extDirection = ps.PS3000A_THRESHOLD_DIRECTION["PS3000A_NONE"] |
| 96 | +auxDirection = ps.PS3000A_THRESHOLD_DIRECTION["PS3000A_NONE"] |
| 97 | +status["setTrigDir"] = ps.ps3000aSetTriggerChannelDirections(chandle, channelADirection, channelBDirection, channelCDirection, channelDDirection, extDirection, auxDirection) |
| 98 | +assert_pico_ok(status["setTrigDir"]) |
| 99 | + |
| 100 | +# Setting the number of sample to be collected |
| 101 | +preTriggerSamples = 40000 |
| 102 | +postTriggerSamples = 40000 |
| 103 | +maxsamples = preTriggerSamples + postTriggerSamples |
| 104 | + |
| 105 | +# Gets timebase innfomation |
| 106 | +# Handle = chandle |
| 107 | +# Timebase = 2 = timebase |
| 108 | +# Nosample = maxsamples |
| 109 | +# TimeIntervalNanoseconds = ctypes.byref(timeIntervalns) |
| 110 | +# MaxSamples = ctypes.byref(returnedMaxSamples) |
| 111 | +# Segement index = 0 |
| 112 | +timebase = 2 |
| 113 | +timeIntervalns = ctypes.c_float() |
| 114 | +returnedMaxSamples = ctypes.c_int16() |
| 115 | +status["GetTimebase"] = ps.ps3000aGetTimebase2(chandle, timebase, maxsamples, ctypes.byref(timeIntervalns), 1, ctypes.byref(returnedMaxSamples), 0) |
| 116 | +assert_pico_ok(status["GetTimebase"]) |
| 117 | + |
| 118 | +# Creates a overlow location for data |
| 119 | +overflow = ctypes.c_int16() |
| 120 | +# Creates converted types maxsamples |
| 121 | +cmaxSamples = ctypes.c_int32(maxsamples) |
| 122 | + |
| 123 | +# Starts the block capture |
| 124 | +# Handle = chandle |
| 125 | +# Number of prTriggerSamples |
| 126 | +# Number of postTriggerSamples |
| 127 | +# Timebase = 2 = 4ns (see Programmer's guide for more information on timebases) |
| 128 | +# time indisposed ms = None (This is not needed within the example) |
| 129 | +# Segment index = 0 |
| 130 | +# LpRead = None |
| 131 | +# pParameter = None |
| 132 | +status["runblock"] = ps.ps3000aRunBlock(chandle, preTriggerSamples, postTriggerSamples, timebase, 1, None, 0, None, None) |
| 133 | +assert_pico_ok(status["runblock"]) |
| 134 | + |
| 135 | +# Create buffers ready for assigning pointers for data collection |
| 136 | +bufferAMax = (ctypes.c_int16 * maxsamples)() |
| 137 | +bufferAMin = (ctypes.c_int16 * maxsamples)() # used for downsampling which isn't in the scope of this example |
| 138 | + |
| 139 | +# Setting the data buffer location for data collection from channel A |
| 140 | +# Handle = Chandle |
| 141 | +# source = ps3000A_channel_A = 0 |
| 142 | +# Buffer max = ctypes.byref(bufferAMax) |
| 143 | +# Buffer min = ctypes.byref(bufferAMin) |
| 144 | +# Buffer length = maxsamples |
| 145 | +# Segment index = 0 |
| 146 | +# Ratio mode = ps3000A_Ratio_Mode_None = 0 |
| 147 | +status["SetDataBuffers"] = ps.ps3000aSetDataBuffers(chandle, 0, ctypes.byref(bufferAMax), ctypes.byref(bufferAMin), maxsamples, 0, 0) |
| 148 | +assert_pico_ok(status["SetDataBuffers"]) |
| 149 | + |
| 150 | +# Creates a overlow location for data |
| 151 | +overflow = (ctypes.c_int16 * 10)() |
| 152 | +# Creates converted types maxsamples |
| 153 | +cmaxSamples = ctypes.c_int32(maxsamples) |
| 154 | + |
| 155 | +# Checks data collection to finish the capture |
| 156 | +ready = ctypes.c_int16(0) |
| 157 | +check = ctypes.c_int16(0) |
| 158 | +while ready.value == check.value: |
| 159 | + status["isReady"] = ps.ps3000aIsReady(chandle, ctypes.byref(ready)) |
| 160 | + |
| 161 | +# Handle = chandle |
| 162 | +# start index = 0 |
| 163 | +# noOfSamples = ctypes.byref(cmaxSamples) |
| 164 | +# DownSampleRatio = 0 |
| 165 | +# DownSampleRatioMode = 0 |
| 166 | +# SegmentIndex = 0 |
| 167 | +# Overflow = ctypes.byref(overflow) |
| 168 | + |
| 169 | +status["GetValues"] = ps.ps3000aGetValues(chandle, 0, ctypes.byref(cmaxSamples), 0, 0, 0, ctypes.byref(overflow)) |
| 170 | +assert_pico_ok(status["GetValues"]) |
| 171 | + |
| 172 | +# Converts ADC from channel A to mV |
| 173 | +adc2mVChAMax = adc2mV(bufferAMax, chARange, maxADC) |
| 174 | + |
| 175 | +# Creates the time data |
| 176 | +time = np.linspace(0, (cmaxSamples.value) * timeIntervalns.value, cmaxSamples.value) |
| 177 | + |
| 178 | +# Plots the data from channel A onto a graph |
| 179 | +plt.plot(time, adc2mVChAMax[:]) |
| 180 | +plt.xlabel('Time (ns)') |
| 181 | +plt.ylabel('Voltage (mV)') |
| 182 | +plt.show() |
| 183 | + |
| 184 | +# Stops the scope |
| 185 | +# Handle = chandle |
| 186 | +status["stop"] = ps.ps3000aStop(chandle) |
| 187 | +assert_pico_ok(status["stop"]) |
| 188 | + |
| 189 | +# Closes the unit |
| 190 | +# Handle = chandle |
| 191 | +status["close"] = ps.ps3000aCloseUnit(chandle) |
| 192 | +assert_pico_ok(status["close"]) |
| 193 | + |
| 194 | +# Displays the staus returns |
| 195 | +print(status) |
| 196 | + |
0 commit comments