Arduino Irrigation and Plant Watering using Soil Moisture Sensor

This project is about a moisture-sensing automatic plant watering system using Arduino UNO. The system reads the moisture content of the soil using soil moisture sensor and switches ON the motor when the moisture is below the set limit. When the moisture level rises above the set point, the system switches off the pump.  The status of the tank, motor and the moisture level will be displayed on a 16×2 LCD display.
So let’s come to our project!

Objectives of the Project

  • Monitor the moisture content of the soil using a soil moisture sensor and thewater level of the tank using a float switch.
  • Turn the motor ON when the soil moisture falls below a certain reference value and if there is enough water in the tank.
  • Display the status of the soil and the tank using a 16×2 LCD.
Let’s begin to build our project –  Soil Moisture Based Automatic Irrigation System.

Circuit Diagram


The soil moisture sensor module used here have two output pins ( Digital output and Analog output ). The output from the probe of the moisture sensor is compared with a reference value using a lm393 comparator. The reference value can be changed by turning the potentiometer in the module. The digital pin gives an active low output when the soil is wet. Here we are using the analog output from the module by connecting it to one of the analog pins of Arduino. While using the analog output the wet detection value can be set/adjusted within the program itself.


As shown in the circuit diagram, a float switch is connected to one of the analog pins of Arduino and a 1K Ohm resistor is used to pulled up the line. Analog pins of Arduino can also be used as digital inputs. The status of the tank is identified by checking the output of the float switch. Arduino reads the voltage dropped across the pull up resistor for sensing the level of water in the tank.  Two LEDs are connected to the 2nd and 3rd pin of Arduino to show the moisture status and tank status respectively. And the 4th pin links to the base of a BC547 transistor which in turn drives the 12 V DC motor.
16×2 LCD is connected with Arduino in 4-bit mode. JHD162A is the LCD module used here. JHD162A is a 16×2 LCD module based on the HD44780 driver from Hitachi. The JHD162A has 16 pins and can be operated in 4-bit mode (using only 4 data lines) or 8-bit mode (using all 8 data lines). Here we are using the LCD module in 4-bit mode. Control pin RS, RW and En are directly connected to arduino pin 13, GND and 12. And data pin D4-D7 is connected to 11, 10, 9 and 8 of arduino.

The Program/Code 
#include<LiquidCrystal.h>


 #define moisture_sensorPin A0
 #define float_switchPin A1
 #define motorPin 4
 #define soil_statusPin 2
 #define tank_statusPin 3
 
 LiquidCrystal lcd(13,12,11,10,9,8);
 
 const int avg_moisture = 800; 



void setup() 
{
 Serial.begin(9600);
 lcd.begin(16,2);
 lcd.clear();
 lcd.setCursor(0,0);
 lcd.print(" AUTOMATIC ");
 lcd.setCursor(0,1);
 lcd.print(" IRRIGATION S/M ");
 delay(2000);
 
 
 pinMode(moisture_sensorPin,INPUT);
 pinMode(float_switchPin,INPUT);
 pinMode(motorPin,OUTPUT);
 pinMode(soil_statusPin,OUTPUT);
 pinMode(tank_statusPin,OUTPUT);
 
 digitalWrite(motorPin,LOW);
 digitalWrite(soil_statusPin,LOW);
 digitalWrite(tank_statusPin,LOW);


}

void loop() 
{

lcd.begin(16,2);
 
 
 
 lcd.setCursor(0,0);
 lcd.print(" MOISTURE - ");
 
 if(analogRead(moisture_sensorPin) > avg_moisture){
 lcd.print("HIGH");
 digitalWrite(soil_statusPin,HIGH);}
 
 if(analogRead(moisture_sensorPin) < avg_moisture){
 lcd.print(" LOW");
 digitalWrite(soil_statusPin,LOW);}



 
 lcd.setCursor(0,1);
 lcd.print("TANK LEVEL- ");
 
 if( digitalRead(float_switchPin) == HIGH){
 lcd.print("HIGH");
 digitalWrite(tank_statusPin,LOW);}
 
 if( digitalRead(float_switchPin) == LOW){
 lcd.print(" LOW");
 digitalWrite(tank_statusPin,HIGH);}


 
 digitalWrite(motorPin,LOW);
 
 
 if(analogRead(moisture_sensorPin) < avg_moisture && digitalRead(float_switchPin) == HIGH)
 { 
 
 while(analogRead(moisture_sensorPin) < avg_moisture && digitalRead(float_switchPin) == HIGH)
 { 
 lcd.setCursor(0,0);
 lcd.print(" MOISTURE - LOW");
 lcd.setCursor(0,1);
 lcd.print(" MOTOR IS ON "); 
 digitalWrite(soil_statusPin,LOW);
 digitalWrite(tank_statusPin,LOW); 
 digitalWrite(motorPin,HIGH); 
 }
 
 if(analogRead(moisture_sensorPin) > avg_moisture){
 lcd.setCursor(0,0);
 lcd.print(" MOISTURE - HIGH");
 lcd.setCursor(0,1);
 lcd.print(" MOTOR - OFF "); 
 digitalWrite(soil_statusPin,HIGH);
 digitalWrite(motorPin,LOW);
 delay(3000);}
 
 if(digitalRead(float_switchPin) == LOW){
 lcd.setCursor(0,0);
 lcd.print(" TANK LEVEL- LOW");
 lcd.setCursor(0,1);
 lcd.print(" MOTOR - OFF "); 
 digitalWrite(tank_statusPin,HIGH);
 digitalWrite(motorPin,LOW);
 delay(3000);}

}
 delay(500);
}
                In the programming part, to facilitate communication between Arduino and LCD module, we make use of a built in library in Arduino <LiquidCrystal.h> – which is written for LCD modules making use of the Hitachi HD44780 chipset (or a compatible chipset). This library can handle both 4 bit mode and 8 bit mode wiring of LCD. In 4 bit mode, data is sent using 4 data pins and 3 control pins. In our project, R/W pin is always grounded so we require only 6 pins in 4 bit mode, thus saving no of pins. During interfacing  the library is first initialized and then define pins using the command LiquidCrystal lcd(RS, E, D4, D5, D6, D7), pins are assigned in this order. In program we can see this command as LiquidCrystal lcd(13,12, 11, 10, 9, 8), here RS pin to 13, Enable pin to 12, D4 pin to 11, D5 pin to 10, D6 pin to 9 and D7 pin to 8 respectively.
The Arduino reads the sensor output through the analog input pins using analogRead function. For example “analogRead(moisture_sensorPin);” converts the voltage (in the range 0 to 5V) at the  A0 pin into a number (in the range 0 to 1023) This way the voltage at A0 is compared to a fixed number (avg_moisture) for identifying the current status of the soil .=
The status of the float switch is compared to identify the current water level and according to these both sensor status the controller will switch the motor to ON or OFF condition. If  values from the float switches is high and if the reading from the moisture sensor is low, then controller will shows a full level tank status and a low level moisture status on LCD and  switches the motor to ON condition. This is done by giving a signal to the base of the BC547 transistor which is connected to the 4th pin of the arduino UNO. The controller will also switch the moisture status LED and the tank status LED OFF by writing a digital 0 to the 2nd and 3rd pin of arduino.  The motor will be in ON condition  until the moisture content goes above reference value or if the float switch status become low. 

Comments