LED Control With APDS-9960 Gesture Sensor Using Raspberry Pi Zero W

Overview

This is a simple application of the APDS-9960 Gesture Sensor on the Raspberry Pi Zero. Throughout the tutorial, you’ll learn about the basics of installing libraries on the Raspberry Pi as well as using them to aid you in the code. In this tutorial, we will use Python programming language to program our Raspberry Pi. Hence, for people migrating from Arduino, learning LED control is the best way to get started on Raspberry Pi projects and become more familiar with Python.


Hardware Used

  • Raspberry Pi Zero W – 1
  • 
    APDS-9960 Gesture Sensor – 1
  • 
    LED – 4
  • 
    Breadboard – 1

  • Jumper Wires
  • 
    
    

    Software Used

    Libraries Used

    • time

    Application Description

    Raspberry Pi Zero W

    The Raspberry Pi (RPi) is a series of small single-board computers developed by Raspberry Pi Foundation to promote teaching of basic computer science in schools and in developing countries. The RPi has been widely used to make devices like cameras, gaming machines, robots, web servers and media centers.

    Pin Mapping

    How does it work?

    The RPi works similar to an Arduino in terms of how it operates, but there are several differences between the two. All Raspberry Pi boards support Python as the main language, but also support Ruby, C/C++, Javascript, while the Arduino only supports C/C++. Moreover, the RPi is more expensive and much more complex for beginners looking to get into electronics projects. However, it can handle multiple programs at a time due to its higher processing power.

    APDS-9960 Gesture Sensor

    The APDS-9960 Gesture Sensor module is not only capable of touchless gesture sensing, but is also of advanced proximity detection, ambient light sensing, and RGB color sensing. Four sensors in such a slim modular package! For this project however, we’ll only be focusing on the gesture sensing. You can check out how to use its proximity sensing feature to turn LEDs on by clicking here.

    How does it work?

    It utilizes four directional photodiodes to sense reflected IR energy to convert physical motion information (i.e. velocity, direction and distance) to a digital information. Learn more from its datasheet.


    Hardware Setup

    APDS-9960 Gesture Sensor Connections

    • SDA connected to RPi board pin 3
    • SCL connected to RPi board pin 5
    • INT connected to RPi board pin 7
    • VCC and GND connected to 5V and Ground respectively

    Fun Fact: SCL (Serial Clock) and SDA (Serial Data) pins are the dedicated pins for I2C communication. On the Raspberry Pi Zero they are found on board pins 3 and 5.

    LED Connections

    • 1st LED connected to RPi board pin 8
    • 2nd LED connected to RPi board pin 10
    • 3rd LED connected to RPi board pin 12
    • 4th LED connected to RPi board pin 16

    Raspberry Pi Setup

    Before proceeding, you need to be able to connect to your Raspberry Pi using the VNC Viewer. Click here for the official documentation on how to do it made by the company themselves.

    Enabling I2C

    To allow the Gesture Sensor to work, we have to enable I2C through the Raspberry Pi Configurations. This also allows us to use the smbus library. Assuming you’ve already connected to your Raspberry Pi, click on the raspberry icon on the bottom left, hover over Preferences, and click on “Raspberry Pi Configuration.”

    When the window pops up, click on “Interfaces” and ensure that I2C is enabled. Once done, click “OK.”

    Installing Required Libraries

    Next, we have to install the Python-APDS9960 library so make sure your Raspberry Pi is connected to the Internet. Open the Terminal by clicking its icon on the bottom left and simply enter the command pip install apds9960.


    Code

    For the code, you can do it on your computer via Python IDLE, Notepad++, or any text editing software or IDE that supports Python then transfer it to the Raspberry Pi through the VNC Viewer. You can also code inside the RPi itself, but I find this to be easier.

    from apds9960.const import *
    from apds9960 import APDS9960
    import RPi.GPIO as GPIO
    import smbus
    
    port = 1
    bus = smbus.SMBus(port)
    
    apds = APDS9960(bus)
    
    GPIO.setmode(GPIO.BOARD)
    GPIO.setup(7, GPIO.IN)
    GPIO.setup(8, GPIO.OUT)
    GPIO.setup(10, GPIO.OUT)
    GPIO.setup(12, GPIO.OUT)
    GPIO.setup(16, GPIO.OUT)
    state1 = False
    state2 = False
    state3 = False
    state4 = False
    
    dirs = {
        APDS9960_DIR_NONE: "none",
        APDS9960_DIR_LEFT: "left",
        APDS9960_DIR_RIGHT: "right",
        APDS9960_DIR_UP: "up",
        APDS9960_DIR_DOWN: "down",
        APDS9960_DIR_NEAR: "near",
        APDS9960_DIR_FAR: "far",
    }
    
    GPIO.add_event_detect(7, GPIO.FALLING)
    
    apds.setProximityIntLowThreshold(50)
    
    print("Gesture Test")
    apds.enableGestureSensor()
    while True:
    	if apds.isGestureAvailable():
    		motion = apds.readGesture()
    		print("Gesture={}".format(dirs.get(motion, "unknown")))
    		if (motion == APDS9960_DIR_UP):
    			if (state1 == False):
    				GPIO.output(8, GPIO.HIGH)
    				state1 = True
    			elif (state1 == True):
    				GPIO.output(8, GPIO.LOW)
    				state1 = False
    		elif (motion == APDS9960_DIR_DOWN):
    			if (state2 == False):
    				GPIO.output(10, GPIO.HIGH)
    				state2 = True
    			elif (state2 == True):
    				GPIO.output(10, GPIO.LOW)
    				state2 = False
    		elif (motion == APDS9960_DIR_LEFT):
    			if (state3 == False):
    				GPIO.output(12, GPIO.HIGH)
    				state3 = True
    			elif (state3 == True):
    				GPIO.output(12, GPIO.LOW)
    				state3 = False
    		elif (motion == APDS9960_DIR_RIGHT):
    			if (state4 == False):
    				GPIO.output(16, GPIO.HIGH)
    				state4 = True
    			elif (state4 == True):
    				GPIO.output(16, GPIO.LOW)
    				state4 = False

    To run the code, open the terminal and change the directory to where the file is located using the command cd <directory> then run the command python <file name>.py.


    Code Breakdown

    Library Import

    from apds9960.const import *
    from apds9960 import APDS9960
    import RPi.GPIO as GPIO
    import smbus

    First things first, we must include the libraries to be used in the project. The APDS9960 library will allow the Gesture Sensor to work. The RPi.GPIO library provides a class to control the GPIO on the Raspberry Pi and the smbus library allows the I2C protocol that the Gesture Sensor requires.

    Channel & Pin Setup

    port = 1
    bus = smbus.SMBus(port)
    
    apds = APDS9960(bus)
    
    GPIO.setmode(GPIO.BOARD)
    GPIO.setup(7, GPIO.IN)
    GPIO.setup(8, GPIO.OUT)
    GPIO.setup(10, GPIO.OUT)
    GPIO.setup(12, GPIO.OUT)
    GPIO.setup(16, GPIO.OUT)
    state1 = False
    state2 = False
    state3 = False
    state4 = False

    Next, we set the SMBus port to 1, which is the default, and then set the APDS9960 Gesture Sensor to that bus. After that, we set the GPIO pin mode to follow the board numbers for easier identification, set the pin 7 as the input coming from the Gesture Sensor, and set pins 8, 10, 12, and 16 as the output for the 4 LEDs. states 1-4 are initially set to false to indicate that the LEDs will be initially in an off state.

    Dictionary for Print

    dirs = {
        APDS9960_DIR_NONE: "none",
        APDS9960_DIR_LEFT: "left",
        APDS9960_DIR_RIGHT: "right",
        APDS9960_DIR_UP: "up",
        APDS9960_DIR_DOWN: "down",
        APDS9960_DIR_NEAR: "near",
        APDS9960_DIR_FAR: "far",
    }

    This part is a dictionary where each gesture detected by the Gesture Sensor, defined by APDS9960_DIR_<gesture> in the Python-APDS9960 library is equated to shorter, easier to understand words to be printed later on.

    Gesture Detection Loop

    while True:
    	if apds.isGestureAvailable():
    		motion = apds.readGesture()
    		print("Gesture={}".format(dirs.get(motion, "unknown")))
    		if (motion == APDS9960_DIR_UP):
    			if (state1 == False):
    				GPIO.output(8, GPIO.HIGH)
    				state1 = True
    			elif (state1 == True):
    				GPIO.output(8, GPIO.LOW)
    				state1 = False
    		elif (motion == APDS9960_DIR_DOWN):
    			if (state2 == False):
    				GPIO.output(10, GPIO.HIGH)
    				state2 = True
    			elif (state2 == True):
    				GPIO.output(10, GPIO.LOW)
    				state2 = False
    		elif (motion == APDS9960_DIR_LEFT):
    			if (state3 == False):
    				GPIO.output(12, GPIO.HIGH)
    				state3 = True
    			elif (state3 == True):
    				GPIO.output(12, GPIO.LOW)
    				state3 = False
    		elif (motion == APDS9960_DIR_RIGHT):
    			if (state4 == False):
    				GPIO.output(16, GPIO.HIGH)
    				state4 = True
    			elif (state4 == True):
    				GPIO.output(16, GPIO.LOW)
    				state4 = False

    GPIO.add_event_detect(7, GPIO.FALLING) adds an event that will trigger when a falling edge is detected; in other words, when a gesture is detected on the Gesture Sensor it will sent that to pin 7. We then set its proximity threshold and enable it. An infinite while loop is then created to simulate a loop that detects for a gesture continuously and once it does, it enters the if statement. Inside the if statement, motion = apds.readGesture() reads the detected gesture and stores it in a variable. Next, it will print what the motion was using the dictionary format made above and turn LEDs on or off depending on the motion.


    Conclusion

    LED controlling is often the first thing people try to become more familiar with the microcontroller they are using. For this specific case, a simple sensor was integrated along with the LED controlling which kicks it up a notch. Initially, migrating from C to Python will be confusing, despite the fact that Python is much easier to use according to many people. It just requires time and experience to get used to.


    References

     

    The post LED Control With APDS-9960 Gesture Sensor Using Raspberry Pi Zero W appeared first on CreateLabz.

    Apds-9960Gesture sensorI2cKnowledgebasePythonRaspberry piRaspberry pi zeroRpiRpi zero wSmbusVncWirelessZero

    Leave a comment

    All comments are moderated before being published