Close
0%
0%

Plant Foliage Health Monitor

Spectrophotometer To Determine Normalized Difference Vegetation Index (NDVI) Built With Raspberry Pi And NIR Spectral Sensor

Public Chat
Similar projects worth following
This project uses the AS7263 NIR (near infrared) spectrometer sensor and the Raspberry Pi 4B board to assess plant foliage health. It explains how to uses the sensor’s channel readings and the standard Normalized Difference Vegetation Index (NDVI) equation to calculate an estimated NDVI value. Also prints the value and a “HEALTHY” or “UNHEALTHY” statement, and turns ON an RGB LED to green or red to indicate whether the foliage is healthy or not, respectively. Finally, it saves the test data into a CSV format file. The latest version includes a real-time IoT monitoring to share the captured information to the whole world in the internet cloud.

This is something that I have wanted to do for a long time because I have always been interested in the measurement of the phenomenon of light. I even once won a prize proposing a new method to measure light. Below I show an introduction to my project.

How does it work?

  1. First, I built a module to accommodate the AS7263 sensor. The goal is to prevent strange light interference.
  2. Then, the pHat module will be configured to interface the AS7263 sensor with the Raspberry Pi board.
  3. The AS7263 NIR Sensor libraries wias installed.
  4. The experiment has a scientific nature. I developed a "Plant Foliage Health Monitor". Here I used the AS7263 NIR (near infrared) sensor, and I adapted a module to do the tests. The objective is to analyze samples of plant leaves and verify their health status as "HEALTHY" or "UNHEALTHY".
  5. The last experiment consists of adapting an IoT monitoring system in real time. The goal is to do experiments and send data to the internet cloud so that colleagues around the world can see the data from our experiments in real time.

plant_foliage_health_monitor_ver2.zip

Code version 2 (Real-Time IoT Monitoring)

x-zip-compressed - 7.34 kB - 06/03/2023 at 05:51

Download

AS7263.pdf

Datasheet

Adobe Portable Document Format - 778.47 kB - 05/30/2023 at 18:46

Preview
Download

x-zip-compressed - 1.01 kB - 05/30/2023 at 15:41

Download

ndvi.zip

CSV file obtained during testing

x-zip-compressed - 2.87 kB - 05/30/2023 at 05:47

Download

stl_files.zip

3D files in STL format

x-zip-compressed - 9.59 kB - 05/30/2023 at 05:33

Download

  • 1 × Raspberry Pi 4B
  • 1 × AS7263 NIR Sensor
  • 1 × Qwiic pHAT module
  • 1 × Qwiic Cable
  • 1 × RGB LED

  • 10. Real-Time IoT Monitoring

    Guillermo Perez Guillen06/03/2023 at 05:36 0 comments

    The main goal of this log is to make an IoT connection from our Spectrophotometer to the IoT cloud and using the ThingSpeak platform.

    Schematic

    Below I attach the schematic diagram of this scientific experiment.

    How does this work?

    • As you can see, we are connecting the spectrophotometer to the Gateway via WiFi connection to send the captured data to the internet cloud.
    • The captured NIR values are packaged to be sent to the ThingSpeak server: R,S,T,U,V,W, and NDVI.
    • In this way, the testing laboratory can share the information with colleagues anywhere in the world.

    ThingSpeak

    ThingSpeak is an IoT analytics platform service that allows you to aggregate, visualize, and analyze live data streams in the cloud. You can send data to ThingSpeak from your devices, create instant visualizations of live data, and send alerts using web services like Twitter® and Twilio®. With MATLAB® analytics inside ThingSpeak, you can write and execute MATLAB code to perform preprocessing, visualizations, and analyses. ThingSpeak enables engineers and scientists to prototype and build IoT systems without setting up servers or developing web software.

    https://thingspeak.com/

    image

    Once an account is created on ThingSpeak, we create a new channel and insert the following fields:

    The system generates several data for us, the one that we will use in the code of our Raspberry Pi is the Write API Key

    Now we are ready to capture the data in the  channel.

    Programming

    Below I show you the code to be uploaded to the Raspberry Pi and then I'll give you some comments.

    iotmonitoring_ndvi.py

    from as7263 import AS7263
    import time
    import RPi.GPIO as GPIO
    import http.client 
    import urllib.parse
    
    as7263 = AS7263()
    
    as7263.set_gain(16)
    as7263.set_integration_time(17.857)
    as7263.set_measurement_mode(2)
    as7263.set_illumination_led(1)
    
    redPin = 16   #Set to appropriate GPIO
    greenPin = 18 #Should be set in the 
    GPIO.setwarnings(False) #to disable warnings
    
    def blink(pin):
        GPIO.setmode(GPIO.BOARD)
        
        GPIO.setup(pin, GPIO.OUT)
        GPIO.output(pin, GPIO.HIGH)
        
    def turnOff(pin):
        GPIO.setmode(GPIO.BOARD)
        GPIO.setup(pin, GPIO.OUT)
        GPIO.output(pin, GPIO.LOW)
    
    def redOn():
        blink(redPin)
    
    def redOff():
        turnOff(redPin)
    
    def greenOn():
        blink(greenPin)
    
    def greenOff():
        turnOff(greenPin)
    
    key = "PX9QECQRVCLKD042"  # Put your API Key here QLB4X8O1OTCZFW1Q
    
    try:
    #    def dedos():    
        while True:
            values = as7263.get_calibrated_values()
            R, S, T, U, V, W = [(value) for value in values]
            print("R = " + "{:4.6f}".format(R))
            print("S = " + "{:4.6f}".format(S))
            print("T = " + "{:4.6f}".format(T))
            print("U = " + "{:4.6f}".format(U))
            print("V = " + "{:4.6f}".format(V))
            print("W = " + "{:4.6f}".format(W))
            NDVI=((V-S)/(V+S))
            print("NDVI = {:4.2f}".format(NDVI))
            file = open("NDVI_thingspeak.csv","a")
            file.write("{0:0.1f},{1:0.1f},{2:0.1f},{3:0.1f},{4:0.1f},{5:0.1f},{6:0.1f}".format(R, S, T, U, V, W, NDVI)+"\n")
            file.close()
            time.sleep(1.0)
            if NDVI > 0.2 and NDVI < 0.60:
                print("HEALTY" + "\n")
                greenOn()
                redOff()
            else:
                print("UNHEALTHY" + "\n")
                redOn()
                greenOff()
            params = urllib.parse.urlencode({'field1': R, 'field2': S, 'field3': T, 'field4': U, 'field5': V, 'field6': W, 'field7': NDVI*100, 'key':key }) 
            headers = {"Content-typZZe": "application/x-www-form-urlencoded","Accept": "text/plain"}
            conn = http.client.HTTPConnection("api.thingspeak.com:80")
            try:
                conn.request("POST", "/update", params, headers)
                response = conn.getresponse()
                print (R, S, T, U, V, W, NDVI)
                print (response.status, response.reason)
                data = response.read()
                conn.close()
                #time.sleep(1.0)
            except:
                print ("connection failed")
            #break
    
    except KeyboardInterrupt:
        as7263.set_measurement_mode(3)
        as7263.set_illumination_led(0)
    
    • The "http.client" library is installed by default in the Raspbian operating system. In addition, I installed the urllib3 library, which contains the version of urllib:
    python -m pip install urllib3
    • Insert your Write API KEY here:
    key =...
    Read more »

  • 9. First Conclusions

    Guillermo Perez Guillen05/30/2023 at 18:39 0 comments

    From the tests I did I could notice these constants:

    1. The healthy leaves gave NDVI values between 0.2 and 0.35;
    2. The semi-dry leaf gave NDVI values between 0.4 and 0.5 in its green area; and
    3. The dried leaves gave NDVI values between 0.66 and 0.75 approx.

    Recommendations to build the AS7263 sensor module: 

    1. It's not necessary to add any additional light source since the LED that the module itself has is sufficient;
    2. It's necessary to place a holder for the leaves so that they are at a constant distance from the sensor (5mm); and 
    3. We must do the tests in a room where the light is constant, it is not recommended to do the tests outdoors due to the strong solar radiation.

    The tests carried out were satisfactory, and it was a good experience to learn new things such as: 

    1. I discovered that the leaves of the plants give NDVI values according to the type of plant analyzed, since the green leaves of plant 1 gave me approx. NDVI values of 0.2, and plant 2 gave me approx NDVI values of 0.3; and 
    2. When I did tests with a semi-dry leaf, I discovered that it gave approximately NDVI values of 0.5 in its green part and 0.73 in its dry part.

  • 8. Image Gallery

    Guillermo Perez Guillen05/30/2023 at 05:46 0 comments

    Here I share some images that I find interesting, like this sample of green leaves.

    image

    Sample of dry leaves.

    image

    Semi dry leaf sample.

    image

    Testing a healthy leaf.

    image

    Testing a unhealthy leaf.

    image

    Testing other healthy leaf.

    image

  • 7. Test

    Guillermo Perez Guillen05/30/2023 at 05:46 0 comments

    Here is a view of the hardware ready to do testing. An important recommendation is that the tests should be done in a light controlled environment similar the one I did. These tests cannot be done outdoors due to the strong solar radiation.

    image

    This is a screenshot of a healthy leaf.

    This other image is a screenshot of an unhealthy leaf.

    Below I show you the video where I did tests with three different types of plant leaves.

    In the download section you can get the CSV file during the test.

  • 6. Programming

    Guillermo Perez Guillen05/30/2023 at 05:38 0 comments

    The libraries don't have code examples for the AS7263 sensor. According to the instructions, you have to use the AS7262 sensor as a reference and make the code by analogy: https://github.com/HeyLlama/as726x-python 

    image

    Below I show you the configuration of the AS7263 sensor: The sensor gain is 16 according to the datasheet.

    as7263 = AS7263()
    
    as7263.set_gain(16)
    as7263.set_integration_time(17.857)
    as7263.set_measurement_mode(2)
    as7263.set_illumination_led(1)

    The configuration of the GPIO pins 16 (red) and 18 (green) of the rgb LED is as follows:

    redPin = 16   #Set to appropriate GPIO
    greenPin = 18 #Should be set in the 
    
    def blink(pin):
        GPIO.setmode(GPIO.BOARD)
        
        GPIO.setup(pin, GPIO.OUT)
        GPIO.output(pin, GPIO.HIGH)
        
    def turnOff(pin):
        GPIO.setmode(GPIO.BOARD)
        GPIO.setup(pin, GPIO.OUT)
        GPIO.output(pin, GPIO.LOW)
    
    def redOn():
        blink(redPin)
    
    def redOff():
        turnOff(redPin)
    
    def greenOn():
        blink(greenPin)
    
    def greenOff():
        turnOff(greenPin)

    The R, S, T, U, V and W values are not indexed. So I got them as shown below:

            values = as7263.get_calibrated_values()
            R, S, T, U, V, W = [(value) for value in values]
            print("R = " + "{:4.6f}".format(R))
            print("S = " + "{:4.6f}".format(S))
            print("T = " + "{:4.6f}".format(T))
            print("U = " + "{:4.6f}".format(U))
            print("V = " + "{:4.6f}".format(V))
            print("W = " + "{:4.6f}".format(W))

    The part of the code that calculates NDVI, and saves the data in the NDVI.csv file is the following:

            NDVI=((V-S)/(V+S))
            print("NDVI = {:4.2f}".format(NDVI))
            file = open("NDVI.csv","a")
            file.write("{0:0.1f},{1:0.1f},{2:0.1f},{3:0.1f},{4:0.1f},{5:0.1f},{6:0.1f}".format(R, S, T, U, V, W, NDVI)+"\n")
            file.close() 

    Finally, the next statement does the following: 1) if the NDVI value is between 0.2 and 0.65, the green led turns ON and prints the message "HEALTHY"; and 2) any other NDVI value, the red led turns ON and prints the "UNHEALTHY" message.

            if NDVI > 0.2 and NDVI < 0.65:
                print("HEALTHY" + "\n")
                greenOn()
                redOff()
            else:
                print("UNHEALTHY" + "\n")
                redOn()
                greenOff()

    Below I show you the code, and then I give you useful comments.

    plantfoliagehealth.py

    from as7263 import AS7263
    import time
    import RPi.GPIO as GPIO
    
    as7263 = AS7263()
    
    as7263.set_gain(16)
    as7263.set_integration_time(17.857)
    as7263.set_measurement_mode(2)
    as7263.set_illumination_led(1)
    
    redPin = 16   #Set to appropriate GPIO
    greenPin = 18 #Should be set in the 
    
    def blink(pin):
        GPIO.setmode(GPIO.BOARD)
        
        GPIO.setup(pin, GPIO.OUT)
        GPIO.output(pin, GPIO.HIGH)
        
    def turnOff(pin):
        GPIO.setmode(GPIO.BOARD)
        GPIO.setup(pin, GPIO.OUT)
        GPIO.output(pin, GPIO.LOW)
    
    def redOn():
        blink(redPin)
    
    def redOff():
        turnOff(redPin)
    
    def greenOn():
        blink(greenPin)
    
    def greenOff():
        turnOff(greenPin)
    
    try:
        while True:
            values = as7263.get_calibrated_values()
            R, S, T, U, V, W = [(value) for value in values]
            print("R = " + "{:4.6f}".format(R))
            print("S = " + "{:4.6f}".format(S))
            print("T = " + "{:4.6f}".format(T))
            print("U = " + "{:4.6f}".format(U))
            print("V = " + "{:4.6f}".format(V))
            print("W = " + "{:4.6f}".format(W))
            NDVI=((V-S)/(V+S))
            print("NDVI = {:4.2f}".format(NDVI))
            file = open("NDVI.csv","a")
            file.write("{0:0.1f},{1:0.1f},{2:0.1f},{3:0.1f},{4:0.1f},{5:0.1f},{6:0.1f}".format(R, S, T, U, V, W, NDVI)+"\n")
            file.close()        
            if NDVI > 0.2 and NDVI < 0.65:
                print("HEALTY" + "\n")
                greenOn()
                redOff()
            else:
                print("UNHEALTHY" + "\n")
                redOn()
                greenOff()
            
            time.sleep(0.5)   
    
    except KeyboardInterrupt:
        as7263.set_measurement_mode(3)
        as7263.set_illumination_led(0)

  • 5. Assembling The Device

    Guillermo Perez Guillen05/30/2023 at 05:12 0 comments

    Schematic Diagram and Wiring

    image

    Below I show you the hardware wiring.

    image

    The box on which I have mounted the AS7263 sensor is something similar to this one:

    image

    This box (part 1) helps you keep the AS7263 sensor motionless in the horizontal plane. The function of part 2 is to hold the leaves at a constant distance above the sensor. I glued the RGB diode connector with silicon. In the download section you can get the STL files.

  • 4. Normalized Difference Vegetation Index (NDVI)

    Guillermo Perez Guillen05/30/2023 at 05:07 0 comments

    Chlorophyll is any of several related green pigments found in cyanobacteria and in the chloroplasts of algae and plants. Chlorophyll allow plants to absorb energy from light. Chlorophylls absorb light most strongly in the blue portion of the electromagnetic spectrum as well as the red portion.Conversely, it is a poor absorber of green and near-green portions of the spectrum. Hence chlorophyll-containing tissues appear green.

    image

    Normalized Difference Vegetation Index (NDVI) quantifies vegetation by measuring the difference between near-infrared (which vegetation strongly reflects) and red light (which vegetation absorbs). So, the scientists use NDVI to assess foliage health by measuring the difference between the amount of near-infrared and red light that is reflected off the foliage, using the following equation: 

    image

    References:

    In my case I used the range between 0.2 to 0.65, because I did tests with my sensor and I found that at values upper 0.7 some leaves were dry. so I lower the upper threshold a bit to ensure good readings.

    For this tutorial, I will apply this method to a three plant’s leaves by plugging in readings from the AS7263 NIR sensor into the NDVI equation. The sensor detects wavelengths across 6 channels and puts out readings as counts per μW/cm2, which gives a measure of the amount of incident light that is being reflected at each wavelength. Two of the sensor’s channels are close to the wavelengths that are typically used in the NDVI equation. These channels are S and V, giving out readings for the 680 nm (red range) and 810 nm (near-infrared) wavelengths, respectively. Once the NDVI value is calculate, we can use an "if else" statement to signal whether the foliage is within a healthy range or not.

  • 3. Getting Started

    Guillermo Perez Guillen05/30/2023 at 05:02 0 comments

    In this chapter we learn how to setup the Raspberry Pi and how to detect the peripheral of the sensor.

    Configuring the Pi

    To get started with your Qwiic pHAT, simply plug it into the headers on the Raspberry Pi with the letters facing you. We'll use the Qwiic pHAT v2.0 in the following image to connect a Qwiic device.

    image

    Once the pHAT is plugged in, you can start plugging in AS7262 6-channel Visible Light Sensor.

    image

    The Raspberry Pi Configuration via Desktop GUI

    You can use the Desktop GUI by heading to the Pi Start Menu > Preferences > Raspberry Pi Configuration. A window will pop up with different tabs to adjust settings. What we are interested is the Interfaces tab. Click on the tab and select Enable for I2C. Click on the OK button.

    image

    It's recommend restarting your Pi to ensure that the changes to take effect. Click on the Pi Start Menu > Preferences > Shutdown. Since we just need to restart, click on the Restart button. The system will reboot. When it comes back up, log in and enter the following command

    ls /dev/*i2c*
    
    

    image

    The Pi should respond with

    /dev/i2c-1

    Which represents the user-mode I2C interface. There is a set of command-line utility programs that can help get an I2C interface working. You can get them with the apt package manager. Enter the following command

    sudo apt-get install -y i2c-tools

    image

    In particular, the i2cdetect program will probe all the addresses on a bus, and report whether any devices are present. Enter the following command in the command line. The -y flag will disable interactive mode so that you do not have to wait for confirmation. The 1 indicates that we are scanning for I2C devices on I2C bus 1.

    i2cdetect -y 1

    You will get an output from your Raspberry Pi similar to the output below.

    image

    This map indicates that there is a peripheral at address 0x49, and according to the AS7263 datasheet, device address is 49 hex.

    image

  • 2. Hardware

    Guillermo Perez Guillen05/30/2023 at 04:51 0 comments

    In this chapter I show you the main features of Raspberry Pi 4B, Qwiic pHAT module and AS7263 sensor. 

    Raspberry Pi 4B

    This product’s key features include a high-performance 64-bit quad-core processor, dual-display support at resolutions up to 4K via a pair of micro-HDMI ports, hardware video decode at up to 4Kp60, up to 4GB of RAM, dual-band 2.4/5.0 GHz wireless LAN, Bluetooth 5.0, Gigabit Ethernet, USB 3.0, and PoE capability (via a separate PoE HAT add-on). The dual-band wireless LAN and Bluetooth have modular compliance certification, allowing the board to be designed into end products with significantly reduced compliance testing, improving both cost and time to market.

    image

    • Broadcom BCM2711, Quad core Cortex-A72 (ARM v8) 64-bit SoC @ 1.8GHz
    • 1GB, 2GB, 4GB or 8GB LPDDR4-3200 SDRAM (depending on model)
    • 2.4 GHz and 5.0 GHz IEEE 802.11ac wireless, Bluetooth 5.0, BLE
    • Gigabit Ethernet
    • 2 USB 3.0 ports; 2 USB 2.0 ports.
    • Raspberry Pi standard 40 pin GPIO header (fully backwards compatible with previous boards)
    • 2 × micro-HDMI ports (up to 4kp60 supported)
    • 2-lane MIPI DSI display port
    • 2-lane MIPI CSI camera port
    • 4-pole stereo audio and composite video port
    • H.265 (4kp60 decode), H264 (1080p60 decode, 1080p30 encode)
    • OpenGL ES 3.1, Vulkan 1.0
    • Micro-SD card slot for loading operating system and data storage
    • 5V DC via USB-C connector (minimum 3A*)
    • 5V DC via GPIO header (minimum 3A*)
    • Power over Ethernet (PoE) enabled (requires separate PoE HAT)
    • Operating temperature: 0 – 50 degrees C ambient

    AS7263 NIR Sensor

    The AS7263 Near Infrared (NIR) Spectral Sensor brings spectroscopy and makes it easier to measure and characterize different materials absorb and reflect different wavelengths of light. The Sparfun AS7263 Breakout has the ability to communicate by both an I2C interface and serial interface using AT commands. Hookup is easy, thanks to the Qwiic connectors attached to the board.

    image

    The AS7263 spectrometer detects wavelengths in the visible range at 610, 680, 730, 760, 810 and 860nm of light, each with 20nm of full-width half-max detection. The board also has multiple ways for you to illuminate objects that you will try to measure for a more accurate spectroscopy reading. There is an onboard LED that has been picked out specifically for this task, as well as two pins to solder your own LED into. The I2C address of the AS7263 is 0x49 and is hardware defined.

    • 6 near-IR channels: 610nm, 680nm, 730nm, 760nm, 810nm and 860nm, each with 20nm FWHM
    • NIR filter set realized by silicon interference filters
    • 16-bit ADC with digital access
    • Programmable LED drivers
    • 2.7V to 3.6V with I2C interface

    Below you can see the spectral responsivity of this sensor.

    image

    SparkFun Qwiic pHAT v2.0 

    The SparkFun Qwiic pHAT connects the I2C bus (GND, 3.3V, SDA, and SCL) on your Raspberry Pi to an array of Qwiic connectors on the HAT. Since the Qwiic system allows for daisy-chaining boards with different addresses, you can stack as many sensors as you’d like. The Qwiic pHAT V2.0 has four Qwiic connect ports (two on its side and two vertical), all on the same I2C bus. It also add a simple 5V screw terminal to power boards that may need more than 3.3V and a general-purpose button. This pHAT is compatible with any Raspberry Pi that utilizes the standard 2x20 GPIO header.

    image

    • 4x Qwiic Connection Ports
    • 1x 5V Tolerant Screw Terminal
    • 1x General Purpose Button
    • HAT-compatible 40-pin Female Header

  • 1. Introduction

    Guillermo Perez Guillen05/30/2023 at 04:27 0 comments

    Optics

    I assume you already have basic knowledge of optics. Optics is the study of light. Optics describes how light is created and how it travels. An important part of optics is the study of what happens when light hits different surfaces. When light hits a surface, it may be reflected, refracted, or absorbed.

    • Reflection occurs when light hits a surface and bounces back. Reflected light makes images appear in mirrors and in other smooth, shiny surfaces.
    • Refraction happens when light changes direction, or bends, when it moves from one material to another. For example, light traveling through the air refracts when it hits water. This can make a straw in a glass of water look bent at the surface of the water.
    • Some surfaces absorb, or take in, light. This causes the surface to heat up. For example, a sidewalk heats up on a hot, sunny day because it is absorbing light.

    image

    Spectrophotometry

    Spectrophotometry is the quantitative measurement of the interaction of ultraviolet (UV), visible, and infrared (IR) radiation with a material and has an impact on a wide field of science and technology.  Spectrophotometry uses photometers, known as spectrophotometers, that can measure the intensity of a light beam at different wavelengths. 

    image

    Types of spectrophotometers:

    • Infrared spectrum: study and identification of chemical substances
    • Ultraviolet spectrum: identification of molecules, black light.
    • NMR spectrophotometer: atomic/nuclear absorption.
    • Reflectance spectrophotometer: this is the spectrum used in paint and body shops to measure color (konica minolta, etc.)
    • Double beam spectrophotometer.
    • Single beam spectrophotometer.

    A double-beam spectrophotometer compares the light intensity between two light paths, one path containing a reference sample and the other the test sample. A single-beam spectrophotometer measures the relative light intensity of the beam before and after a test sample is inserted. Although comparison measurements from double-beam instruments are easier and more stable, single-beam instruments can have a larger dynamic range and are optically simpler and more compact. Additionally, some specialized instruments, such as spectrophotometers built onto microscopes or telescopes, are single-beam instruments due to practicality.

View all 10 project logs

  • 1
    Software apps and online services
    • Python
    • ThingSpeak IoT Platform
    • Excel
  • 2
    Hand tools and fabrication machines
    • 3D Printer
    • Drill
    • Soldering iron
    • Silicone
    • Glue
    • Screws

View all instructions

Enjoy this project?

Share

Discussions

Guillermo Perez Guillen wrote 05/30/2023 at 19:10 point

This project is open source and is one way we can monitor plant health and help keep our planet running a little cleaner and healthier. I can see green foliage, but I didn't know if I had enough chlorophyll until I used this device.

  Are you sure? yes | no

Similar Projects

Does this project spark your interest?

Become a member to follow this project and never miss any updates