Expanding input and output pin

Good day, I bought sensor shield V 4.0 And i was thinking it expand the input and output, i use all pin there to controll input and output from 2 to 13 but now i want to expand it to connect SD card to it And increase the number of output if possible in simple way?! Any help? Best regard, Sayed

Is it possible to expand by connecting I2C adapter as the following to expand output to 16 pin in order to control 16 relay board? http://www.dx.com/p/lcd1602-adapter-board-w-iic-i2c-interface-black-works-with-official-arduino-boards-216865

Sayed: Good day, And I was thinking it expand the input and output, I use all pin there to control input and output from 2 to 13 put now i want to expand it to connect SD card to it

Don't forget digital pins A0 to A5.

Sayed: Is it possible to expand by connecting I2C adapter as the following to expand output to 16 pin in order to control 16 relay board?

Excellent question!

I2C peripherals use A4 and A5 to connect any (reasonable) number of I2C slaves.

If (from eBay or DX.com) you buy a "PCF8574T IO Extension Board" it tends to cost a ridiculous amount of money (though that red one from DX.com is far more reasonable than most, and is the one you would actually want ... but).

The one you first picked uses the same chip and is considerably cheaper, but is configured as an interface for the common LCD displays. Seven bits of the interface are directly brought out to pins on the edge, while the eighth drives a transistor intended to control the illumination LED on the LCD display. In fact, if you are controlling active-low relay boards (as most are) than that will work perfectly well, if you take note that that the function of that pin will be inverted compared to the others. And you will have to check out the order in which the pin functions are brought out.

So yes, it should do the job. You will need two of them for 16 outputs and you will have to configure them (with the solder jumpers) for two different addresses.

SD card needs to connect to D11-12-13, and a chip select pin, typically D10. Signals (MOSI, SCK, Chip Select) and power going to the card need to be at 3.3V level unless you have a SD module with an adapter on it. MISO coming back will work at 3.3V level, I like to run it thru a buffer like 74HC125 with chip select to protect the Din on the SD card from 5V signals from other devices that may be using SPI, such as shift in (74HC165) or shift out (74HC595, TPIC6B595) registers.

The simplest way to increase the number of ouput pins is just to buy a bigger board. The Arduino Mega provides a whopping 54 output pins. But it will cost you: the Mega is $50. And unlike the basic Arduino, you are limited in your choices regarding form factor and input power. It’s big with lots of deluxe options and that’s what you get.

Some multiplexers are chainable, so you can fairly easily add 8 more signals without needing to keep taking them away from the arduino itself.

thank you very much Paul__B, CrossRoads, and recyclenation, i most like what Paul Said, i connect already LCD to I2C port and also i have the item that i attach the link on my hand which have 16 pin and 4 pin for it is input, i want to know the way to use them to control the relay board and the push button to save more pin on the arduino, if that possible this is better for me than upgrade to large arduino mega. my question after i connect the two I2C adapter to the port SDA and SCL, the LCD work fine for me and i am using it now to display my output, now i want to know how to use the second adapter for controlling the relay board as output and if possible to control input if there is enough pin of the 16 pin, i get the following table |500x289 and |500x94 the LCD are the following LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE); if i will do it for the pcf8574 that will used as expansion how i can run each pin and change the signal from low to high or high to low? thanks very much all, Best regards, Sayed

There are eight possible combinations of A0, A1 and A2. Each board must have a different address. If with no jumpers soldered, the address is 0x27, then with A0 jumpered, it will be 0x26, with A1 jumpered, 0x25, both A0 and A1 jumpered, 0x24, A2 only jumpered 0x23 and so on.

To control the PCF8574s you will need their datasheet and to study the “Wire” library. The LiquidCrystal_I2C library itself uses this library to control the LCD but you have to use the Wire library itself to control basic I/O. As long as you only send commands to one device at a time and close the communication properly (as LiquidCrystal_I2C will do) before moving on to another function, there would be no problems.

I cannot comment on the relay board connections without a proper reference to their corresponding datasheet/ circuit.

thank you, can you please see this link there is datasheet as i think maybe this what you ask for

http://m5.img.dxcdn.com/CDDriver/CD/sku.216865.rar

Best regards

wiring and connection done, every thing is ok, now i need help in how to change specific pin of the 8 pin to high and to low if need, i test it by the following Wire.beginTransmission(relay); Wire.write(1); Wire.endTransmission(); when i write in the write function 1 as i test P0 relay run and then if i write 255 it stop, now i need to know how to specify the pin and the state for it alone can any body help me in that? Best regards, Sayed

The Arduino Mega provides a whopping 54 output pins.

The 16 Analog input pins can also be used as digital input/output pins, so really 70 output pins.

And unlike the basic Arduino, you are limited in your choices regarding form factor and input power.

Huh? It has the same power section as the Uno Arduino.

It's big with lots of deluxe options and that's what you get.

It only has more IO pins, the only real difference is 3 more hardware serial ports and 8 more analog inputs (feeding into the same single channel analog mux). Hardly "deluxe options".

thanks CrossRoads, but that one i have it on my hand now, and getting other if i decide will delay my programming and finishing the project. only now i need to know the way to control each pin alone for relay, if i write Wire.write(00000001); in order to run last pin it work fine, but if each pin in control loop alone for example controller need to run the first pin without doing any thing with other pin status, if it run Wire.write(10000000); this will change last pin status, if statement and multiplication and subtracting maybe help if i can store value with 00001 without loosing the 0000

if i can convert from 0 to 128 to binary then i can solve it to run the target pins and keep other unchanged, any idea?

Sayed: if i write Wire.write(00000001); in order to run last pin it work fine, but if each pin in control loop alone for example controller need to run the first pin without doing any thing with other pin status, if it run Wire.write(10000000); this will change last pin status, if statement and multiplication and subtracting maybe help if i can store value with 00001 without loosing the 0000

Since you cannot (easily) read back the Wire.write() value, you need to store it in a variable, modify it using AND and OR operations ("&" and "|") and then write that composite value to the chip via I2C.

thanks Paul, it work fine now as output , is there any way to convert it to input? how it can be used as input? for output work fine as the following

    Wire.beginTransmission(relay);
     binary=B11111111;
     if (PinNo1e==0){
        binary=binary-B00000000;
     }
     if (PinNo2e==0){
        binary=binary-B00000001;
     }
     if (PinNo3e==0){
        binary=binary-B00000010;
     }
     if (PinNo4e==0){
        binary=binary-B00000100;
     }
     if (PinNo5e==0){
        binary=binary-B00010000;
     }
     if (PinNo6e==0){
        binary=binary-B00100000;
     }
     Wire.write(binary); 
     Wire.endTransmission();

Uh,,, you READ it's data ports??

yes it work fine, it control the output but after some time arduino have wrong thing on the LCD and when push button pressed then arduino Restart! my problem maybe due to connecting both I2C LCD with I2C that used to control output with same 4 pin but with two address

//LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);  // Set the LCD I2C address

#define Cont 0x26 // relay board

and for LCD i start comminication by the following

lcd.setCursor(0, 1);
    lcd.print("Test LCD 1");

while for I2C output

Wire.beginTransmission(Cont);
 binary=B11111111;
     if (PinNo1e==0){
        binary=binary-B00000000;
     }
     if (PinNo2e==0){
        binary=binary-B00000001;
     }
     if (PinNo3e==0){
        binary=binary-B00000010;
     }
     if (PinNo4e==0){
        binary=binary-B00000100;
     }
     if (PinNo5e==0){
        binary=binary-B00010000;
     }
     if (PinNo6e==0){
        binary=binary-B00100000;
     }
     Wire.write(binary); 
     Wire.endTransmission();

is there a way to solve these problem?

There is a rule here.

If you expect anyone to find the faults in you code, then you must post the whole code every time, because the problem is more than likely in the bit you did not post. :astonished:

no problem! i only add the previous line to shot the time for who will check!!
i didnt know if it is true to do it like that in the lcd or not!
the lcd freeze some time and some time the word and time become unknown thing in the LCD!!
also the SD card get problem when adding hour count!
the filename is ok but sd card file dose not open!

#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <OneWire.h>
#include <SD.h>
#include <SPI.h>
#include <EEPROM.h>
LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);
#define Cont 0x26 // relay board

int PinNo1e = 1;
int PinNo2e = 1;
int PinNo3e = 1;
int PinNo4e = 1;
int PinNo5e = 1;
int PinNo6e = 1;
int PinNo2 = 2;
int PinNo3 = 3;
int PinNo4 = 4;
int PinNo5 = 5;
int SetVent1;
int SetVent2;
int SetTimer1;
int SetTimer2;
long hour=0;
long day=0;
byte binary=0;
long timenw=0;
long timepr1=0;
long timepr2=0;
long timepr3=0;
long timepr4=0;
long Ventc=0;
long Timec1=0;
long Timec2=0;
int rvent=0;
int ovent=0;
int rtimer=0;
int side=0;
int addr=0;
char filename[14]= {'\0'};
void setup() {
  // put your setup code here, to run once:
   Serial.begin(9600); //(Remove all 'Serial' commands if not needed)
   Wire.begin();
   day=EEPROM.read(6); 
   lcd.begin(20,4);         // initialize the lcd for 20 chars 4 lines, turn on backlight
   lcd.backlight();
    while (!Serial) {
    ; 
    }
    pinMode(10, OUTPUT);
    pinMode(4, OUTPUT);
    sprintf(filename,"Log%04d_%02.txt",day,hour);
    if (!SD.begin(4)){
      return;
    }
    
}


void Status(){

     Wire.beginTransmission(Cont);
     binary=B11111111;
     if (PinNo1e==0){
        binary=binary-B00000000;
     }
     if (PinNo2e==0){
        binary=binary-B00000001;
     }
     if (PinNo3e==0){
        binary=binary-B00000010;
     }
     if (PinNo4e==0){
        binary=binary-B00000100;
     }
     if (PinNo5e==0){
        binary=binary-B00010000;
     }
     if (PinNo6e==0){
        binary=binary-B00100000;
     }
     Wire.write(binary); 
     Wire.endTransmission();

}



void normal(){
    lcd.setCursor(0, 1);
    lcd.print("My Machine");
    lcd.setCursor(0, 2);
    lcd.print("Vent:");
    lcd.print((timenw-timepr2)/60000);    
    
    lcd.print("min");
    if(PinNo3e == 0){
      lcd.print("!");
    }else{
      lcd.print("x");
    }
    lcd.print(" Run:");
    lcd.print((float)Ventc,0);
    lcd.print(" ");
    lcd.setCursor(0, 3);
    lcd.print("Turn:");
     lcd.print((timenw-timepr1)/60000);
    lcd.print("min");
    if(PinNo5e == 0 || PinNo6e == 0){
    lcd.print("!");
    }else{
    lcd.print("x");
    }
    lcd.print(" Run:");
    lcd.print((float)Timec1,0);
    lcd.print(" ");
    delay(750);
  
}






void loop() {
 
timenw=millis();
//Serial.print(timenw-timepr3);

if (timenw-timepr3>=3600000){
  hour=hour+1;
  if(hour==23){
    hour=0;
    day=day+1;
    EEPROM.write(6,day);
  }
}
if (timenw-timepr4>=1000)
{
  timepr4=timenw;
  String dataString = "";
  
  sprintf(filename,"Log%04d_%02d.txt",day,hour);
  File dataFile = SD.open(filename, FILE_WRITE);
  Serial.print(filename);
  //Serial.print(",");
  
  
  // if the file is available, write to it:
  if (dataFile) {
      dataString +="Vent. : ";
      dataString += String(Ventc);
      dataString += ",";
      dataString +="Turnten : ";
      dataString += String(Timec1);
      dataString += ",";
      dataString += "Day";
      dataString += String(day);
      dataString += ",";
      dataString += "Hour";
      dataString += String(hour);
      dataString += ";";

    dataFile.println(dataString);
    dataFile.close();
    // print to the serial port too:
    
    Serial.print("Result");
    Serial.print(dataString);
 
  }
  
  // if the file isn't open, pop up an error:
  else {
    Serial.println("error opening datalog txt");
  } 
}   
  


 if(millis()<=2000){
 if(EEPROM.read(5)>90||EEPROM.read(4)>120){
 
    EEPROM.write(4,SetTimer1);
    EEPROM.write(5,SetTimer2); 
 }else{
    SetTimer1=EEPROM.read(4);
    SetTimer2=EEPROM.read(5);
 }
 delay(2000);
  }

      timer1();
      timer2();
      Status();
}

void timer1(){
  timenw=millis();
  if ((timenw-timepr1)< 0||(timenw-timepr2)< 0){
    timepr1=0;
    timepr2=0;
    timepr3=0;
    timepr4=0;
  }
  if(timenw-timepr1>=SetTimer1*60000){
    rtimer=0;
     if(side==0){
      PinNo6e=0;
    }else if(side==1){
      PinNo5e=0;
    }
  }
 if(rtimer==0){
   if(timenw-timepr1>=SetTimer1*60000+SetTimer2*1000){
      if(PinNo6e==0){
        side=1;
      }
      if(PinNo5e==0){
        side=0;
      }
      PinNo6e=1;
      PinNo5e=1;
      timepr1=timenw;
      rtimer=1;
      Timec1=Timec1+1;
  }
  }
}
void timer2(){
  timenw=millis();

  if(timenw-timepr2>=SetVent1*60000){
   PinNo3e=0;
    if(timenw-timepr2>=(SetVent1*60000+SetVent2*1000)){
   PinNo3e=1;
   Ventc=Ventc+1;
  }
  }
  
  

}