Hands-On I2C Arduino - Practical Guided
Hands-On I2C Arduino - Practical Guided
Figure 1: I2C bus wiring, reproduced from http://www.lammertbies.nl/comm/info/I2C-bus.html If you are only using one I2C device, the pull-up resistors are (normally) not required. However, if you are running several devices, use two 10 kilo ohm resistors. The maximum length of an I2C bus is around one meter. As there are several components that use the I2C interface! and our Arduino boards can control them all. There are many applications, such a real-time clocks, digital potentiometers, temperature sensors, digital compasses, memory chips, FM radio circuits, I/O expanders, LCD controllers, ampliers, and so on. And you can have more than one on the bus at any time, in fact the maximum number of I2C devices used at any one time is 112. Each device can be connected to the bus in any order, and devices can be masters or slaves. In our Arduino situation, the board is the master and the devices on the I2C bus are the slaves. We can write data to a device, or read data from a device. Each device has a unique address (7-bit address). We use that address in the functions to direct our read or write requests to the correct device. It is possible to use several devices with identical addresses on an I2C bus. I2C Communication Protocol I2C has a master/slave protocol. The master initiates the communication. The sequences of events are: 1. The Master device issues a START condition. This condition informs all the slave devices to listen on the serial data line for instructions. 2. The Master device sends the 7-bit address of the target slave device and a read/write ag. 3. The Slave device with the matching address responds with an ACK signal. 4. Communcation proceeds between the Master and the Slave on the data bus. Both the master and slave can receive or transmit data depending on whether the communcation is a read or write. The transmitter sends 8-bits of data to the receiver which replies with a 1-bit ACK
5. When the communication is complete, the master issues a STOP condition indicating that everything is done.
#include<Wire.h> #define PCF8574 B00100000 //PCF8574 ID code #define PCF8574A B00111000 //PCF8574A ID code //input byte inpRead; byte inpBuff = 0x0F; //Don't care LED port void setup(){ Wire.begin();
Serial.begin(9600); //Start serial for output } void loop(){ inpRead = ReadInput(PCF8574A); inpBuff = inpRead&0x01; //Check P0 pin Serial.println(inpBuff,HEX); delay(500); } byte ReadInput(int IDCode) { Wire.requestFrom(IDCode,1); //1 byte Read return(Wire.read()); } Result and Conclusion: This example shows the result of reading input of PCF8574 through RS232. The program displays the input data from Input Port of PCF8574 in HEX format. The value is changed when button is pressed.
Assignment
Write Arduino program to run four LEDs by using the rst PCF8574-IC which its address {A2,A1,A0} is {0,0,0}. When the button is pressed, all LEDs are blinked in every 1 second. The button is connected at P0
pins of the second PCF8574-IC which its address {A2,A1,A0} is {0,0,1}. The given code is not complete, you need to nish.
Figure 4: Expand I/O port with Arduino //Experiment of PCF8574 expander I/O by using I2C interface //Connect two PCF8574 ICs with different addresses #include<Wire.h> #define PCF8574 B00100000 #define PCF8574A B00111000 #define PCF8574A2 B00111001
//PCF8574 ID code //1st-PCF8574A ID code (A0=0, A1=0, A2=0); //2nd-PCF8574A ID code (A0=1, A1=0, A2=0);
int out[4] = {0x10, 0x20, 0x40, 0x80}; int out2 = 0xF0; byte inpRead; byte inpBuff = 0x0F; void setup(){ Wire.begin(); } void loop(){ inpRead = ReadInput(PCF8574A2); //read input from 2nd-PCF8574 inpBuff = inpRead&0x01; //check P0 Pin if(inpBuff==0){ //button is pressed WriteOutput(PCF8574A, (~out2)|0x0F); out2 = ~out2; delay(1000); } else{ //Run LED for(int i=0; i<4;i++) { WriteOutput(PCF8574A, ~out[i]|0x0F);
References
http://www.lammertbies.nl/comm/info/I2C-bus.html