This is a rudimentary oscilloscope built with python for Arduino (DUE)
Sample Output
PyScope - Introduction So, the other day I was playing around with a pet project involving electronics. And I came upon a situation where I needed to generate a very fast PWM pulse (with a frequency of 1MHz). Thus, I came upon two problems.
- Generate the pulse, and
- check to see if it the pulse is generated correctly.
To tackle the first problem, I utilized an Arduino Due that I had lying around. The problem was that digitalWrite(), digitalRead() and analogRead() were too slow for my purposes. And so, I set up, and then, directly wrote to the PIO registers of the Atmel Chip. First, initialize digital pin 2 as output:
Then, write the corresponding value (HIGH, or LOW) to the pin, based on the duty cycle defined by the counter:
The bottleneck happened when reading the pin that generated the pulse. I modified somewhat (rather, I stripped down) the code that I found here:
https://forum.arduino.cc/t/arduino-due-adc-dma-channel-ordering-in-buffer/620520
First, set up the ADC on pin A0:
Then, simply wait until the ADC conversion happens. Finally, read the data from pin A0:
Problem (1) solved!
And now, off to the second problem. How do I visualize correctly the data that ADC read? Well, with the trusty contemporary multitool of course! Which is none other than Python. The code I wrote is rather simple and most of it is for visualization purposes rather than calculations. Firstly, we open a connection to the Serial Port that our Arduino is connected to, we set the buffer size and clear the initial (garbage) input data:
Afterwards, we read the input data whenever a threshold (in bytes) is reached
Then, we convert the read data to a python string and parse it (while surrounding the code with a block to catch the times when input is malformed, or some other type of exception is thrown)
If the resulting list is not empty, we convert it to a list of integers, and finally we read the voltage amplitude with the calculation at line 81 (3.3 volts is the digital HIGH on Due and 4095 is the resolution of the ADC). Int_data now has the measured voltages.
The final part of the calculations, concerns triggering. To do this, we search the converted array to find the first time where the voltage goes from LOW to HIGH, and toss the previous samples. Int_data is now triggered. Pun intended 😊
The rest of the python code utilizes the matplotlib library to render the information to the screen and I consider it to be self-explanatory. Nevertheless, If you feel it should be further explained drop me a line and I will remedy that 😊. Oh! Also don’t forget! At the end, we close the port we opened. Here is a sample output!