Build Your Own Plant Watering Robot With a Raspberry Pi
by sguequierre in Circuits > Raspberry Pi
1291 Views, 2 Favorites, 0 Comments
Build Your Own Plant Watering Robot With a Raspberry Pi
Building a useful robot doesn’t have to require complicated code or expensive equipment. With a Raspberry Pi and some cheap, basic hardware, you can keep your plants healthy and happy from anywhere in the world!
Follow this guide to learn how to set up an automatic plant watering system with a Raspberry Pi and moisture sensor.
Supplies
The tutorial uses the following hardware, but you can adjust it as needed:
- A Raspberry Pi 3B or 4B with SD card and 5V USB power supply
- A capacitive soil moisture sensor
- A peristaltic pump motor and tubing
- An Adafruit MCP3008 ADC
- A motor speed controller
- A breadboard
- A 9V battery
- Optional: wire leads in place of alligator clips for wiring the battery
- Assorted breadboard jumper wires, including wires with alligator clips
- A planter box or flower pot
- A water container
- A screwdriver
Set Up Your Plant Watering Robot
Before programming the Pi to make the plant watering robot functional, you need to physically set up the plant watering robot by wiring the different components together. You will set up the robot to receive signals from the capacitive soil moisture sensor and signal to the peristaltic pump when it is time to pump water from the water’s container to the plant’s container.
Full wiring diagram
Refer back to this diagram as you complete the steps to wire your hardware.
Wire your ADC
The analog-to-digital converter (ADC) converts the capacitive soil moisture sensor’s analog readings to digital signals that can be processed by your Pi, which expects digital signals to come to it through its GPIO pins.
Start wiring your project by wiring your ADC to your Raspberry Pi board.
You can find a Raspberry Pi pinout diagram at pinout.xyz. Reference the following pinout diagram for your MCP3008 analog-to-digital converter:
The half circle shown in the pinout diagram above should be physically present on your ADC. Use this to orient the ADC to determine the location to insert your wires.
Insert the MCP3008 into your breadboard so that it bridges both sides of the divide. Then, use the rows on the side of your MCP3008’s pins and the GPIO pins on your PI to connect the pins with wires as follows:
Wire your capacitive soil moisture sensor
Next, wire your capacitive soil moisture sensor to your Pi and ADC.
Reference this diagram of the blue module part of the sensor:
Start by connecting the female jumper wires at the end of the sensor prongs to the blue module where the diagram shown above is labeled “Connect with Probe.”
Then, wire the rest of the pins on the module to the Pi and ADC as follows:
Put the soil moisture sensor inside of the container holding your plant.
Wire your pump
Now, wire and power your Peristaltic Pump motor and motor speed controller to complete your hardware setup.
Reference this diagram of the motor speed controller:
- Attach alligator wire clips to your battery to connect it to the DC power pins on your motor speed controller. Match the + notation on the battery to the + DC power pin.
- Attach alligator wire clips to the pump to connect the output pins on your motor speed controller to the pump.
- Connect the GND pin hole on the controller to GND on the Pi.
- Connect the PWM pin hole on the pump to Pin 12 (GPIO 18) of the Pi. Note that the controller does not come with header pins.
Tips:
To complete steps 2 and 3, you must insert the end of the jumper wires into the DC and output pin gates on the motor speed controller and tighten the screws on these gates with your screwdriver to close the wires inside.
For steps 3 and 4, note that the motor speed controller linked does not come with header pins. You can either bend or soldier the jumper wire here to make the connection between the jumper wire and the PWM hole of the controller.
Program Your Plant Watering Robot
Enable SPI on your Pi
Now that you have wired your ADC and moisture sensor, make sure that the Serial Peripheral Interface (SPI) is enabled on your Pi. Enabling this protocol is necessary to allow the Pi to communicate with the moisture sensor peripheral.
SSH into your Pi and run the following command:
sudo raspi-config
Once the raspi-config interface is open, navigate to Interface Options:
Then, select SPI:
Now, select Yes to enable SPI:
Finally, select Finish. Restart your Pi using sudo reboot to make these changes take effect.
Test your soil moisture readings on your Pi
Next, install the Adafruit ADC library Adafruit_CircuitPython_MCP3xxxon your Pi.
Before installation, make sure any packages on your Pi are up to date:
sudo apt update
sudo apt upgrade
Make sure you have pip installed for Python 3:
pip --version
If not, run the following command:
sudo apt install python3-pip
Run the following command while connected to your Pi with SSH to install Adafruit_CircuitPython_MCP3xxx:
sudo pip3 install adafruit-circuitpython-mcp3xxx
Create a new directory for your plant watering robot’s files and navigate to this directory in your terminal session. For example, run the following commands:
mkdir plant-watering-robot
cd plant-watering-robot
After navigating to this directory, create a new Python file called adctesting.py and open up the file. For example, run the following commands:
touch adctesting.py
nano adctesting.py
Now, add the following Python code to adctesting.py to test reading values from your capacitive soil moisture sensor through your MCP3008 ADC:
import time
import busio
import digitalio
import board
import adafruit_mcp3xxx.mcp3008 as MCP
from adafruit_mcp3xxx.analog_in import AnalogIn
# Create the SPI bus
spi = busio.SPI(clock=board.SCK, MISO=board.MISO, MOSI=board.MOSI)
# Create the cs (chip select)
cs = digitalio.DigitalInOut(board.D8)
# Create the MCP3008 object
mcp = MCP.MCP3008(spi, cs)
# Create an analog input channel on Pin 0
chan = AnalogIn(mcp, MCP.P0)
print('Reading MCP3008 values, press Ctrl-C to quit...')
while True:
print('Raw ADC Value: ', chan.value)
time.sleep(1)
Run the code as follows:
sudo python3 adctesting.py
Tip: If running this code returns ImportError: No module named busio, try again after reinstalling adafruit-blinka:
sudo pip3 install --force-reinstall adafruit-blinka
Now, you should see the moisture sensor values outputted by the MCP3008.
Test your sensor by putting it in air, water, and different soils to see how the values change to determine your baseline for wet and dry values.
Configure the components of your robot in the Viam app
Follow this guide to install viam-server on your Pi, create a new robot, and connect to it on the Viam app.
Then, navigate to your new robot’s page on the app and click on the Config tab.
First, add your Pi as a board component by creating a new component with type board and model pi:
Raw JSON Mode:
{
"components": [
{
"name": "local",
"type": "board",
"model": "pi",
"attributes": {},
"depends_on": []
} // Motor JSON ...
]
}
Then, add your pump as a motor component by adding a new component with typemotor and modelgpio.
Set the motor’s attributes Max RPM to 1000 and PWM to 12 GPIO 18 (the board and GPIO pin that you wired the pump’s PWM to).
Raw JSON Mode:
// Board JSON ... },
{
"name": "water-pump",
"type": "motor",
"model": "gpio",
"attributes": {
"pins": {
"a": "",
"b": "",
"dir": "",
"pwm": "12"
},
"board": "local",
"max_rpm": 1000
},
"depends_on": []
}
Click Save config.
Now, if you navigate to your robot’s Control tab, you should be able to control the motor by setting the power and direction of rotation and clicking the RUN button:
Configure the ADC as a module from the registry
Resources refer to the different components and services Viam provides for robots to use. Components refer to types of hardware, and each component’s built-in models support the most common models of this hardware. For example, the sensor component has an ultrasonic model built in for the ubiquitous ultrasonic sensor.
However, there are many different types of sensors used for sensing different things across the Internet of Things. Although the capacitive soil moisture sensor is not currently one of Viam’s built-in models, you can add an analog-to-digital-converter (ADC) as a module and use it to get readings from the moisture sensor.
A module provides one or more modular resources, which add resource types (components and services) or models that are not built into Viam. A module can be added to your robot from the Viam registry.
The Viam registry allows hardware and software engineers to collaborate on their robotics projects by writing and sharing custom modules with each other. You can add a module from the Viam registry directly from your robot’s Configuration tab in the Viam app, using the + Create component button.
Add the mcp300x-adc-sensor module to your robot in 4 steps:
1. Go to your robot's Config tab. Select Create component.
2. Search mcp300x. Click Add module.
3. Give your module a name of your choice, and click Create to add this module to your robot.
4. Find your module's card on the Config page. In Attributes, add the necessary attributes as "channel_map" and "sensor_pin".For example, if you have a moisture sensor on channel 0, and your sensor_pin is 8, your configuration should look like this:
{
"channel_map": {
"moisture": 0
},
"sensor_pin": 8
}
This module allows you to get multiple readings at the same time from different channels of the ADC sensor. If you wire and configure another sensor, such as a temperature sensor on channel 1, you can add the sensor to the "channel_map" and get a reading from it.
If you would like to see how the module works, you can find its code on GitHub.
Now that you have set up your robot and are able to control your motor, you can put the suction tube of your pump into the water cup, and the output tube into the plant!
Add Python control code
Follow these instructions to start working on your Python control code:
- Navigate to your robot’s page in the Viam app, and click on the Code sample tab.
- Select Python as the language.
By default, the sample code does not include your robot location secret. We strongly recommend that you add your location secret as an environment variable and import this variable into your development environment as needed. To show your robot’s location secret in the sample code, toggle Include secret on the Code sample tab. You can also see your location secret on the locations page. Do not share your location secret, part secret, or robot address publicly.
- Click Copy to copy the generated code sample, which establishes a connection with your robot when run.
- Paste this code sample into a new file in the plant-watering-robot directory you created on your Pi.
- Name the file plant-watering-robot.py, and save it.
For example, run the following commands on your Pi to create and open the file:
cd plant-watering-robot
touch plant-watering-robot.py
nano plant-watering-robot.py
Now, you can add code into plant-watering-robot.py to write the logic that defines your plant watering system.
To start, add your system logic code into the main() function of the program. Use the Viam motor and sensor API methods.
You can get your components from the robot like this:
# Note that this name, `sensor`, is defined when you add the module
sensor = Sensor.from_robot(robot=robot, name='sensor')
water_pump = Motor.from_robot(robot=robot, name='water-pump')
And you can add your system logic to run continuously like this:
while True:
# Get the moisture sensor's readings
readings = await sensor.get_readings()
soil_moisture = readings.get('moisture')
# Calculate average moisture reading from the list of readings, to account
# for outliers
avg_moisture = sum(soil_moisture) / len(soil_moisture)
# If the average moisture reading is greater than 60000, trigger pump
# watering
if (avg_moisture > 60000):
print('this plant is too thirsty! giving it more water')
# Run the water pump for 100 rev. at 1000 rpm
await water_pump.go_for(rpm=1000, revolutions=100)
# Wait 60 seconds so that the water can soak into the soil a bit before
# trying to water again
print('waiting a little bit for water to soak in')
time.sleep(60)
Tip: Make sure to import time at the beginning of your version of plant-watering-robot.py to be able to use sleep()! Also, make sure to import viam.components.sensor.
See the motor component’s API documentation for more information about water_pump.go_for().
Save your plant-watering-robot.py program with this logic added in, and then run it on your Pi like this:
sudo python3 plant-watering-robot.py
To tinker this example code to work best for you, determine at what analog value from the soil moisture readings you want to water your plant, as your thirsty plant’s average moisture reading might differ from our example value of 60000. Also, consider how often you would like to check the moisture levels of the plant, and how long the plant should be watered.
Next Steps
Now that you have created your automatic plant watering system with a capacitive soil moisture sensor, you can easily use Viam to automate other aspects of your garden. For example, you can use a light sensor or a temperature sensor, and get readings from other channels of the MCP3008!
If you build something based on this please share it in Viam's Community Discord - we’d love to see it.