Introduction: Browser Controlled Signal Generator
This instructable describes a signal generator that is controlled by a browser client.
I have for a long time used an analogue signal generator I built many years ago based around the venerable ICL8038 chip. This was controlled with manual switches and potentiometers to give me sine, triangle and square waves from 10Hz to a few 100 KHz and a variable amplitude.
I decided to replace this with a more up to date, digitally controlled unit based around the AD9833 chip. This gave me a much smaller battery operated unit with enhanced performance and range which I can control much more flexibly from a browser.
It has the following features.
Signal generation from 0.1Hz to 5MHz, 1.8Vpp max
Sine, Triangle and square waves
Amplitude set by digital potentiometer (0-127) and switched attenuators (0, -20.6dB, -26.5dB, -41.9dB)
Can playback files holding sequence of frequencies and amplitudes
Web based GUI allowing control from PC, phone, tablet
Wifi Management to allow easy initial router set up
OTA software update
- AD9833 signal generator module
- ESP8266 ESP-12F module
- MCP40D18 digital potentiometer
- MCP6022 dual op-amp
- xc6203E332 voltage regulator
- 18650 Lithium battery
- TP4056 Lithium charger module
- 2 BC247 bipolar transistors
- Resistors, Capacitors (see schematic)
- Prototyping board
- Power switch
- 3 pin output connector
- Enclosure - I used a 3D printed box https://www.thingiverse.com/thing:4949996
Step 1: Hardware Design
The schematic shows the ESP8266 module controlling the AD9833 chip through its 3 wire SPI interface.
The output of the AD9833 is a fixed amplitude signal (0.6Vpp for triangle and sine and 3.3Vpp for square waves). This is fed into a MCP40D18 digital potentiometer which can vary it from full to 0 output in 128 steps. A 5k version of the potentiometer is used to keep bandwidth. This is chip is also controlled by the ESP8266 using the I2C interface.
The output of the potentiometer is fed into a x3.2 amplifier so that a maximum of 2Vpp can be obtained. For square waves the potentiometer will only reduce the output for settings below about 40.
The MCP6022 is chosen for the op-amp as it has good bandwidth and also supports inputs and outputs very close to the supply rails allowing direct coupling throughout which makes it easier to support the very low frequencies that can be used. As the input needs to be a little bit above ground (25mV) a small bias signal is fed in via a 220K resistor.
The output of the first stage is fed into a unity gain buffer using the other half of the MCP6022 via a network which can be switched to give approximately 0db, -20db, -26db, -40db. The attenuator uses two bc847 transistors to switch in attenuating resistors and these are controlled by digital outputs from the ESP8266. I chose to use BJT transistors here rather than MOSFETS as they have low output capacitance preserving the frequency performance. Many common MOSFETS although being good switches have high output capacitance. It is possible to get low capacitance MOSFETS but then the Rds when turned on can be no better than the saturation resistance of the BJT. By choosing the base resistor of the BJTs it is possible to get low switch resistance and low offset voltage.
I chose to provide outputs from the amplitude controlled buffer amplifier and the raw output from the AD9833 as the latter maintains waveforms at the very high frequencies.
The power is provided by a 18650 battery regulated by a low drop out xc6203. The battery operation has the benefit of isolation from the mains which is good in avoiding hum and ground loops when using low amplitude outputs. A TP4056 USB charger unit is built in to allow recharging from USB.
Step 2: Construction
I chose to construct the electronics on a long thin piece of prototype board about the same length as the 18650 battery.
The ESP-12F overhangs the end of this so the wifi antenna has no board underneath to degrade the wifi performance.
The AD9833 was mounted piggy pack on top of the ESP-12F.
I used the MCP40D18 chip which is very small so I mounted this on breakout board which supported the package type and then mounted this onto the prototype board. An I2C digital potentiometer module could be substituted to make construction easier. Other I2C digital potentiometers could also be used with a small adjustment to the software.
Likewise the MCP6022 dual op-amp was mounted on a break out board. This chip is in a SOIC-8 so is relatively easy to handle.
The voltage regulator, BJTs, resistors and capacitor were likewise mounted direct onto the prototype board.
The TP4056 module was mounted on the end presenting its USB interface to provide access for charging.
Outputs were fed to a small 3 pin socket and a small switch was used in line with the battery + lead to act as an on/off switch.
Step 3: Software
The software is available at https://github.com/roberttidey/espSignalGenerator
This is compiled under the Arduino IDE and first serially uploaded to the board.
It supports wifi management which means that on first use it will open a portal network which can be connected to and browsed to 192.168.4.1 to set up the local wifi connection.
It also supports OTA update by browsing to ip/firmware.
Support files from the data folder should be uploaded one at a time by browsing to ip/upload.
The software supports a web server which by browsing to ip will show an interface allowing control of the signal generator. There are simple GET urls as follows
- /setfreq?freq=495.5 Sets the operating frequency
- /setphase?phase=0 Sets phase
- /setmode?mode=1 Sets waveform (-1 off, 1 sine, 2 square, 3 square-div2, 4 triangle
- /setamplitude?amplitude=320 Set amplitude - attenuation. See note below
- /setall/freq=495&mode=1 Allows all above parameters to be to set in one go
- /getdatafiles Retrieves list of al sequence files
Note on amplitude. This value is made up of 2 parts 256 * attenuator(0-3) + potentiometer level(0-127). The attenuator is (3 0db, 2 -20.6db, 1 -26.5db, 0 -41.9db) where those are nominal values.
The nominal attenuation values and the calculation of output amplitudes can be tuned in the index.html
Attenuation values are defined in
const AttenuationVal = [0.00803, 0.04752,0.09353, 1.0];
if these are changed then the corresponding labels should be changed to 20log of these values
Vpp values are calculated from
const VppByMode = [0.0, 1813.0, 10000.0, 10000.0, 1813.0];
These are nominal values in mV for full output of the AD9833 after amplification.
Vrms values are calculated from
const VrmsByMode = [0.0, 641.0, 5000.0, 5000.0, 523.4];
where these are the Vpp divided by 2root(2) for sine, 2root(3) for triangle and 2 for square
Access to the filing system is via ip/edit
Step 4: Operation
Operation is via the browser interface supported by the ESP8266.
When accessing ESPIPaddress/ you get a control page which has 2 tabs.
The main tab provides direct control of the frequency, amplitude, attenuation and waveform type. Changing any value takes immediate effect. The page gives an indication of the Vpp and Vrms corresponding to the selected values. These can be tuned up by changing values in the index page.
The files tab gives access to a list of any preset sequence files. Each file is a simple text file where each line controls the time duration, frequency, phase, mode, amplitude/attenuation parameters for each step. The time duration is in milliseconds. One can ignore particular parameters by using a -2 value. This facility can be used to provide frequency sweeps or more sophisticated sequences like step frequency changes interspersed with silence to aloww for automated measurements.