0

Feather accelerometer, RF transmitter, data logging project.
Moderators: adafruit_support_bill, adafruit

Please be positive and constructive with your questions and comments.

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Wed Jan 30, 2019 5:06 pm

Say I start with this example from the radiohead library.

Code: Select all | TOGGLE FULL SIZE
// rf69_server.pde
// -*- mode: C++ -*-


#include <SPI.h>
#include <RH_RF69.h>

// Singleton instance of the radio driver
RH_RF69 rf69;
//RH_RF69 rf69(15, 16); // For RF69 on PJRC breakout board with Teensy 3.1
//RH_RF69 rf69(4, 2); // For MoteinoMEGA https://lowpowerlab.com/shop/moteinomega

void setup()
{
  Serial.begin(9600);
  if (!rf69.init())
    Serial.println("init failed");
  // Defaults after init are 434.0MHz, modulation GFSK_Rb250Fd250, +13dbM
  // No encryption
  if (!rf69.setFrequency(433.0))
    Serial.println("setFrequency failed");

  // If you are using a high power RF69, you *must* set a Tx power in the
  // range 14 to 20 like this:
  // rf69.setTxPower(14);

 // The encryption key has to be the same as the one in the client
  uint8_t key[] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08,
                    0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08};
  rf69.setEncryptionKey(key);
 
#if 0
  // For compat with RFM69 Struct_send
  rf69.setModemConfig(RH_RF69::GFSK_Rb250Fd250);
  rf69.setPreambleLength(3);
  uint8_t syncwords[] = { 0x2d, 0x64 };
  rf69.setSyncWords(syncwords, sizeof(syncwords));
  rf69.setEncryptionKey((uint8_t*)"thisIsEncryptKey");
#endif
}

void loop()
{
  if (rf69.available())
  {
    // Should be a message for us now   
    uint8_t buf[RH_RF69_MAX_MESSAGE_LEN];
    uint8_t len = sizeof(buf);
    if (rf69.recv(buf, &len))
    {
//      RH_RF69::printBuffer("request: ", buf, len);
      Serial.print("got request: ");
      Serial.println((char*)buf);
//      Serial.print("RSSI: ");
//      Serial.println(rf69.lastRssi(), DEC);
     
      // Send a reply
      uint8_t data[] = "And hello back to you";
      rf69.send(data, sizeof(data));
      rf69.waitPacketSent();
      Serial.println("Sent a reply");
    }
    else
    {
      Serial.println("recv failed");
    }
  }
}


Should I be using an "if" statement to define my pins directly after the "singleton instance of the radio driver"?

I've found examples for the RFM69 that have something like:

Code: Select all | TOGGLE FULL SIZE
#if defined (ADAFRUIT_FEATHER_M0) // Feather M0 w/Radio
  #define RFM69_CS      8
  #define RFM69_INT     3
  #define RFM69_RST     4
  #define LED           13
#endif

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by adafruit_support_bill on Wed Jan 30, 2019 6:11 pm

The #define macros should go just before your RH_RF69 declaration. And you need to use those definitions in your RHRF69 declaration just as they do in the examples:

Code: Select all | TOGGLE FULL SIZE
// Singleton instance of the radio driver
RH_RF69 rf69(RFM69_CS, RFM69_INT);



These may also be referenced in other areas of the example code such as in this example: https://github.com/adafruit/RadioHead/b ... emo_TX.ino

Code: Select all | TOGGLE FULL SIZE
  pinMode(LED, OUTPUT);     
  pinMode(RFM69_RST, OUTPUT);
  digitalWrite(RFM69_RST, LOW);

  Serial.println("Feather Addressed RFM69 TX Test!");
  Serial.println();

  // manual reset
  digitalWrite(RFM69_RST, HIGH);
  delay(10);
  digitalWrite(RFM69_RST, LOW);
  delay(10);

adafruit_support_bill
 
Posts: 71756
Joined: Sat Feb 07, 2009 10:11 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Wed Jan 30, 2019 7:13 pm

Thank you for the clarification.

When defining, should I comment out the if/end if posted below?

I'm currently getting these errors

Code: Select all | TOGGLE FULL SIZE
rf69_server:16:14: error: 'RFM69_CS' was not declared in this scope
 RH_RF69 rf69(RFM69_CS, RFM69_INT);
              ^
rf69_server:16:24: error: 'RFM69_INT' was not declared in this scope
 RH_RF69 rf69(RFM69_CS, RFM69_INT);
                        ^
exit status 1
'RFM69_CS' was not declared in this scope


When attempting to compile this code

Code: Select all | TOGGLE FULL SIZE
// rf69_server.pde
// -*- mode: C++ -*-


#include <SPI.h>
#include <RH_RF69.h>

#if defined (ADAFRUIT_FEATHER_M0) // Feather M0 w/Radio
  #define RFM69_CS      8
  #define RFM69_INT     3
  #define RFM69_RST     4
  #define LED           13
#endif

// Singleton instance of the radio driver
RH_RF69 rf69(RFM69_CS, RFM69_INT);

void setup()
{
  Serial.begin(9600);
  if (!rf69.init())
    Serial.println("init failed");
  // Defaults after init are 434.0MHz, modulation GFSK_Rb250Fd250, +13dbM
  // No encryption
  if (!rf69.setFrequency(433.0))
    Serial.println("setFrequency failed");

  // If you are using a high power RF69, you *must* set a Tx power in the
  // range 14 to 20 like this:
  // rf69.setTxPower(14);

 // The encryption key has to be the same as the one in the client
  uint8_t key[] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08,
                    0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08};
  rf69.setEncryptionKey(key);
 
#if 0
  // For compat with RFM69 Struct_send
  rf69.setModemConfig(RH_RF69::GFSK_Rb250Fd250);
  rf69.setPreambleLength(3);
  uint8_t syncwords[] = { 0x2d, 0x64 };
  rf69.setSyncWords(syncwords, sizeof(syncwords));
  rf69.setEncryptionKey((uint8_t*)"thisIsEncryptKey");
#endif
}

void loop()
{
  if (rf69.available())
  {
    // Should be a message for us now   
    uint8_t buf[RH_RF69_MAX_MESSAGE_LEN];
    uint8_t len = sizeof(buf);
    if (rf69.recv(buf, &len))
    {
//      RH_RF69::printBuffer("request: ", buf, len);
      Serial.print("got request: ");
      Serial.println((char*)buf);
//      Serial.print("RSSI: ");
//      Serial.println(rf69.lastRssi(), DEC);
     
      // Send a reply
      uint8_t data[] = "And hello back to you";
      rf69.send(data, sizeof(data));
      rf69.waitPacketSent();
      Serial.println("Sent a reply");
    }
    else
    {
      Serial.println("recv failed");
    }
  }
}

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Wed Jan 30, 2019 7:58 pm

I simply commented out the if statement and now it works!

It makes sense, but I'm new to coding and I'm not aware of such silly mistakes.

Thanks again for the advice!

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Thu Jan 31, 2019 4:27 pm

Hello,

I've been successful with uploading a basic Rx/Tx code to my set of feather M0's. I'm now trying to have a buzzer make noise when the server receives a packet from the client.

I initially started adding lines to the code, that would power the LED for 0.5s after a packet was received as indication. I was successful in lighting up the LED, but now I would like to have a pin turn on a buzzer for 0.5 s.. Here's my code thus far, does it look legit?

Code: Select all | TOGGLE FULL SIZE
// Send a reply
      uint8_t data[] = "TEAM UNICONE";
      rf69.send(data, sizeof(data));
      rf69.waitPacketSent();
      Serial.println("Sent a reply");
      digitalWrite(10, HIGH);   // turn the buzzer on (HIGH is the voltage level)
      delay(500);              // wait for a second
      digitalWrite(10, LOW);    // turn the buzzer off by making the voltage LOW
      delay(500);              // wait for a second


Thanks!

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by adafruit_support_bill on Thu Jan 31, 2019 4:43 pm

That may work. It depends on what type of buzzer you have. Some have an internal oscillator to make the buzz. Others require you to pulse the power yourself.

adafruit_support_bill
 
Posts: 71756
Joined: Sat Feb 07, 2009 10:11 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Thu Jan 31, 2019 5:03 pm

For testing, I am using a small enclosed piezo buzzer.

Do you know if I need to pulse the power for that?

I'm honestly not sure what "pulsing power" means.. Do I just send voltage/current to a pin?

What function does that?

Thanks

Noah

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by adafruit_support_bill on Thu Jan 31, 2019 5:08 pm

If you mean this one: https://www.adafruit.com/product/1740
then you need to send it pulses. The simplest way to do that is using the 'tone' library: https://www.arduino.cc/reference/en/lan ... d-io/tone/

adafruit_support_bill
 
Posts: 71756
Joined: Sat Feb 07, 2009 10:11 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Thu Jan 31, 2019 5:21 pm

Thank you, what works best for the small vibrating disc? or vibrating motors in general?

I plan on using the haptic motor controller in the future, but want to play around without it for now.

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by adafruit_support_bill on Thu Jan 31, 2019 5:50 pm

You can drive them directly from an Arduino pin at reduced power) if you wire a 100 ohm resistor in series. It is also possible to drive them with a simple transistor like a PN2222.

For best results, use a haptic controller like the DRV2605
https://www.adafruit.com/product/2305

adafruit_support_bill
 
Posts: 71756
Joined: Sat Feb 07, 2009 10:11 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Mon Feb 11, 2019 3:46 pm

I'm currently attempting to write data from the accelerometer to the FRAM.

I have started with the most basic example from the example library, and am unable to get the FRAM and Feather M0 to communicate.

I've attached the example, with the correct pins entered for the Feather M0.

Code: Select all | TOGGLE FULL SIZE
#include <SPI.h>
#include "Adafruit_FRAM_SPI.h"

/* Example code to interrogate Adafruit SPI FRAM breakout for address size and storage capacity */

/* NOTE: This sketch will overwrite data already on the FRAM breakout */

uint8_t FRAM_CS = 10;
Adafruit_FRAM_SPI fram = Adafruit_FRAM_SPI();  // use hardware SPI

uint8_t FRAM_SCK = 24;
uint8_t FRAM_MISO = 22;
uint8_t FRAM_MOSI = 23;
//Or use software SPI, any pins!
//Adafruit_FRAM_SPI fram = Adafruit_FRAM_SPI(FRAM_SCK, FRAM_MISO, FRAM_MOSI, FRAM_CS);

uint8_t           addrSizeInBytes = 2; //Default to address size of two bytes
uint32_t          memSize;




int32_t readBack(uint32_t addr, int32_t data) {
  int32_t check = !data;
  int32_t wrapCheck, backup;
  fram.read(addr, (uint8_t*)&backup, sizeof(int32_t));
  fram.writeEnable(true);
  fram.write(addr, (uint8_t*)&data, sizeof(int32_t));
  fram.writeEnable(false);
  fram.read(addr, (uint8_t*)&check, sizeof(int32_t));
  fram.read(0, (uint8_t*)&wrapCheck, sizeof(int32_t));
  fram.writeEnable(true);
  fram.write(addr, (uint8_t*)&backup, sizeof(int32_t));
  fram.writeEnable(false);
  // Check for warparound, address 0 will work anyway
  if (wrapCheck==check)
    check = 0;
  return check;
}

bool testAddrSize(uint8_t addrSize) {
  fram.setAddressSize(addrSize);
  if (readBack(4, 0xbeefbead) == 0xbeefbead)
    return true;
  return false;
}


void setup(void) {
  #ifndef ESP8266
    while (!Serial);     // will pause Zero, Leonardo, etc until serial console opens
  #endif

  Serial.begin(9600);
 
  if (fram.begin(FRAM_CS, addrSizeInBytes)) {
    Serial.println("Found SPI FRAM");
  } else {
    Serial.println("Keep trying");
    while (1);
  }

  if (testAddrSize(2))
    addrSizeInBytes = 2;
  else if (testAddrSize(3))
    addrSizeInBytes = 3;
  else if (testAddrSize(4))
    addrSizeInBytes = 4;
  else {
    Serial.println("SPI FRAM can not be read/written with any address size\r\n");
    while (1);
  }
 
  memSize = 0;
  while (readBack(memSize, memSize) == memSize) {
    memSize += 256;
    //Serial.print("Block: #"); Serial.println(memSize/256);
  }
 
  Serial.print("SPI FRAM address size is ");
  Serial.print(addrSizeInBytes);
  Serial.println(" bytes.");
  Serial.println("SPI FRAM capacity appears to be..");
  Serial.print(memSize); Serial.println(" bytes");
  Serial.print(memSize/0x400); Serial.println(" kilobytes");
  Serial.print((memSize*8)/0x400); Serial.println(" kilobits");
  if (memSize >= (0x100000/8)) {
    Serial.print((memSize*8)/0x100000); Serial.println(" megabits");
  }
}

void loop(void) {

}


Any help/input would be greatly appreciated!

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by adafruit_support_bill on Mon Feb 11, 2019 4:02 pm

You have defined the pins you are using. But you are still calling the constructor to use the default "hardware spi"
Code: Select all | TOGGLE FULL SIZE
Adafruit_FRAM_SPI fram = Adafruit_FRAM_SPI();  // use hardware SPI


You need to use the software SPI form of the constructor - passing in the pins that you defined:
Code: Select all | TOGGLE FULL SIZE
//Or use software SPI, any pins!
Adafruit_FRAM_SPI fram = Adafruit_FRAM_SPI(FRAM_SCK, FRAM_MISO, FRAM_MOSI, FRAM_CS);

adafruit_support_bill
 
Posts: 71756
Joined: Sat Feb 07, 2009 10:11 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Fri Feb 15, 2019 11:53 pm

I've ran into an issue when attempting to wake the Feather M0, using the interrupt pin on LIS3DH accelerometer. I've been successful thus far communicating between two RFM69 devices, upon impact of the accelerometer attached to the client.

Our code contains several other processes, but I wanted to post the entire code incase you happen to see something simple that could be causing the error.

I greatly appreciate any input!

Code: Select all | TOGGLE FULL SIZE
#include <RTCZero.h>
/* Create an rtc object */

#include <avr/interrupt.h>      // library for interrupts handling

RTCZero rtc;
#define VBATPIN A7

/* Change these values to set the current initial time */
const byte hours = 00;
const byte minutes = 00;
byte seconds = 00;

const byte pinToInt = 12;

/* Change these values to set the current initial date */

const byte year = 19;
const byte month = 01;
const byte day = 01;

//Initialize battery voltage variables
float measuredvbat = 00;
const byte vbatthreshold = 4;

//==================From Impact Sensor Device
// This is the full acceleromter code that includes interupt and output
// This code also communicates with the reciever

// For the Accelerometer
#include <Wire.h>
#include <Adafruit_LIS3DH.h>
#include <Adafruit_Sensor.h>

// For Transmission
#include <SPI.h>
#include <RH_RF69.h>

#define RFM69_CS      8
#define RFM69_INT     3
#define RFM69_RST     4
#define LED           13
#define RFM69_FREQ    888.0

// I2C configuration
Adafruit_LIS3DH lis = Adafruit_LIS3DH();

// Singleton instance of the radio driver
RH_RF69 rf69(RFM69_CS, RFM69_INT);


// Adjust this number for the sensitivity of the 'click' force
// this strongly depend on the range! for 16G, try 5-10
// for 8G, try 10-20. for 4G try 20-40. for 2G try 40-80
#define CLICKTHRESHHOLD 40

void setup()
{
  pinMode(LED_BUILTIN, OUTPUT);
  pinMode(pinToInt, INPUT);

  //Setup for RTC
  rtc.begin();
  rtc.setTime(hours, minutes, seconds);
  rtc.setDate(day, month, year);
  rtc.attachInterrupt(alarmMatch);

  //Attach interrupt for accelerometer
  attachInterrupt(digitalPinToInterrupt(pinToInt), accIntPin, RISING);

  //==============Setup for Impact Sensor Device
  // Radio

  Serial.begin(9600);
  if (!rf69.init())
    Serial.println("init failed");

  if (!rf69.setFrequency(RFM69_FREQ))
    Serial.println("setFrequency failed");
  rf69.setTxPower(20);

  // The encryption key has to be the same as the one in the server
  uint8_t key[] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08,
                    0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08
                  };
  rf69.setEncryptionKey(key);

  //Transmitter

#ifndef ESP8266
  while (!Serial);     // will pause Zero, Leonardo, etc until serial console opens
#endif

  Serial.begin(9600);
  Serial.println("Go team Unicone!");

  //Error message if failue to communicate
  if (! lis.begin(0x18)) {   // change this to 0x19 for alternative i2c address
    Serial.println("You have made a mistake");
    while (1);
  }
  Serial.println("Communication successful. Celebrate!");


  lis.setRange(LIS3DH_RANGE_4_G);   // 2, 4, 8 or 16 G!

  Serial.print("Range = "); Serial.print(2 << lis.getRange());
  Serial.println("G");


  // To adjust threshhold, edit line CLICKTHRESHOLD in setup loop. Higher is less sensitive
  // 1 sets to single event, 2 sets to double hit, 0 turns off
  lis.setClick(1, CLICKTHRESHHOLD);
  delay(100);
}

//===================================================LOOP=========================================
void loop()
{
  delay(3000);
  measuredvbat = analogRead(VBATPIN); //read the voltage from the vbat pin
  measuredvbat *= 2;    // we divided by 2, so multiply back
  measuredvbat *= 3.3;  // Multiply by 3.3V, our reference voltage
  measuredvbat /= 1024; // convert to voltage

  if (measuredvbat <= vbatthreshold)  //turns on LED if measured battery voltage is lower than this threshold
  {
    digitalWrite(LED_BUILTIN, HIGH);
  }

  rtc.setTime(hours, minutes, seconds);  //reset time before standby mode
  rtc.setAlarmTime(rtc.getHours(), rtc.getMinutes(), rtc.getSeconds() + 30); //set alarm time from now +chosen delay
  rtc.enableAlarm(rtc.MATCH_HHMMSS);  //turns alarm on
  rtc.standbyMode();    // Sleep until next alarm match
  rtc.disableAlarm();   //disables the alarm after the time is matched and the standby is interrupted

  //=======================For Impact Sensing Device
  detachInterrupt(digitalPinToInterrupt(12));

  uint8_t click = lis.getClick();
  if (click == 0) return;
  if (! (click & 0x30)) return;

  lis.read();      // get X Y and Z data at once

  /* This normalizes the acceleromter reading */
  sensors_event_t event;
  lis.getEvent(&event);

  /* This displays the results (acceleration is measured in m/s^2) */
  Serial.print("\t\tX: "); Serial.print(event.acceleration.x);
  Serial.print(" \tY: "); Serial.print(event.acceleration.y);
  Serial.print(" \tZ: "); Serial.print(event.acceleration.z);
  Serial.println(" m/s^2 ");
  Serial.println();

  //Start transmission
  Serial.println("Sending to rf69_server");
  // Send a message to rf69_server
  uint8_t data[] = "Hello Team Unicone";
  rf69.send(data, sizeof(data));

  rf69.waitPacketSent();
  // Now wait for a reply
  uint8_t buf[RH_RF69_MAX_MESSAGE_LEN];
  uint8_t len = sizeof(buf);

  if (rf69.waitAvailableTimeout(500))
  {
    // Should be a reply message for us now
    if (rf69.recv(buf, &len))
    {
      Serial.print("got reply: ");
      Serial.println((char*)buf);
    }
    else
    {
      Serial.println("recv failed");
    }
  }
  else
  {
    Serial.println("No reply, is rf69_server running?");
  }
  delay(200);
}

//=========================================FUNCTIONS==============================================



void accIntPin()
{

}

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Re: Feather accelerometer, RF transmitter, data logging proj

by adafruit_support_bill on Sat Feb 16, 2019 7:18 am

I've ran into an issue when attempting to wake the Feather M0, using the interrupt pin on LIS3DH accelerometer.

What exactly is the issue you are seeing?

adafruit_support_bill
 
Posts: 71756
Joined: Sat Feb 07, 2009 10:11 am

Re: Feather accelerometer, RF transmitter, data logging proj

by wahleworld on Sun Feb 17, 2019 5:27 pm

The accelerometer is either not generating an interrupt or the Feather M0 is failing to recognize the interrupt and therefore is not waking up.

wahleworld
 
Posts: 45
Joined: Sun Nov 11, 2018 12:50 am

Please be positive and constructive with your questions and comments.