Java ME 8 + Raspberry Pi + Sensors = IoT World (Part 1)

Learn how to connect sensors to the Raspberry Pi and control them with Java.

Published September 2014

The latest release of Java ME 8 includes a powerful API for controlling devices such as LEDs, relays, LCDs, sensors, motors, and switches.

Java ME 8 + Raspberry Pi + Sensors

This article is the first in a three-part series about how to connect electronic sensors to the Raspberry Pi Model B using general-purpose input/output (GPIO), inter-integrated circuit bus (I2C), serial peripheral interface bus (SPI), or universal asynchronous receiver/transmitter (UART) interfaces.

By using Java ME 8 to control devices with different types of interfaces and connecting the devices to a Raspberry Pi, we can create an Internet of Things (IoT) world.

This article focuses on using GPIO and shows examples of how to develop classes in Java ME 8 that can

Note: The complete example code for this NetBeans IDE 8.0 project can be downloaded here.

Device I/O API

The Device I/O API specification defines a generic peripheral device I/O API for Java applications running on small embedded devices. It defines APIs for some of the most common peripheral devices, including the following:

  • GPIO devices
  • I2C devices
  • SPI devices
  • Analog-to-digital converters (ADCs)
  • Digital-to-analog converters (DACs)
  • UART devices
  • Memory-mapped I/O (MMIO) devices
  • AT command devices
  • Watchdog timers
  • Pulse counters
  • Pulse-width modulation (PWM) generators
  • Generic devices

Circuits We Will Create

A GPIO device can be used as either a digital input or a digital output, it can be disabled or enabled, and it can be used to drive “interrupt” lines. However, a very important consideration is that all Raspberry Pi GPIO pins operate at 3.3 V. Therefore, it is very important to check the technical specifications of the devices you want connect to determine if they are using 3.3 V or 5 V. In some cases, you will need to use a logic level converter such as this.

Connecting the Flame Detector

The DFR0076 flame sensor from DFRobot can be used to detect fire or other wavelengths of light between approximately 760 nm and 1100 nm. We can connect it to 3.3 V or 5 V, and the detection range is approximately 20 cm (4.8 V) to 100 cm (1 V). When fire is detected, it pulls up the signal pin.

Let's connect the flame sensor to the Raspberry Pi's 3.3 V, Gnd, and GPIO 22 pins, as shown in Figure 3, and create a Java ME 8 class for the flame detector sensor control.

First, create a class DFR0076Device that uses the Device Access API, and define a variable pin that supports the interface to GPIO, as shown in Listing 1.

public class DFR0076Device {

    private GPIOPin pin = null;  //Define the pin for flame sensor control

Listing 1. Class for the flame detector sensor control

Next, create a class constructor that initializes and activates the GPIO 22 pin using the DeviceManager API and the GPIOPinConfigclass (see Listing 2) to establish the following conditions:

  • Device name: 0
  • Pin number: GPIO 22 (specified through pinGPIO)
  • Direction: input only
  • Mode: pull-up
  • Trigger: rising-edge
  • Initial value: false
public DFR0076Device(int pinGPIO) { 
...
   pin = (GPIOPin) DeviceManager.open(new GPIOPinConfig(
           0, pinGPIO,GPIOPinConfig.DIR_INPUT_ONLY,GPIOPinConfig.MODE_INPUT_PULL_UP,
           GPIOPinConfig.TRIGGER_RISING_EDGE, false));
...
}

Listing 2. Establishing the initial conditions

Now, create a method that receives a defined listener class that supports flame detection events, as shown in Listing 3.

public void setListener(PinListener flameListener) {
...
     if (pin!=null)
          pin.setInputListener(flameListener);
...
}

Listing 3. Method that supports flame detection events

It's also important that you close the pin when you are done, and also make sure you free the pin listener, as shown in Listing 4.

public void close() {
...
       if (pin!=null){
            pin.setInputListener(null);
            pin.close();
       }
...
}

Listing 4. Closing the pin and freeing the listener

Now, create a main MIDlet that invokes our code and defines a listener class for processing flame detection events, as shown in Listing 5.

public class TestSensors extends MIDlet {
    DFR0076Device flame;
    private static final int FLAME_DETECTOR_PIN = 22;
       public void startApp() {
           //Initialize Flame Sensor
           flame = new DFR0076Device(FLAME_DETECTOR_PIN);
           flame.setListener(new FlameSensor());
       }
       public void destroyApp(boolean unconditional) {
             flame.close();
       }

    private static int waitnext = 1;
    class FlameSensor implements PinListener {
            public void valueChanged(PinEvent event) {
                if (event.getValue() && --waitnext == 0) {
                    System.out.println("WARNING Flame detected!!!");
                    waitnext = 10;
                }
             }
        }
}

Listing 5. Creating a MIDlet to invoke our code

Connecting the Motion Detector

Now let's add motion detector functionality to our TestSensors MIDlet. To do that, we need a motion sensor such as the HC-SR501 shown in Figure 2.

PIR sensors enable you to sense motion. Everything emits a small amount of infrared radiation, and the hotter something is, the more radiation it emits. PIR sensors are able to detect a change in IR levels that occur within their detection zone (for example, when a human enters a room) and, hence, sense motion.

The PIR sensor we'll be using has three pins: ground, digital out, and 3–5 Vdc in. At idle, when no motion has been detected, the digital out signal will remain low. However, when motion is detected, the digital out signal will pulse high (3.3 V). It is OK to connect the digital out pin directly to the Raspberry Pi.

For testing, the PIR sensor has a jumper (see Figure 4).

  • Setting the jumper to the “L” position creates a single (nonrepeatable) trigger. When the jumper is in this position, sensing is enabled after a sense event occurs, which allows for continuous motion detection. The output is still latched low for 3 seconds after motion is no longer detected.
  • Setting the jumper to the “H” position creates a repeatable trigger. When the jumper is set to the “H” (default) position, sensing is disabled after a sense event occurs (that is, once output is high).

You can make the following adjustments:

  • Adjusting the sensitivity potentiometer clockwise increases the sensing distance to about 7 meters; adjusting it counterclockwise decreases the sensing distance to about 3 meters.
  • Adjusting the time delay potentiometer clockwise lengthens the induction delay to 300 seconds; adjusting it counterclockwise shortens the induction delay to 5 seconds.

Let's connect the PIR sensor to the Raspberry Pi 5 V, Gnd, and GPIO 24 pins, as shown in Figure 3, and create a Java ME 8 classHCSR501Device to control it using the Device Access API, as shown in Listing 6.

public class HCSR501Device {
    private GPIOPin pin = null;

Listing 6. HCSR501Device class

Then, create a class constructor that initializes and activates the GPIO 24 pin using the DeviceManager API and the GPIOPinConfigclass (see Listing 7) to establish the following conditions:

  • Device name: 0
  • Pin number: GPIO 24 (specified through pinGPIO)
  • Direction: input only
  • Mode: pull-down
  • Trigger: rising-edge
  • Initial value: false
  • Wait three seconds before initializing the PIR
public HCSR501Device(int pinGPIO) {
 ...
   pin = (GPIOPin) DeviceManager.open(new GPIOPinConfig(
           0, pinGPIO, GPIOPinConfig.DIR_INPUT_ONLY, GPIOPinConfig.MODE_INPUT_PULL_DOWN,
           GPIOPinConfig.TRIGGER_RISING_EDGE, false));
       I2CUtils.I2Cdelay(3000);    //wait for 3 seconds
  ...
}

Listing 7. Establishing the initial conditions

Now, create a method that receives a defined listener class that supports motion detection events, as shown in Listing 8.

public void setListener(PinListener pirListener) {
...
       if (pin!=null)
          pin.setInputListener(pirListener);
...
}

Listing 8. Method that supports motion detection events

It's also important that you close the pin when you are done, and also make sure you free the pin listener as shown in Listing 9.

public void close() {
...
     if (pin!=null){
          pin.setInputListener(null);
          pin.close();
     }
...
}

Listing 9. Closing the pin and freeing the listener

Java ME 8 + Raspberry Pi + Sensors diagram

Let's extend our MIDlet class to support the PIR sensor and its listener, as shown in Listing 10.

//Define HCSR501 Device object
HCSR501Device pir;
private static final int MOTION_DETECTOR_PIN = 24;

@Override
public void startApp() {
...    
    //Initialize PIR sensor
    pir = new HCSR501Device(MOTION_DETECTOR_PIN);
    pir.setListener(new PirSensor());
...    
}

@Override
public void destroyApp(boolean unconditional) {
...
    pir.close();
...
}

//Check PIR Sensor for motion detection
class PirSensor implements PinListener {

    @Override
    public void valueChanged(PinEvent event) {
        if (event.getValue()) {
            System.out.println("WARNING Motion detected!!!");
        }

    }
}

Listing 10. Extending the MIDlet class to support the PIR sensor and its listener

 

For more detail: Java ME 8 + Raspberry Pi + Sensors = IoT World (Part 1)


About The Author

Ibrar Ayyub

I am an experienced technical writer holding a Master's degree in computer science from BZU Multan, Pakistan University. With a background spanning various industries, particularly in home automation and engineering, I have honed my skills in crafting clear and concise content. Proficient in leveraging infographics and diagrams, I strive to simplify complex concepts for readers. My strength lies in thorough research and presenting information in a structured and logical format.

Follow Us:
LinkedinTwitter

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top