Mailbox alarm with moteino

Here is how I build my alarm, quite simple to do and to get push messages from prowl or mail.
For Gateway I use a moteino connected to a raspberryPi model B+ as you can see from the pictures below.

Feel free to ask questions or guidance if you want to build one by you own.

The work in pictures:

Mailbox alarm

The result

Prowl push msg

Mailbox moteino schematic

Arduino IDE Code:

    #include <RFM69.h>
    #include <SPI.h>
    #include <LowPower.h>
    #include <PinChangeInt.h>        // Two lines to include pinChangeInt library
    // NOTE!  The logic of mailbox OPEN vs CLOSED has been reversed for D4
    // D4 = HIGH is Mailbox OPENED (magnetic switch open)
    // D4 = LOW  is Mailbox CLOSED (magnetic switch closed)
    #define NODEID 2 // unique for each node on same network
    #define GATEWAYID 1
    #define NETWORKID 100 // the same on all nodes that talk to each other
    #define FREQUENCY RF69_868MHZ
    #define ENCRYPTKEY "sampleEncryptKey" // exactly the same 16 characters/bytes on all nodes!
    #define ACK_TIME 30 // max # of ms to wait for an ack
    #define LED 9 // Moteinos have LEDs on D9
    #define SERIAL_BAUD 115200
    #define D4 4
    #ifdef SERIAL_EN
      #define DEBUG(input)   {Serial.print(input); delay(1);}
      #define DEBUGln(input) {Serial.println(input); delay(1);}
      #define DEBUG(input);
      #define DEBUGln(input);
    RFM69 radio;
    bool promiscuousMode = false; // Set to 'true' to sniff all packets on the same network
    bool sentOpen = true;
    bool stateCheck=LOW;
    uint32_t switchTime=0;      // variable to monitor when the switch last changed state (for debouncing)
    #define  DEBOUNCE_TIME  50  // give it 50 mS to debounce a noisy switch
    // Add function to catch interrupt, doesn't need to do anything as the interrupt is all that's needed to wakeup
    void wakeUp(void)   
    void setup()
    //Setup the pins
      pinMode(LED, OUTPUT);
      pinMode(D4, INPUT_PULLUP);  // TOMWS: Use internal pullup as it's easier than adding an external one...
    //Start the Serial
    //Initialize the radio
      #ifdef IS_RFM69HW
      //radio.setHighPower(); // Uncomment only for RFM69HW!
      radio.encrypt(ENCRYPTKEY); // Turn encryption ON
      radio.promiscuous(promiscuousMode);  // TOMWS: This is not necessary if not using this mode
      char buff[50];
      sprintf(buff, "\nTransmiting at %d Mhz...", FREQUENCY==RF69_433MHZ ? 433 : FREQUENCY==RF69_868MHZ ? 868 : 915);
    void loop()
      if (digitalRead(D4) == HIGH)  // If the mailbox is opened
        switchTime = millis();   // record when we saw the switch change state
        stateCheck = LOW;
        if (sentOpen == false)  // have we already sent this?
          // no, send it now
          if (radio.sendWithRetry(GATEWAYID, "MAIL:OPN", 8))
            Serial.println(" nothing...");
            // Blink(LED,3);
          } else
            Serial.println("Sending Open mailboxstatus to gateway..");
          sentOpen = true;
          radio.sleep();  // we're done with the radio, make it sleep to save power immediately
      } else 
        switchTime = millis();   // record when we saw the switch change state
        stateCheck = HIGH;
        if (sentOpen == true)  // have we already sent this?
          // no, send it now
          if (radio.sendWithRetry(GATEWAYID, "MAIL:CLS", 8))
            Serial.println(" nothing...");
          } else
            Serial.println("Sending closed, once... ");
          sentOpen = false;
          radio.sleep();  // we're done with the radio, make it sleep to save power immediately
      while ((switchTime-millis()) < DEBOUNCE_TIME)  // debounce the switch
        if (digitalRead(D4) == stateCheck) switchTime = millis();  // if we sense a 'bounce' reset the timer
      Serial.flush();  // need to do before sleeping.
      // Allow wake up pin to trigger interrupt on either edge.
      PCintPort::attachInterrupt(D4, wakeUp, CHANGE);  // New code to trap interrupt on pin change
      LowPower.powerDown(SLEEP_FOREVER, ADC_OFF, BOD_OFF);  // Changed to SLEEP_FOREVER so that only interrupts wake up, no WDT used
      // WOKEN UP!  Disable further interrupts until debounced
      PCintPort::detachInterrupt(D4);  // disable interrupts until debounced
    void Blink(byte PIN, int DELAY_MS) // Local led blinking function
     // pinMode(PIN, OUTPUT);
     // digitalWrite(PIN,HIGH);
     // delay(DELAY_MS);
     // digitalWrite(PIN,LOW);

Shopping list:
Kjell o Co
39780 Batterycase 4xR6 (AA) (fits perfect in the Box, had to remove some plastic)
89024 Box Höjd: 20 mm
42480 AA Litium 4-pack

Leave a Reply