If you’ve been reading the blog regularly you’ll know I added I2c to the ESP8266 code some time ago – that is, the ability to send an I2c message either to read or write – originally intended and still working with cheap I/O expanders – so you lose 2 wires (GPIO4 and 5) and gain another 6 or 14 for one or two I/O expander boards.
Well, I’ve updated it as of tonight.
Of course, ESP12 talking to Arduino is nothing new but given what we’ve built up here with the ESP boards and Node-Red I thought it might be useful to have the option to expand further.
What a few hours ago seems like something in the distance – well, it is done – and it works – and it has LOTS of potential. Read on.
What you see above (the FTDI is just stuck into the ESP8266 board for power) is a 1284 Aiduino boards flashing lights – controlled by MQTT – that is, the ESP12 board on the RIGHT is taking in the MQTT and sending commands via I2c to the 1284-based board and to the little red expander in the middle (on the same 2 pins).
Hence, I’ve spent the day working on the I2c code adding the ability to send multiple byte parameters and to receive a byte (I could have made it receive multiple bytes but for simple control a byte will do).
The next step was to set up an Arduino – or in my case specifically an ATMEGA1284 chip to talk to the ESP – hence giving us the ability to control Arduino ports via Node-Red. Now as yet another blog entry here will testify, you can of course connect (now that the node is fixed) an Arduino directly to the Raspberry Pi in charge – but puts too many physical constraints up. I had no intention of developing Firmata on the ESP – and so a simple i2c protocol was develop and SO much more can be done.
Right now I have an ESP8266 on the bench with a 2-wire I2c connection to an I/O expander – and an Arduino-type board using the 1284. I can talk to both from the ESP (and hence from my Arduino wirelessly via MQTT) and can control the following:
- Any pin as an output (and PWM outputs where appropriate
- Any pin as an input (and analog inputs where appropriate)
So first things first – I used the Atmega1284 simply as I have loads of them – both DIP40 and surface mount in our little AIDUINO boards. The 1284 has twice the RAM of a 2560 and is easy to use. However this would work equally well in a normal Arduino or in the massive 2560 boards.. the only difference being which two pins are used for i2c. The red chart above, shamelessly stolen from ManicBug’s website shows the pins (in parentheses the numbering system I use).
So in the ESP8266 (grab the latest ROMS or SOURCE) I have a simple method of communication which can be used by MQTT or serial. The format is similar to that used elsewhere in the home control system.
i2c: device, return, param1, param2, param3, param4, param5.
Not all parameters are needed.
So – to talk to an i2c expander sitting as device 39, connected to pins 4 and 5 of the ESP board…
{i2c:39,0,3}
device 39, no return value, send out 3 (which lights up the bottom 2 LEDS.
{i2c:39}
This returns the value in the port expander. this is covered in two previous blogs.
https://tech.scargill.net/sunday-morning-experimenting/
https://tech.scargill.net/i2c-expansion-for-raspberry-pi/
So what has changed is that the code can now send out multiple parameters – and optionally receive information back.
{i2c:8,0,1,20,1}
The above sends out to device 8, expecting nothing back, type 1 means set a port bit, bit 20 in this case (see red table above) – to 1.
{i2c:8,1,4,30}
Above – device 8, 1 means return a byte, type 4 means read analog value and port number is 30 – the instruction will return the value of the analog input.
1 is digital out, 2 is digital in, 3 is PWM out, 4 is analog in – you must use appropriate ports – not all are able to handle analog in or PWM out… and you don’t have to worry about port direction setting – this is checked before any operation and set.
There is SO much more potential here but only so many hours. I will likely make the settings for outputs non-volatile at some point – and add in all manner of device monitoring and probably also make use of the multiple serial ports on these devices.
For now that’s not bad for a Sunday session. If you’re seriously interested I’ll make the Arduino code available but right now it is highly volatile – but it works!!
Peter note have a look here – see comments at the end
Thanks for that – so essentially he’d forgotten to set the init to ensure the lines were open with pullups – already done that right at the start – and I can get rock-solid reliable sending of several parameters to the Arduino – it’s coming back that is the issue – if I send one byte back that’s fine – but trying to add more writes and reads fails – maybe I need some acks or something in there… but it won’t work beyond one byte back.