1+ #
2+ # Copyright (C) 2020 Pico Technology Ltd. See LICENSE file for terms.
3+ #
4+ # PS6000 A BLOCK MODE EXAMPLE
5+ # This example opens a 6000a driver device, sets up two 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+ import numpy as np
10+ from picosdk .ps6000a import ps6000a as ps
11+ from picosdk .PicoDeviceEnums import picoEnum as enums
12+ import matplotlib .pyplot as plt
13+ from picosdk .functions import adc2mV , assert_pico_ok , splitMSODataFast
14+
15+ # Create chandle and status ready for use
16+ chandle = ctypes .c_int16 ()
17+ status = {}
18+
19+ # Open 6000 A series PicoScope
20+ # returns handle to chandle for use in future API functions
21+ resolution = enums .PICO_DEVICE_RESOLUTION ["PICO_DR_8BIT" ]
22+ status ["openunit" ] = ps .ps6000aOpenUnit (ctypes .byref (chandle ), None , resolution )
23+ assert_pico_ok (status ["openunit" ])
24+
25+ # Set channel A on
26+ # handle = chandle
27+ channelA = enums .PICO_CHANNEL ["PICO_CHANNEL_A" ]
28+ coupling = enums .PICO_COUPLING ["PICO_DC" ]
29+ channelRange = 7
30+ # analogueOffset = 0 V
31+ bandwidth = enums .PICO_BANDWIDTH_LIMITER ["PICO_BW_FULL" ]
32+ status ["setChannelA" ] = ps .ps6000aSetChannelOn (chandle , channelA , coupling , channelRange , 0 , bandwidth )
33+ assert_pico_ok (status ["setChannelA" ])
34+
35+ # set channel B-H off
36+ for x in range (1 , 7 , 1 ):
37+ channel = x
38+ status ["setChannel" ,x ] = ps .ps6000aSetChannelOff (chandle ,channel )
39+ assert_pico_ok (status ["setChannel" ,x ])
40+
41+ # set MSO pod 1 on
42+ # handle = chandle
43+ port = enums .PICO_CHANNEL ["PICO_PORT0" ]
44+ # logic level needs to be set individually for all digital channels/pins in the port
45+ pins = 8
46+ logicThresholdLevel = (ctypes .c_int16 * pins )(0 )
47+ logicThresholdLevel [0 ] = 1000
48+ logicThresholdLevelLength = len (logicThresholdLevel )
49+ hysteresis = enums .PICO_DIGITAL_PORT_HYSTERESIS ["PICO_LOW_50MV" ]
50+ status ["setDigitalPortOn" ] = ps .ps6000aSetDigitalPortOn (chandle , port , ctypes .byref (logicThresholdLevel ), logicThresholdLevelLength , hysteresis )
51+ assert_pico_ok (status ["setDigitalPortOn" ])
52+
53+ # Set MSO pod 2 off
54+ port2 = enums .PICO_CHANNEL ["PICO_PORT1" ]
55+ status ["setDigitalPortOff" ] = ps .ps6000aSetDigitalPortOff (chandle ,port2 )
56+ assert_pico_ok (status ["setDigitalPortOff" ])
57+
58+ # Set simple trigger on channel A, 1 V rising with 1 s autotrigger
59+ # handle = chandle
60+ # enable = 1
61+ source = channelA
62+ # threshold = 1000 mV
63+ direction = enums .PICO_THRESHOLD_DIRECTION ["PICO_RISING" ]
64+ # delay = 0 s
65+ # autoTriggerMicroSeconds = 1000000 us
66+ status ["setSimpleTrigger" ] = ps .ps6000aSetSimpleTrigger (chandle , 1 , source , 1000 , direction , 0 , 1000000 )
67+ assert_pico_ok (status ["setSimpleTrigger" ])
68+
69+ # Set number of samples to be collected
70+ noOfPreTriggerSamples = 500000
71+ noOfPostTriggerSamples = 1000000
72+ nSamples = noOfPostTriggerSamples + noOfPreTriggerSamples
73+
74+ # Check timebase is valid
75+ # handle = chandle
76+ timebase = ctypes .c_uint32 (1 )
77+ timeInterval = ctypes .c_double (0 )
78+ returnedMaxSamples = ctypes .c_uint64 ()
79+ #segment = 0
80+ status ["getTimebase" ] = ps .ps6000aGetTimebase (chandle , timebase , nSamples , ctypes .byref (timeInterval ), ctypes .byref (returnedMaxSamples ), 0 )
81+ assert_pico_ok (status ["getTimebase" ])
82+ print ("timebase = " , timebase .value )
83+ print ("sample interval =" , timeInterval .value , "ns" )
84+
85+ # Create buffers
86+ bufferAMax = (ctypes .c_int16 * nSamples )()
87+ bufferAMin = (ctypes .c_int16 * nSamples )() # used for downsampling which isn't in the scope of this example
88+
89+ bufferDPort0Max = (ctypes .c_int16 * nSamples )()
90+ bufferDPort0Min = (ctypes .c_int16 * nSamples )()
91+
92+ # Set data buffers
93+ # handle = chandle
94+ # channel = channelA
95+ # bufferMax = bufferAMax
96+ # bufferMin = bufferAMin
97+ # nSamples = nSamples
98+ dataType = enums .PICO_DATA_TYPE ["PICO_INT16_T" ]
99+ waveform = 0
100+ downSampleMode = enums .PICO_RATIO_MODE ["PICO_RATIO_MODE_RAW" ]
101+ clear = enums .PICO_ACTION ["PICO_CLEAR_ALL" ]
102+ add = enums .PICO_ACTION ["PICO_ADD" ]
103+ action = clear | add # PICO_ACTION["PICO_CLEAR_WAVEFORM_CLEAR_ALL"] | PICO_ACTION["PICO_ADD"]
104+ status ["setDataChABuffers" ] = ps .ps6000aSetDataBuffers (chandle , channelA , ctypes .byref (bufferAMax ), ctypes .byref (bufferAMin ), nSamples , dataType , waveform , downSampleMode , action )
105+ assert_pico_ok (status ["setDataChABuffers" ])
106+
107+ status ["setDataDP0Buffers" ] = ps .ps6000aSetDataBuffers (chandle , port , ctypes .byref (bufferDPort0Max ), ctypes .byref (bufferDPort0Min ), nSamples , dataType , waveform , downSampleMode , action )
108+ assert_pico_ok (status ["setDataDP0Buffers" ])
109+
110+ # Run block capture
111+ # handle = chandle
112+ # timebase = timebase
113+ timeIndisposedMs = ctypes .c_double (0 )
114+ # segmentIndex = 0
115+ # lpReady = None Using IsReady rather than a callback
116+ # pParameter = None
117+ status ["runBlock" ] = ps .ps6000aRunBlock (chandle , noOfPreTriggerSamples , noOfPostTriggerSamples , timebase , ctypes .byref (timeIndisposedMs ), 0 , None , None )
118+ assert_pico_ok (status ["runBlock" ])
119+
120+ # Check for data collection to finish using ps5000aIsReady
121+ ready = ctypes .c_int16 (0 )
122+ check = ctypes .c_int16 (0 )
123+ while ready .value == check .value :
124+ status ["isReady" ] = ps .ps6000aIsReady (chandle , ctypes .byref (ready ))
125+
126+ # Get data from scope
127+ # handle = chandle
128+ # startIndex = 0
129+ noOfSamples = ctypes .c_uint64 (nSamples )
130+ # downSampleRatio = 1
131+ # segmentIndex = 0
132+ overflow = ctypes .c_int16 (0 )
133+ status ["getValues" ] = ps .ps6000aGetValues (chandle , 0 , ctypes .byref (noOfSamples ), 1 , downSampleMode , 0 , ctypes .byref (overflow ))
134+ assert_pico_ok (status ["getValues" ])
135+
136+ # get max ADC value
137+ # handle = chandle
138+ minADC = ctypes .c_int16 ()
139+ maxADC = ctypes .c_int16 ()
140+ status ["getAdcLimits" ] = ps .ps6000aGetAdcLimits (chandle , resolution , ctypes .byref (minADC ), ctypes .byref (maxADC ))
141+ assert_pico_ok (status ["getAdcLimits" ])
142+
143+ # convert ADC counts data to mV
144+ adc2mVChAMax = adc2mV (bufferAMax , channelRange , maxADC )
145+
146+ # Obtain binary for Digital Port 0
147+ # The tuple returned contains the channels in order (D7, D6, D5, ... D0).
148+ bufferDPort0 = splitMSODataFast (noOfSamples , bufferDPort0Max )
149+
150+ # Create time data
151+ time = np .linspace (0 , (nSamples ) * timeInterval .value * 1000000000 , nSamples )
152+
153+ # plot data from channel A and B
154+ plt .figure (num = 'Channel A Data' )
155+ plt .plot (time , adc2mVChAMax [:])
156+ plt .xlabel ('Time (ns)' )
157+ plt .ylabel ('Voltage (mV)' )
158+ plt .title ('Channel A data' )
159+ #plt.show()
160+
161+ # Plot the data from digital channels onto a graph
162+ plt .figure (num = 'Digital Port 0 Data' )
163+ plt .title ('Plot of Digital Port 0 digital channels vs. time' )
164+ plt .plot (time , bufferDPort0 [0 ], label = 'D7' ) # D7 is the first array in the tuple.
165+ plt .plot (time , bufferDPort0 [1 ], label = 'D6' )
166+ plt .plot (time , bufferDPort0 [2 ], label = 'D5' )
167+ plt .plot (time , bufferDPort0 [3 ], label = 'D4' )
168+ plt .plot (time , bufferDPort0 [4 ], label = 'D3' )
169+ plt .plot (time , bufferDPort0 [5 ], label = 'D2' )
170+ plt .plot (time , bufferDPort0 [6 ], label = 'D1' )
171+ plt .plot (time , bufferDPort0 [7 ], label = 'D0' ) # D0 is the last array in the tuple.
172+ plt .xlabel ('Time (ns)' )
173+ plt .ylabel ('Logic Level' )
174+ plt .legend (loc = "upper right" )
175+ plt .show ()
176+
177+ # Close the scope
178+ status ["closeunit" ] = ps .ps6000aCloseUnit (chandle )
179+ assert_pico_ok (status ["closeunit" ])
180+
181+ print (status )
0 commit comments