Photon WKP Pin - Button Library

I’m building a product where the Photon will be inside the product enclosure.

I will have a 4DSystems LCD Touchscreen for interfacing with the Photon but I need to run a single push button to the outside of the product that can be pushed to bring the Photon and LCD out of a low power sleep state via the WKP pin.

@peekay123 I’m wondering if I can use the button library you have to make this single button trigger different actions after the Photon has been woken from deep sleep.

Will that library work with the WKP pin?

At a minimum, I would like to trigger a REST via the software reset command if the button is held down for 10-15 seconds. That beats only being able to use the button for waking from deep sleep.

I’m running the RGB led pins to the RGB LED ring on the button to keep the Photon status indicators working as usual which I like.

Only thing I do not think is possible is getting into Safe mode via a software function. Not sure if an end product would need that mode if the code is tested pretty well before updating devices in the field.

1 Like

I use this simple thing for arduino, which you can easily adapt for Particle.

example:

#include "SimplePress.h"

const byte buttonPin0 = 2;
const byte buttonPin1 = 3;
const byte buttonPin2 = 4;

SimplePress button0(buttonPin0, 500);         // half second capture for multi-presses; uses default 200ms debounce
                                              // a long press is defined as greater than the capture time (500ms in this example)
                                              // or...
SimplePress button1(buttonPin1, 500, 50);    // or specify custom debounce time in ms

SimplePress button2(buttonPin2, 500);

void setup() 
{
  Serial.begin(9600);
  pinMode(13, OUTPUT);
  button0.begin();
  button1.begin();
  button2.begin();
}

void loop() 
{
  if(int pressCount = button0.pressed())  // check to see if there is a button press event
  {
    switch(pressCount)  // the event can be any positive integer (the number of button presses) or -1 in the case of a long press
    {
      case -1:
        Serial.println(F("Button 0 long Press"));
        longFlashPin13();
        break;
      case 1:
        Serial.println(F("Button 0 one Press"));
        flashPin13(1);
        break;
      case 2:
        Serial.println(F("Button 0 two Presses"));
        flashPin13(2);
        break;
    }
  }
  if(int press2count = button1.pressed())
  {
    switch(press2count)
    {
      case -1:
        Serial.println(F("Button 1 long Press"));
        break;
      case 1:
        Serial.println(F("Button 1 one Press"));
        break;
    }
  }
  if (button2.pressed()) // Simple press detection
  {
    Serial.println(F("Button 2 Pressed!")); 
  }
}

void flashPin13(byte numTimes)
{
  for(byte i = 0; i < numTimes; i++)
  {
    digitalWrite(13, HIGH);
    delay(250);
    digitalWrite(13, LOW);
    if (i < numTimes - 1) delay(250);
  }
}

void longFlashPin13(void)
{
  digitalWrite(13, HIGH);
  delay(1000);
  digitalWrite(13, LOW);
}

the header I use:

#ifndef SIMPLEPRESS_H
#define SIMPLEPRESS_H

#include <Arduino.h>

class SimplePress{
  public:
    SimplePress(int _pin, uint32_t _pressInterval, uint32_t _debouncePeriod = 200);
    bool begin();
    int8_t pressed();

  private:
    byte pressCount;
    byte lastState;
    byte pin;
    uint32_t lastMillis;
    uint32_t debouncePeriod;
    uint32_t pressInterval;
};

SimplePress::SimplePress(int _pin, uint32_t _pressInterval, uint32_t _debouncePeriod)
{
  pin = _pin;
  debouncePeriod = _debouncePeriod;
  pressInterval = _pressInterval;
}

bool SimplePress::begin()
{
  pinMode(pin, INPUT_PULLUP);
  lastState = HIGH;
  return true;
}

int8_t SimplePress::pressed()
{
  byte nowState = digitalRead(pin);
  if(nowState != lastState)
  {
    if(millis() - lastMillis < debouncePeriod) return 0;
    if(nowState == LOW)
    {
      lastMillis = millis();
      pressCount++;
    }
    else 
    {
      if (millis() - lastMillis > pressInterval) // a long press
      {
        lastState = nowState;
        pressCount = 0;
        return -1;
      }
    }
  }
  if(pressCount != 0)
  {
    if(millis() - lastMillis > pressInterval and nowState == HIGH)
    {
      int presses = pressCount;
      pressCount = 0;
      return presses;
    }
  }
  lastState = nowState;
  return 0;
}

#endif

PS: I like that button switch!

Thanks for the tip. That will do the job.

I’m wondering if the library @Peekay123 uses is any better or worse than this Arduino version.

The button is pretty nice and it’s only $10, which is about 3 times less than anything comparable I have found.