publish libraries to avoid users to have to download them one by one

This commit is contained in:
1technophile committed 2018-03-04 13:47:37 +01:00
1 parent 93c075e880
commit f0546fab8c
396 files changed
+536928

No files matched your search

+57
View File
@@ -0,0 +1,57 @@
SparkFun License Information
============================
SparkFun uses two different licenses for our files - one for hardware and one for code.
Hardware
---------
**SparkFun hardware is released under [Creative Commons Share-alike 4.0 International](http://creativecommons.org/licenses/by-sa/4.0/).**
Note: This is a human-readable summary of (and not a substitute for) the [license](http://creativecommons.org/licenses/by-sa/4.0/legalcode).
You are free to:
Share — copy and redistribute the material in any medium or format
Adapt — remix, transform, and build upon the material
for any purpose, even commercially.
The licensor cannot revoke these freedoms as long as you follow the license terms.
Under the following terms:
Attribution — You must give appropriate credit, provide a link to the license, and indicate if changes were made. You may do so in any reasonable manner, but not in any way that suggests the licensor endorses you or your use.
ShareAlike — If you remix, transform, or build upon the material, you must distribute your contributions under the same license as the original.
No additional restrictions — You may not apply legal terms or technological measures that legally restrict others from doing anything the license permits.
Notices:
You do not have to comply with the license for elements of the material in the public domain or where your use is permitted by an applicable exception or limitation.
No warranties are given. The license may not give you all of the permissions necessary for your intended use. For example, other rights such as publicity, privacy, or moral rights may limit how you use the material.
Code
--------
**SparkFun code, firmware, and software is released under the [MIT License](http://opensource.org/licenses/MIT).**
The MIT License (MIT)
Copyright (c) 2015 SparkFun Electronics
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
+61
View File
@@ -0,0 +1,61 @@
SparkFun <PRODUCT NAME> Arduino Library
========================================
![SparkFun BME280 Breakout](https://github.com/sparkfun/SparkFun_BME280_Arduino_Library/blob/master/readme_picture.jpg)
[*SparkFun BME280 (SEN-13676)*](https://www.sparkfun.com/products/13676)
This library allows the user to:
* Read pressure in Pa
* Read temperature in C
* Read humidity in %RH
It also provides the following mathematical functions based from the above.
* Read temperature in F
* Read altitude in meters
* Read altitude in feet
Some examples include a circular buffer class for averaging.
Repository Contents
-------------------
* **/examples** - Example sketches for the library (.ino). Run these from the Arduino IDE.
* **/extras** - Additional documentation for the user. These files are ignored by the IDE.
* **/src** - Source files for the library (.cpp, .h).
* **keywords.txt** - Keywords from this library that will be highlighted in the Arduino IDE.
* **library.properties** - General library properties for the Arduino package manager.
Documentation
--------------
* **[Installing an Arduino Library Guide](https://learn.sparkfun.com/tutorials/installing-an-arduino-library)** - Basic information on how to install an Arduino library.
* **[Product Repository](https://github.com/sparkfun/BME280-Breakout-Board)** - Main repository (including hardware files) for the SparkFun BME280 Breakout.
* **[Hookup Guide](https://learn.sparkfun.com/tutorials/bme280-breakout-hookup-guide)** - Basic hookup guide for the SparkFun BME280 Breakout.
Products that use this Library
---------------------------------
* [*SEN-13676*](https://www.sparkfun.com/products/13676)
Version History
---------------
* [V_1.0.0](https://github.com/sparkfun/SparkFun_BME280_Arduino_Library/tree/V_1.0.0) - Public release.
* [V_1.1.0](https://github.com/sparkfun/SparkFun_BME280_Arduino_Library/tree/V_1.1.0) - Pulled request to add decimal precision to readFloatPressure() and readFloatHumidity().
* [V_1.2.0](https://github.com/sparkfun/SparkFun_BME280_Arduino_Library/tree/V_1.2.0) - Added ESP32 architecture directives to modify begin operation.
License Information
-------------------
This product is _**open source**_!
Please review the LICENSE.md file for license information.
If you have any questions or concerns on licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
- Your friends at SparkFun.
@@ -0,0 +1,116 @@
/******************************************************************************
CSV_Output.ino
BME280 Arduino and Teensy example
Marshall Taylor @ SparkFun Electronics
May 20, 2015
https://github.com/sparkfun/SparkFun_BME280_Arduino_Library
This sketch configures two BME280 to produce comma separated values for use
in generating spreadsheet graphs.
in 10 being used for chip select.
Resources:
Uses Wire.h for I2C operation
Uses SPI.h for SPI operation
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
#include <stdint.h>
#include "SparkFunBME280.h"
#include "Wire.h"
#include "SPI.h"
//Global sensor object
BME280 mySensor;
unsigned int sampleNumber = 0; //For counting number of CSV rows
void setup()
{
//***Driver settings********************************//
//commInterface can be I2C_MODE or SPI_MODE
//specify chipSelectPin using arduino pin names
//specify I2C address. Can be 0x77(default) or 0x76
//For I2C, enable the following and disable the SPI section
mySensor.settings.commInterface = I2C_MODE;
mySensor.settings.I2CAddress = 0x77;
//For SPI enable the following and dissable the I2C section
//mySensor.settings.commInterface = SPI_MODE;
//mySensor.settings.chipSelectPin = 10;
//***Operation settings*****************************//
mySensor.settings.runMode = 3; // 3, Normal mode
mySensor.settings.tStandby = 0; // 0, 0.5ms
mySensor.settings.filter = 0; // 0, filter off
//tempOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.tempOverSample = 1;
//pressOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.pressOverSample = 1;
//humidOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.humidOverSample = 1;
Serial.begin(57600);
Serial.print("Program Started\n");
Serial.print("Starting BME280... result of .begin(): 0x");
delay(10); //Make sure sensor had enough time to turn on. BME280 requires 2ms to start up.
//Calling .begin() causes the settings to be loaded
Serial.println(mySensor.begin(), HEX);
//Build a first-row of column headers
Serial.print("\n\n");
Serial.print("Sample,");
Serial.print("T(deg C),");
Serial.print("T(deg F),");
Serial.print("P(Pa),");
Serial.print("Alt(m),");
Serial.print("Alt(ft),");
Serial.print("%RH");
Serial.println("");
}
void loop()
{
//Print each row in the loop
//Start with temperature, as that data is needed for accurate compensation.
//Reading the temperature updates the compensators of the other functions
//in the background.
Serial.print(sampleNumber);
Serial.print(",");
Serial.print(mySensor.readTempC(), 2);
Serial.print(",");
Serial.print(mySensor.readTempF(), 3);
Serial.print(",");
Serial.print(mySensor.readFloatPressure(), 0);
Serial.print(",");
Serial.print(mySensor.readFloatAltitudeMeters(), 3);
Serial.print(",");
Serial.print(mySensor.readFloatAltitudeFeet(), 3);
Serial.print(",");
Serial.print(mySensor.readFloatHumidity(), 0);
Serial.println();
sampleNumber++;
delay(50);
}
@@ -0,0 +1,104 @@
#include "CircularBuffer.h"
#include <stdint.h>
//****************************************************************************//
//
// Circular buffer
//
//****************************************************************************//
//Construct a CircularBuffer type with arguments
// uint16_t inputSize: number of elements
CircularBuffer::CircularBuffer(uint16_t inputSize)
{
cBufferData = new float[inputSize];
cBufferLastPtr = 0;
cBufferElementsUsed = 0;
cBufferSize = inputSize;
}
CircularBuffer::~CircularBuffer()
{
delete[] cBufferData;
}
//Get an element at some depth into the circular buffer
//zero is the push location. Max is cBufferSize - 1
//
//Arguments:
// uint16_t elementNum: number of element in
//
float CircularBuffer::getElement( uint16_t elementNum )
{
//Translate elementNum into terms of cBufferLastPtr.
int16_t virtualElementNum;
virtualElementNum = cBufferLastPtr - elementNum;
if( virtualElementNum < 0 )
{
virtualElementNum += cBufferSize;
}
//Output the value
return cBufferData[virtualElementNum];
}
//Put a new element into the buffer.
//This also expands the size up to the max size
//Arguments:
//
// int16_t elementVal: value of new element
//
void CircularBuffer::pushElement( float elementVal )
{
//inc. the pointer
cBufferLastPtr++;
//deal with roll
if( cBufferLastPtr >= cBufferSize )
{
cBufferLastPtr = 0;
}
//write data
cBufferData[cBufferLastPtr] = elementVal;
//increase length up to cBufferSize
if( cBufferElementsUsed < cBufferSize )
{
cBufferElementsUsed++;
}
}
//Averages the last n numbers and provides that. Discards fractions
float CircularBuffer::averageLast( uint16_t numElements )
{
if( numElements < recordLength() )
{
numElements = recordLength();
}
//Add up all the elements
float accumulator = 0;
int8_t i;
for( i = 0; i < numElements; i++ )
{
accumulator += getElement( i );
}
//Divide by number of elements
if( numElements != 0 )
{
accumulator /= numElements;
}
else
{
accumulator = 0;
}
return accumulator;
}
//Returns the current size of the buffer
uint16_t CircularBuffer::recordLength( void )
{
return cBufferElementsUsed;
}
@@ -0,0 +1,33 @@
#ifndef CIRCULARBUFFER_H
#define CIRCULARBUFFER_H
#include <stdint.h>
//****************************************************************************//
//
// Circular Buffer
//
//****************************************************************************//
//Class CircularBuffer is int16_t
//Does not care about over-running real data ( if request is outside length's bounds ).
//For example, the underlying machine writes [48], [49], [0], [1] ...
class CircularBuffer
{
public:
CircularBuffer( uint16_t inputSize );
~CircularBuffer();
float getElement( uint16_t ); //zero is the push location
void pushElement( float );
float averageLast( uint16_t );
uint16_t recordLength( void );
private:
uint16_t cBufferSize;
float *cBufferData;
int16_t cBufferLastPtr;
uint8_t cBufferElementsUsed;
};
#endif // CIRCULARBUFFER_H
@@ -0,0 +1,170 @@
/******************************************************************************
I2C_DeltaAltitude.ino
BME280 Arduino and Teensy example
Marshall Taylor @ SparkFun Electronics
May 20, 2015
https://github.com/sparkfun/SparkFun_BME280_Arduino_Library
This sketch configures a BME280 to measure height changes, with a button
to zero relative altitude.
Hardware connections:
BME280 -> Arduino
GND -> GND
3.3 -> 3.3
SDA -> A4
SCL -> A5
Button (Normally open) between A4 and A5.
To use, run the sketch then press and hold the button until the data on the
serial monitor shows zero. Then, move the sensor to a new altitude and watch
how the output changes!
Note: For most accurate results keep the sensor orientation and temperature the
same between measurements.
Resources:
Uses Wire.h for I2C operation
Uses SPI.h for SPI operation
Included CircularBuffer class for averaging
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
#include <stdint.h>
#include "SparkFunBME280.h"
#include "CircularBuffer.h"
#include "Wire.h"
#include "SPI.h"
//Global sensor object
BME280 mySensor;
uint8_t buttonGroundPin = A0;
uint8_t buttonSensePin = A2;
//This is a fixed-size buffer used for averaging data, a software LP filter
//Depending on the settings, the response can be quite slow.
CircularBuffer myBuffer(50);
float reference = 0;
void setup()
{
//Configure the button IO
pinMode( buttonSensePin, INPUT_PULLUP );
pinMode( buttonGroundPin, OUTPUT );
digitalWrite( buttonGroundPin, 0 );
//***Driver settings********************************//
//commInterface can be I2C_MODE or SPI_MODE
//specify chipSelectPin using arduino pin names
//specify I2C address. Can be 0x77(default) or 0x76
//For I2C, enable the following and disable the SPI section
mySensor.settings.commInterface = I2C_MODE;
mySensor.settings.I2CAddress = 0x77;
//For SPI enable the following and dissable the I2C section
//mySensor.settings.commInterface = SPI_MODE;
//mySensor.settings.chipSelectPin = 10;
//***Operation settings*****************************//
//renMode can be:
// 0, Sleep mode
// 1 or 2, Forced mode
// 3, Normal mode
mySensor.settings.runMode = 3; //Normal mode
//tStandby can be:
// 0, 0.5ms
// 1, 62.5ms
// 2, 125ms
// 3, 250ms
// 4, 500ms
// 5, 1000ms
// 6, 10ms
// 7, 20ms
mySensor.settings.tStandby = 0;
//filter can be off or number of FIR coefficients to use:
// 0, filter off
// 1, coefficients = 2
// 2, coefficients = 4
// 3, coefficients = 8
// 4, coefficients = 16
mySensor.settings.filter = 4; //Lots of HW filter
//tempOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.tempOverSample = 5;
//pressOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.pressOverSample = 5;
//humidOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.humidOverSample = 1;
Serial.begin(57600);
Serial.print("Program Started\n");
Serial.print("Starting BME280... result of .begin(): 0x");
delay(10); //Make sure sensor had enough time to turn on. BME280 requires 2ms to start up.
//Calling .begin() causes the settings to be loaded
Serial.println(mySensor.begin(), HEX);
Serial.println();
}
void loop()
{
//Get the local temperature! Do this for calibration
mySensor.readTempC();
//Check button. No debounce, so hold for operation
if( digitalRead( buttonSensePin ) == 0 )
{
//Set reference altitude.
reference = mySensor.readFloatAltitudeFeet();
}
float lastAlt = mySensor.readFloatAltitudeFeet() - reference;
myBuffer.pushElement(lastAlt);
float tempAlt = myBuffer.averageLast(15); //Do an average of the latest samples
Serial.println();
Serial.print("Temperature: ");
Serial.print(mySensor.readTempC(), 2);
Serial.println(" degrees C");
Serial.print("Last sample: ");
if(lastAlt >= 0)
{
Serial.print(" ");
}
Serial.print(lastAlt, 2);
Serial.println(" ft");
Serial.print("Last 15 samples averaged: ");
if(tempAlt >= 0)
{
Serial.print(" ");
}
Serial.print(tempAlt);
Serial.println(" ft");
delay(200);
}
@@ -0,0 +1,214 @@
/******************************************************************************
I2C_ReadAllData.ino
BME280 Arduino and Teensy example
Marshall Taylor @ SparkFun Electronics
May 20, 2015
https://github.com/sparkfun/SparkFun_BME280_Arduino_Library
This sketch configures the BME280 to read all measurements. The sketch also
displays the BME280's physical memory and what the driver perceives the
calibration words to be.
Resources:
Uses Wire.h for I2C operation
Uses SPI.h for SPI operation
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
#include <stdint.h>
#include "SparkFunBME280.h"
//Library allows either I2C or SPI, so include both.
#include "Wire.h"
#include "SPI.h"
//Global sensor object
BME280 mySensor;
void setup()
{
//***Driver settings********************************//
//commInterface can be I2C_MODE or SPI_MODE
//specify chipSelectPin using arduino pin names
//specify I2C address. Can be 0x77(default) or 0x76
//For I2C, enable the following and disable the SPI section
mySensor.settings.commInterface = I2C_MODE;
mySensor.settings.I2CAddress = 0x77;
//For SPI enable the following and dissable the I2C section
//mySensor.settings.commInterface = SPI_MODE;
//mySensor.settings.chipSelectPin = 10;
//***Operation settings*****************************//
//renMode can be:
// 0, Sleep mode
// 1 or 2, Forced mode
// 3, Normal mode
mySensor.settings.runMode = 3; //Normal mode
//tStandby can be:
// 0, 0.5ms
// 1, 62.5ms
// 2, 125ms
// 3, 250ms
// 4, 500ms
// 5, 1000ms
// 6, 10ms
// 7, 20ms
mySensor.settings.tStandby = 0;
//filter can be off or number of FIR coefficients to use:
// 0, filter off
// 1, coefficients = 2
// 2, coefficients = 4
// 3, coefficients = 8
// 4, coefficients = 16
mySensor.settings.filter = 0;
//tempOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.tempOverSample = 1;
//pressOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.pressOverSample = 1;
//humidOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.humidOverSample = 1;
Serial.begin(57600);
Serial.print("Program Started\n");
Serial.print("Starting BME280... result of .begin(): 0x");
//Calling .begin() causes the settings to be loaded
delay(10); //Make sure sensor had enough time to turn on. BME280 requires 2ms to start up.
Serial.println(mySensor.begin(), HEX);
Serial.print("Displaying ID, reset and ctrl regs\n");
Serial.print("ID(0xD0): 0x");
Serial.println(mySensor.readRegister(BME280_CHIP_ID_REG), HEX);
Serial.print("Reset register(0xE0): 0x");
Serial.println(mySensor.readRegister(BME280_RST_REG), HEX);
Serial.print("ctrl_meas(0xF4): 0x");
Serial.println(mySensor.readRegister(BME280_CTRL_MEAS_REG), HEX);
Serial.print("ctrl_hum(0xF2): 0x");
Serial.println(mySensor.readRegister(BME280_CTRL_HUMIDITY_REG), HEX);
Serial.print("\n\n");
Serial.print("Displaying all regs\n");
uint8_t memCounter = 0x80;
uint8_t tempReadData;
for(int rowi = 8; rowi < 16; rowi++ )
{
Serial.print("0x");
Serial.print(rowi, HEX);
Serial.print("0:");
for(int coli = 0; coli < 16; coli++ )
{
tempReadData = mySensor.readRegister(memCounter);
Serial.print((tempReadData >> 4) & 0x0F, HEX);//Print first hex nibble
Serial.print(tempReadData & 0x0F, HEX);//Print second hex nibble
Serial.print(" ");
memCounter++;
}
Serial.print("\n");
}
Serial.print("\n\n");
Serial.print("Displaying concatenated calibration words\n");
Serial.print("dig_T1, uint16: ");
Serial.println(mySensor.calibration.dig_T1);
Serial.print("dig_T2, int16: ");
Serial.println(mySensor.calibration.dig_T2);
Serial.print("dig_T3, int16: ");
Serial.println(mySensor.calibration.dig_T3);
Serial.print("dig_P1, uint16: ");
Serial.println(mySensor.calibration.dig_P1);
Serial.print("dig_P2, int16: ");
Serial.println(mySensor.calibration.dig_P2);
Serial.print("dig_P3, int16: ");
Serial.println(mySensor.calibration.dig_P3);
Serial.print("dig_P4, int16: ");
Serial.println(mySensor.calibration.dig_P4);
Serial.print("dig_P5, int16: ");
Serial.println(mySensor.calibration.dig_P5);
Serial.print("dig_P6, int16: ");
Serial.println(mySensor.calibration.dig_P6);
Serial.print("dig_P7, int16: ");
Serial.println(mySensor.calibration.dig_P7);
Serial.print("dig_P8, int16: ");
Serial.println(mySensor.calibration.dig_P8);
Serial.print("dig_P9, int16: ");
Serial.println(mySensor.calibration.dig_P9);
Serial.print("dig_H1, uint8: ");
Serial.println(mySensor.calibration.dig_H1);
Serial.print("dig_H2, int16: ");
Serial.println(mySensor.calibration.dig_H2);
Serial.print("dig_H3, uint8: ");
Serial.println(mySensor.calibration.dig_H3);
Serial.print("dig_H4, int16: ");
Serial.println(mySensor.calibration.dig_H4);
Serial.print("dig_H5, int16: ");
Serial.println(mySensor.calibration.dig_H5);
Serial.print("dig_H6, uint8: ");
Serial.println(mySensor.calibration.dig_H6);
Serial.println();
}
void loop()
{
//Each loop, take a reading.
//Start with temperature, as that data is needed for accurate compensation.
//Reading the temperature updates the compensators of the other functions
//in the background.
Serial.print("Temperature: ");
Serial.print(mySensor.readTempC(), 2);
Serial.println(" degrees C");
Serial.print("Temperature: ");
Serial.print(mySensor.readTempF(), 2);
Serial.println(" degrees F");
Serial.print("Pressure: ");
Serial.print(mySensor.readFloatPressure(), 2);
Serial.println(" Pa");
Serial.print("Altitude: ");
Serial.print(mySensor.readFloatAltitudeMeters(), 2);
Serial.println("m");
Serial.print("Altitude: ");
Serial.print(mySensor.readFloatAltitudeFeet(), 2);
Serial.println("ft");
Serial.print("%RH: ");
Serial.print(mySensor.readFloatHumidity(), 2);
Serial.println(" %");
Serial.println();
delay(1000);
}
@@ -0,0 +1,147 @@
/******************************************************************************
I2C_and_SPI_Multisensor.ino
BME280 Arduino and Teensy example
Marshall Taylor @ SparkFun Electronics
May 20, 2015
https://github.com/sparkfun/SparkFun_BME280_Arduino_Library
This sketch configures two BME280 breakouts. One is configured as I2C and
the other as SPI. Data from both are displayed.
Sensor A is I2C and connected through A4 and A5 (SDA/SCL)
Sensor B is SPI and connected through pins 10, 11, 12, and 13 through a
level shifter, with pin 10 being used for chip select.
Resources:
Uses Wire.h for I2C operation
Uses SPI.h for SPI operation
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
#include <stdint.h>
#include "SparkFunBME280.h"
#include "Wire.h"
#include "SPI.h"
//Global sensor object
BME280 mySensorA;
BME280 mySensorB;
void setup()
{
//***Set up sensor 'A'******************************//
//commInterface can be I2C_MODE or SPI_MODE
mySensorA.settings.commInterface = I2C_MODE;
mySensorA.settings.I2CAddress = 0x77;
mySensorA.settings.runMode = 3; // 3, Normal mode
mySensorA.settings.tStandby = 0; // 0, 0.5ms
mySensorA.settings.filter = 0; // 0, filter off
//tempOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensorA.settings.tempOverSample = 1;
//pressOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensorA.settings.pressOverSample = 1;
//humidOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensorA.settings.humidOverSample = 1;
//***Set up sensor 'B'******************************//
//commInterface can be I2C_MODE or SPI_MODE
//specify chipSelectPin using arduino pin names
//specify I2C address. Can be 0x77(default) or 0x76
mySensorB.settings.commInterface = SPI_MODE;
mySensorB.settings.chipSelectPin = 10;
mySensorB.settings.runMode = 3; // 3, Normal mode
mySensorB.settings.tStandby = 0; // 0, 0.5ms
mySensorB.settings.filter = 0; // 0, filter off
//tempOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensorB.settings.tempOverSample = 1;
//pressOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensorB.settings.pressOverSample = 1;
//humidOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensorB.settings.humidOverSample = 1;
//***Initialize the things**************************//
Serial.begin(57600);
Serial.print("Program Started\n");
Serial.println("Starting BME280s... result of .begin():");
delay(10); //Make sure sensor had enough time to turn on. BME280 requires 2ms to start up.
//Calling .begin() causes the settings to be loaded
Serial.print("Sensor A: 0x");
Serial.println(mySensorA.begin(), HEX);
Serial.print("Sensor B: 0x");
Serial.println(mySensorB.begin(), HEX);
}
void loop()
{
//Start with temperature, as that data is needed for accurate compensation.
//Reading the temperature updates the compensators of the other functions
//in the background.
Serial.print("Temperature: ");
Serial.print(mySensorA.readTempC(), 2);
Serial.print(", ");
Serial.print(mySensorB.readTempC(), 2);
Serial.println(" degrees C");
Serial.print("Temperature: ");
Serial.print(mySensorA.readTempF(), 2);
Serial.print(", ");
Serial.print(mySensorB.readTempF(), 2);
Serial.println(" degrees F");
Serial.print("Pressure: ");
Serial.print(mySensorA.readFloatPressure(), 2);
Serial.print(", ");
Serial.print(mySensorB.readFloatPressure(), 2);
Serial.println(" Pa");
Serial.print("Altitude: ");
Serial.print(mySensorA.readFloatAltitudeMeters(), 2);
Serial.print(", ");
Serial.print(mySensorB.readFloatAltitudeMeters(), 2);
Serial.println("m");
Serial.print("Altitude: ");
Serial.print(mySensorA.readFloatAltitudeFeet(), 2);
Serial.print(", ");
Serial.print(mySensorB.readFloatAltitudeFeet(), 2);
Serial.println("ft");
Serial.print("%RH: ");
Serial.print(mySensorA.readFloatHumidity(), 2);
Serial.print(", ");
Serial.print(mySensorB.readFloatHumidity(), 2);
Serial.println(" %");
Serial.println();
delay(1000);
}
@@ -0,0 +1,104 @@
#include "CircularBuffer.h"
#include <stdint.h>
//****************************************************************************//
//
// Circular buffer
//
//****************************************************************************//
//Construct a CircularBuffer type with arguments
// uint16_t inputSize: number of elements
CircularBuffer::CircularBuffer(uint16_t inputSize)
{
cBufferData = new float[inputSize];
cBufferLastPtr = 0;
cBufferElementsUsed = 0;
cBufferSize = inputSize;
}
CircularBuffer::~CircularBuffer()
{
delete[] cBufferData;
}
//Get an element at some depth into the circular buffer
//zero is the push location. Max is cBufferSize - 1
//
//Arguments:
// uint16_t elementNum: number of element in
//
float CircularBuffer::getElement( uint16_t elementNum )
{
//Translate elementNum into terms of cBufferLastPtr.
int16_t virtualElementNum;
virtualElementNum = cBufferLastPtr - elementNum;
if( virtualElementNum < 0 )
{
virtualElementNum += cBufferSize;
}
//Output the value
return cBufferData[virtualElementNum];
}
//Put a new element into the buffer.
//This also expands the size up to the max size
//Arguments:
//
// int16_t elementVal: value of new element
//
void CircularBuffer::pushElement( float elementVal )
{
//inc. the pointer
cBufferLastPtr++;
//deal with roll
if( cBufferLastPtr >= cBufferSize )
{
cBufferLastPtr = 0;
}
//write data
cBufferData[cBufferLastPtr] = elementVal;
//increase length up to cBufferSize
if( cBufferElementsUsed < cBufferSize )
{
cBufferElementsUsed++;
}
}
//Averages the last n numbers and provides that. Discards fractions
float CircularBuffer::averageLast( uint16_t numElements )
{
if( numElements < recordLength() )
{
numElements = recordLength();
}
//Add up all the elements
float accumulator = 0;
int8_t i;
for( i = 0; i < numElements; i++ )
{
accumulator += getElement( i );
}
//Divide by number of elements
if( numElements != 0 )
{
accumulator /= numElements;
}
else
{
accumulator = 0;
}
return accumulator;
}
//Returns the current size of the buffer
uint16_t CircularBuffer::recordLength( void )
{
return cBufferElementsUsed;
}
@@ -0,0 +1,33 @@
#ifndef CIRCULARBUFFER_H
#define CIRCULARBUFFER_H
#include <stdint.h>
//****************************************************************************//
//
// Circular Buffer
//
//****************************************************************************//
//Class CircularBuffer is int16_t
//Does not care about over-running real data ( if request is outside length's bounds ).
//For example, the underlying machine writes [48], [49], [0], [1] ...
class CircularBuffer
{
public:
CircularBuffer( uint16_t inputSize );
~CircularBuffer();
float getElement( uint16_t ); //zero is the push location
void pushElement( float );
float averageLast( uint16_t );
uint16_t recordLength( void );
private:
uint16_t cBufferSize;
float *cBufferData;
int16_t cBufferLastPtr;
uint8_t cBufferElementsUsed;
};
#endif // CIRCULARBUFFER_H
@@ -0,0 +1,181 @@
/******************************************************************************
LCD_DeltaAltitude.ino
BME280 Arduino and Teensy example
Marshall Taylor @ SparkFun Electronics
Oct 19, 2015
https://github.com/sparkfun/SparkFun_BME280_Arduino_Library
This sketch configures a BME280 to measure height changes, with a button
to zero.
Hardware connections:
BME280 -> Arduino
GND -> GND
3.3 -> 3.3
SDA -> A4
SCL -> A5
Button (Normally open) between A4 and A5.
LCD:
* LCD RS pin to digital pin 7
* LCD Enable pin to digital 6
* LCD D4 pin to digital pin 5
* LCD D5 pin to digital pin 4
* LCD D6 pin to digital pin 3
* LCD D7 pin to digital pin 2
* LCD R/W pin to ground
* 10K resistor:
* ends to +5V and ground
* wiper to LCD VO pin (pin 3)
To use, run the sketch, then press and hold the button until the data on the
serial monitor shows zero. Then, move the sensor to a new altitude and watch
how the output changes!
Note: For most accurate results keep the sensor orientation and temperature the
same between measurements.
Resources:
Uses Wire.h for I2C operation
Uses SPI.h for SPI operation
Included CircularBuffer class for averaging
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
#include <stdint.h>
#include "SparkFunBME280.h"
#include "CircularBuffer.h"
#include "Wire.h"
#include "SPI.h"
#include <LiquidCrystal.h>
//Global sensor object
BME280 mySensor;
uint8_t buttonGroundPin = A0;
uint8_t buttonSensePin = A2;
CircularBuffer myBuffer(50);
//int icounter = 0;
float reference = 0;
LiquidCrystal lcd(7,6,5,4,3,2);
void setup()
{
//Configure the button IO
pinMode( buttonSensePin, INPUT_PULLUP );
pinMode( buttonGroundPin, OUTPUT );
digitalWrite( buttonGroundPin, 0 );
//***Driver settings********************************//
//commInterface can be I2C_MODE or SPI_MODE
//specify chipSelectPin using arduino pin names
//specify I2C address. Can be 0x77(default) or 0x76
//For I2C, enable the following and disable the SPI section
mySensor.settings.commInterface = I2C_MODE;
mySensor.settings.I2CAddress = 0x77;
//For SPI enable the following and dissable the I2C section
//mySensor.settings.commInterface = SPI_MODE;
//mySensor.settings.chipSelectPin = 10;
//***Operation settings*****************************//
//renMode can be:
// 0, Sleep mode
// 1 or 2, Forced mode
// 3, Normal mode
mySensor.settings.runMode = 3; //Forced mode
//tStandby can be:
// 0, 0.5ms
// 1, 62.5ms
// 2, 125ms
// 3, 250ms
// 4, 500ms
// 5, 1000ms
// 6, 10ms
// 7, 20ms
mySensor.settings.tStandby = 0;
//filter can be off or number of FIR coefficients to use:
// 0, filter off
// 1, coefficients = 2
// 2, coefficients = 4
// 3, coefficients = 8
// 4, coefficients = 16
mySensor.settings.filter = 4;
//tempOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.tempOverSample = 5;
//pressOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.pressOverSample = 5;
//humidOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.humidOverSample = 0;
Serial.begin(57600);
Serial.print("Program Started\n");
Serial.print("Starting BME280... result of .begin(): 0x");
//Calling .begin() causes the settings to be loaded
delay(10);//Needs > 2 ms to start up
Serial.println(mySensor.begin(), HEX);
Serial.println();
lcd.begin(16, 2);
lcd.clear();
}
void loop()
{
//Get the local temperature! Do this for calibration
mySensor.readTempC();
//Check button. No debounce, so hold for operation
if( digitalRead( buttonSensePin ) == 0 )
{
//Set reference altitude.
reference = mySensor.readFloatAltitudeFeet();
}
float lastAlt = mySensor.readFloatAltitudeFeet() - reference;
myBuffer.pushElement(lastAlt);
float tempAlt = myBuffer.averageLast(8); //Do an average of the latest samples
lcd.setCursor(0,0);
lcd.print("Altitude: ");
myBuffer.pushElement(lastAlt);
lcd.setCursor(0,1);
if(tempAlt >= 0)
{
lcd.print(" ");
}
lcd.print(tempAlt);
lcd.print(" ft ");
delay(200);
}
@@ -0,0 +1,230 @@
/*BME280 Arduino and Teensy example
Marshall Taylor @ SparkFun Electronics
Oct 19, 2015
https://github.com/sparkfun/SparkFun_BME280_Arduino_Library
This sketch displays the pressure in pascals and temperature
in fahrenheit.
Resources:
Uses Wire.h for I2C operation
Uses SPI.h for SPI operation
Hardware connections:
BME280 -> Arduino
GND -> GND
3.3 -> 3.3
SDA -> A4
SCL -> A5
LCD:
* LCD RS pin to digital pin 7
* LCD Enable pin to digital 6
* LCD D4 pin to digital pin 5
* LCD D5 pin to digital pin 4
* LCD D6 pin to digital pin 3
* LCD D7 pin to digital pin 2
* LCD R/W pin to ground
* 10K resistor:
* ends to +5V and ground
* wiper to LCD VO pin (pin 3)
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
// Load the LiquidCrystal library, which will give us
// commands to interface to the LCD:
#include <LiquidCrystal.h>
// Initialize the library with the pins we're using.
// (Note that you can use different pins if needed.)
// See http://arduino.cc/en/Reference/LiquidCrystal
// for more information:
#include <stdint.h>
#include "SparkFunBME280.h"
//Library allows either I2C or SPI, so include both.
#include "Wire.h"
#include "SPI.h"
//Global sensor object
BME280 mySensor;
LiquidCrystal lcd(7,6,5,4,3,2);
void setup()
{
lcd.begin(16, 2);
lcd.clear();
//***Driver settings********************************//
//commInterface can be I2C_MODE or SPI_MODE
//specify chipSelectPin using arduino pin names
//specify I2C address. Can be 0x77(default) or 0x76
//For I2C, enable the following and disable the SPI section
mySensor.settings.commInterface = I2C_MODE;
mySensor.settings.I2CAddress = 0x77;
//For SPI enable the following and dissable the I2C section
//mySensor.settings.commInterface = SPI_MODE;
//mySensor.settings.chipSelectPin = 10;
//***Operation settings*****************************//
//renMode can be:
// 0, Sleep mode
// 1 or 2, Forced mode
// 3, Normal mode
mySensor.settings.runMode = 3; //Forced mode
//tStandby can be:
// 0, 0.5ms
// 1, 62.5ms
// 2, 125ms
// 3, 250ms
// 4, 500ms
// 5, 1000ms
// 6, 10ms
// 7, 20ms
mySensor.settings.tStandby = 0;
//filter can be off or number of FIR coefficients to use:
// 0, filter off
// 1, coefficients = 2
// 2, coefficients = 4
// 3, coefficients = 8
// 4, coefficients = 16
mySensor.settings.filter = 0;
//tempOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.tempOverSample = 1;
//pressOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.pressOverSample = 1;
//humidOverSample can be:
// 0, skipped
// 1 through 5, oversampling *1, *2, *4, *8, *16 respectively
mySensor.settings.humidOverSample = 1;
Serial.begin(57600);
Serial.print("Program Started\n");
Serial.print("Starting BME280... result of .begin(): 0x");
//Calling .begin() causes the settings to be loaded
Serial.println(mySensor.begin(), HEX);
delay(10); //Use delay if reading directly after .begin is called. BME280 requires 2ms to start up.
Serial.print("Displaying ID, reset and ctrl regs\n");
Serial.print("ID(0xD0): 0x");
Serial.println(mySensor.readRegister(BME280_CHIP_ID_REG), HEX);
Serial.print("Reset register(0xE0): 0x");
Serial.println(mySensor.readRegister(BME280_RST_REG), HEX);
Serial.print("ctrl_meas(0xF4): 0x");
Serial.println(mySensor.readRegister(BME280_CTRL_MEAS_REG), HEX);
Serial.print("ctrl_hum(0xF2): 0x");
Serial.println(mySensor.readRegister(BME280_CTRL_HUMIDITY_REG), HEX);
Serial.print("\n\n");
Serial.print("Displaying all regs\n");
uint8_t memCounter = 0x80;
uint8_t tempReadData;
for(int rowi = 8; rowi < 16; rowi++ )
{
Serial.print("0x");
Serial.print(rowi, HEX);
Serial.print("0:");
for(int coli = 0; coli < 16; coli++ )
{
tempReadData = mySensor.readRegister(memCounter);
Serial.print((tempReadData >> 4) & 0x0F, HEX);//Print first hex nibble
Serial.print(tempReadData & 0x0F, HEX);//Print second hex nibble
Serial.print(" ");
memCounter++;
}
Serial.print("\n");
}
Serial.print("\n\n");
Serial.print("Displaying concatenated calibration words\n");
Serial.print("dig_T1, uint16: ");
Serial.println(mySensor.calibration.dig_T1);
Serial.print("dig_T2, int16: ");
Serial.println(mySensor.calibration.dig_T2);
Serial.print("dig_T3, int16: ");
Serial.println(mySensor.calibration.dig_T3);
Serial.print("dig_P1, uint16: ");
Serial.println(mySensor.calibration.dig_P1);
Serial.print("dig_P2, int16: ");
Serial.println(mySensor.calibration.dig_P2);
Serial.print("dig_P3, int16: ");
Serial.println(mySensor.calibration.dig_P3);
Serial.print("dig_P4, int16: ");
Serial.println(mySensor.calibration.dig_P4);
Serial.print("dig_P5, int16: ");
Serial.println(mySensor.calibration.dig_P5);
Serial.print("dig_P6, int16: ");
Serial.println(mySensor.calibration.dig_P6);
Serial.print("dig_P7, int16: ");
Serial.println(mySensor.calibration.dig_P7);
Serial.print("dig_P8, int16: ");
Serial.println(mySensor.calibration.dig_P8);
Serial.print("dig_P9, int16: ");
Serial.println(mySensor.calibration.dig_P9);
Serial.print("dig_H1, uint8: ");
Serial.println(mySensor.calibration.dig_H1);
Serial.print("dig_H2, int16: ");
Serial.println(mySensor.calibration.dig_H2);
Serial.print("dig_H3, uint8: ");
Serial.println(mySensor.calibration.dig_H3);
Serial.print("dig_H4, int16: ");
Serial.println(mySensor.calibration.dig_H4);
Serial.print("dig_H5, int16: ");
Serial.println(mySensor.calibration.dig_H5);
Serial.print("dig_H6, uint8: ");
Serial.println(mySensor.calibration.dig_H6);
Serial.println();
}
void loop()
{
//Get the local temperature! Do this for calibration
mySensor.readTempC();
lcd.setCursor(0,0);
lcd.print("Press: ");
lcd.print((uint32_t)mySensor.readFloatPressure());
lcd.print(" Pa");
lcd.setCursor(0,1);
lcd.print("Humid: ");
lcd.print((uint8_t)mySensor.readFloatHumidity());
lcd.print(" %");
delay(1000);
}
+77
View File
@@ -0,0 +1,77 @@
########################################################
# Syntax Coloring Map for SparkFun LSM6DS3 IMU Library #
########################################################
# Class
###################################################################
BME280 KEYWORD1
###################################################################
# Methods and Functions
###################################################################
begin KEYWORD2
reset KEYWORD2
readFloatPressure KEYWORD2
readFloatAltitudeMeters KEYWORD2
readFloatAltitudeFeet KEYWORD2
readFloatHumidity KEYWORD2
readTempC KEYWORD2
readTempF KEYWORD2
readRegisterRegion KEYWORD2
readRegister KEYWORD2
readRegisterInt16 KEYWORD2
writeRegister KEYWORD2
###################################################################
# Constants
###################################################################
I2C_MODE LITERAL1
SPI_MODE LITERAL1
BME280_DIG_T1_LSB_REG LITERAL1
BME280_DIG_T1_MSB_REG LITERAL1
BME280_DIG_T2_LSB_REG LITERAL1
BME280_DIG_T2_MSB_REG LITERAL1
BME280_DIG_T3_LSB_REG LITERAL1
BME280_DIG_T3_MSB_REG LITERAL1
BME280_DIG_P1_LSB_REG LITERAL1
BME280_DIG_P1_MSB_REG LITERAL1
BME280_DIG_P2_LSB_REG LITERAL1
BME280_DIG_P2_MSB_REG LITERAL1
BME280_DIG_P3_LSB_REG LITERAL1
BME280_DIG_P3_MSB_REG LITERAL1
BME280_DIG_P4_LSB_REG LITERAL1
BME280_DIG_P4_MSB_REG LITERAL1
BME280_DIG_P5_LSB_REG LITERAL1
BME280_DIG_P5_MSB_REG LITERAL1
BME280_DIG_P6_LSB_REG LITERAL1
BME280_DIG_P6_MSB_REG LITERAL1
BME280_DIG_P7_LSB_REG LITERAL1
BME280_DIG_P7_MSB_REG LITERAL1
BME280_DIG_P8_LSB_REG LITERAL1
BME280_DIG_P8_MSB_REG LITERAL1
BME280_DIG_P9_LSB_REG LITERAL1
BME280_DIG_P9_MSB_REG LITERAL1
BME280_DIG_H1_REG LITERAL1
BME280_CHIP_ID_REG LITERAL1
BME280_RST_REG LITERAL1
BME280_DIG_H2_LSB_REG LITERAL1
BME280_DIG_H2_MSB_REG LITERAL1
BME280_DIG_H3_REG LITERAL1
BME280_DIG_H4_MSB_REG LITERAL1
BME280_DIG_H4_LSB_REG LITERAL1
BME280_DIG_H5_MSB_REG LITERAL1
BME280_DIG_H6_REG LITERAL1
BME280_CTRL_HUMIDITY_REG LITERAL1
BME280_STAT_REG LITERAL1
BME280_CTRL_MEAS_REG LITERAL1
BME280_CONFIG_REG LITERAL1
BME280_PRESSURE_MSB_REG LITERAL1
BME280_PRESSURE_LSB_REG LITERAL1
BME280_PRESSURE_XLSB_REG LITERAL1
BME280_TEMPERATURE_MSB_REG LITERAL1
BME280_TEMPERATURE_LSB_REG LITERAL1
BME280_TEMPERATURE_XLSB_REG LITERAL1
BME280_HUMIDITY_MSB_REG LITERAL1
BME280_HUMIDITY_LSB_REG LITERAL1
+9
View File
@@ -0,0 +1,9 @@
name=SparkFun BME280
version=1.2.0
author=Marshall Taylor
maintainer=SparkFun Electronics <sparkfun.com>
sentence=A library to drive the Bosch BME280 Altimeter and Pressure sensor
paragraph=See code for comments.
category=Sensors
url=https://github.com/sparkfun/SparkFun_BME280_Arduino_Library
architectures=*
Binary file not shown.

After

Width:  |  Height:  |  Size: 26 KiB

+400
View File
@@ -0,0 +1,400 @@
/******************************************************************************
SparkFunBME280.cpp
BME280 Arduino and Teensy Driver
Marshall Taylor @ SparkFun Electronics
May 20, 2015
https://github.com/sparkfun/BME280_Breakout
Resources:
Uses Wire.h for i2c operation
Uses SPI.h for SPI operation
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
//See SparkFunBME280.h for additional topology notes.
#include "SparkFunBME280.h"
#include "stdint.h"
#include <math.h>
#include <Arduino.h>
#include "Wire.h"
#include "SPI.h"
//****************************************************************************//
//
// Settings and configuration
//
//****************************************************************************//
//Constructor -- Specifies default configuration
BME280::BME280( void )
{
//Construct with these default settings if nothing is specified
//Select interface mode
settings.commInterface = I2C_MODE; //Can be I2C_MODE, SPI_MODE
//Select address for I2C. Does nothing for SPI
settings.I2CAddress = 0x77; //Ignored for SPI_MODE
//Select CS pin for SPI. Does nothing for I2C
settings.chipSelectPin = 10;
settings.runMode = 0;
settings.tempOverSample = 0;
settings.pressOverSample = 0;
settings.humidOverSample = 0;
}
//****************************************************************************//
//
// Configuration section
//
// This uses the stored SensorSettings to start the IMU
// Use statements such as "mySensor.settings.commInterface = SPI_MODE;" to
// configure before calling .begin();
//
//****************************************************************************//
uint8_t BME280::begin()
{
//Check the settings structure values to determine how to setup the device
uint8_t dataToWrite = 0; //Temporary variable
switch (settings.commInterface)
{
case I2C_MODE:
Wire.begin();
break;
case SPI_MODE:
// start the SPI library:
SPI.begin();
#ifdef ARDUINO_ARCH_ESP32
SPI.setFrequency(1000000);
// Data is read and written MSb first.
SPI.setBitOrder(SPI_MSBFIRST);
// Like the standard arduino/teensy comment below, mode0 seems wrong according to standards
// but conforms to the timing diagrams when used for the ESP32
SPI.setDataMode(SPI_MODE0);
#else
// Maximum SPI frequency is 10MHz, could divide by 2 here:
SPI.setClockDivider(SPI_CLOCK_DIV32);
// Data is read and written MSb first.
SPI.setBitOrder(MSBFIRST);
// Data is captured on rising edge of clock (CPHA = 0)
// Base value of the clock is HIGH (CPOL = 1)
// This was SPI_MODE3 for RedBoard, but I had to change to
// MODE0 for Teensy 3.1 operation
SPI.setDataMode(SPI_MODE3);
#endif
// initalize the data ready and chip select pins:
pinMode(settings.chipSelectPin, OUTPUT);
digitalWrite(settings.chipSelectPin, HIGH);
break;
default:
break;
}
//Reading all compensation data, range 0x88:A1, 0xE1:E7
calibration.dig_T1 = ((uint16_t)((readRegister(BME280_DIG_T1_MSB_REG) << 8) + readRegister(BME280_DIG_T1_LSB_REG)));
calibration.dig_T2 = ((int16_t)((readRegister(BME280_DIG_T2_MSB_REG) << 8) + readRegister(BME280_DIG_T2_LSB_REG)));
calibration.dig_T3 = ((int16_t)((readRegister(BME280_DIG_T3_MSB_REG) << 8) + readRegister(BME280_DIG_T3_LSB_REG)));
calibration.dig_P1 = ((uint16_t)((readRegister(BME280_DIG_P1_MSB_REG) << 8) + readRegister(BME280_DIG_P1_LSB_REG)));
calibration.dig_P2 = ((int16_t)((readRegister(BME280_DIG_P2_MSB_REG) << 8) + readRegister(BME280_DIG_P2_LSB_REG)));
calibration.dig_P3 = ((int16_t)((readRegister(BME280_DIG_P3_MSB_REG) << 8) + readRegister(BME280_DIG_P3_LSB_REG)));
calibration.dig_P4 = ((int16_t)((readRegister(BME280_DIG_P4_MSB_REG) << 8) + readRegister(BME280_DIG_P4_LSB_REG)));
calibration.dig_P5 = ((int16_t)((readRegister(BME280_DIG_P5_MSB_REG) << 8) + readRegister(BME280_DIG_P5_LSB_REG)));
calibration.dig_P6 = ((int16_t)((readRegister(BME280_DIG_P6_MSB_REG) << 8) + readRegister(BME280_DIG_P6_LSB_REG)));
calibration.dig_P7 = ((int16_t)((readRegister(BME280_DIG_P7_MSB_REG) << 8) + readRegister(BME280_DIG_P7_LSB_REG)));
calibration.dig_P8 = ((int16_t)((readRegister(BME280_DIG_P8_MSB_REG) << 8) + readRegister(BME280_DIG_P8_LSB_REG)));
calibration.dig_P9 = ((int16_t)((readRegister(BME280_DIG_P9_MSB_REG) << 8) + readRegister(BME280_DIG_P9_LSB_REG)));
calibration.dig_H1 = ((uint8_t)(readRegister(BME280_DIG_H1_REG)));
calibration.dig_H2 = ((int16_t)((readRegister(BME280_DIG_H2_MSB_REG) << 8) + readRegister(BME280_DIG_H2_LSB_REG)));
calibration.dig_H3 = ((uint8_t)(readRegister(BME280_DIG_H3_REG)));
calibration.dig_H4 = ((int16_t)((readRegister(BME280_DIG_H4_MSB_REG) << 4) + (readRegister(BME280_DIG_H4_LSB_REG) & 0x0F)));
calibration.dig_H5 = ((int16_t)((readRegister(BME280_DIG_H5_MSB_REG) << 4) + ((readRegister(BME280_DIG_H4_LSB_REG) >> 4) & 0x0F)));
calibration.dig_H6 = ((uint8_t)readRegister(BME280_DIG_H6_REG));
//Set the oversampling control words.
//config will only be writeable in sleep mode, so first insure that.
writeRegister(BME280_CTRL_MEAS_REG, 0x00);
//Set the config word
dataToWrite = (settings.tStandby << 0x5) & 0xE0;
dataToWrite |= (settings.filter << 0x02) & 0x1C;
writeRegister(BME280_CONFIG_REG, dataToWrite);
//Set ctrl_hum first, then ctrl_meas to activate ctrl_hum
dataToWrite = settings.humidOverSample & 0x07; //all other bits can be ignored
writeRegister(BME280_CTRL_HUMIDITY_REG, dataToWrite);
//set ctrl_meas
//First, set temp oversampling
dataToWrite = (settings.tempOverSample << 0x5) & 0xE0;
//Next, pressure oversampling
dataToWrite |= (settings.pressOverSample << 0x02) & 0x1C;
//Last, set mode
dataToWrite |= (settings.runMode) & 0x03;
//Load the byte
writeRegister(BME280_CTRL_MEAS_REG, dataToWrite);
return readRegister(0xD0);
}
//Strictly resets. Run .begin() afterwards
void BME280::reset( void )
{
writeRegister(BME280_RST_REG, 0xB6);
}
//****************************************************************************//
//
// Pressure Section
//
//****************************************************************************//
float BME280::readFloatPressure( void )
{
// Returns pressure in Pa as unsigned 32 bit integer in Q24.8 format (24 integer bits and 8 fractional bits).
// Output value of “24674867” represents 24674867/256 = 96386.2 Pa = 963.862 hPa
int32_t adc_P = ((uint32_t)readRegister(BME280_PRESSURE_MSB_REG) << 12) | ((uint32_t)readRegister(BME280_PRESSURE_LSB_REG) << 4) | ((readRegister(BME280_PRESSURE_XLSB_REG) >> 4) & 0x0F);
int64_t var1, var2, p_acc;
var1 = ((int64_t)t_fine) - 128000;
var2 = var1 * var1 * (int64_t)calibration.dig_P6;
var2 = var2 + ((var1 * (int64_t)calibration.dig_P5)<<17);
var2 = var2 + (((int64_t)calibration.dig_P4)<<35);
var1 = ((var1 * var1 * (int64_t)calibration.dig_P3)>>8) + ((var1 * (int64_t)calibration.dig_P2)<<12);
var1 = (((((int64_t)1)<<47)+var1))*((int64_t)calibration.dig_P1)>>33;
if (var1 == 0)
{
return 0; // avoid exception caused by division by zero
}
p_acc = 1048576 - adc_P;
p_acc = (((p_acc<<31) - var2)*3125)/var1;
var1 = (((int64_t)calibration.dig_P9) * (p_acc>>13) * (p_acc>>13)) >> 25;
var2 = (((int64_t)calibration.dig_P8) * p_acc) >> 19;
p_acc = ((p_acc + var1 + var2) >> 8) + (((int64_t)calibration.dig_P7)<<4);
return (float)p_acc / 256.0;
}
float BME280::readFloatAltitudeMeters( void )
{
float heightOutput = 0;
heightOutput = ((float)-45846.2)*(pow(((float)readFloatPressure()/(float)101325), 0.190263) - (float)1);
return heightOutput;
}
float BME280::readFloatAltitudeFeet( void )
{
float heightOutput = 0;
heightOutput = readFloatAltitudeMeters() * 3.28084;
return heightOutput;
}
//****************************************************************************//
//
// Humidity Section
//
//****************************************************************************//
float BME280::readFloatHumidity( void )
{
// Returns humidity in %RH as unsigned 32 bit integer in Q22. 10 format (22 integer and 10 fractional bits).
// Output value of “47445” represents 47445/1024 = 46. 333 %RH
int32_t adc_H = ((uint32_t)readRegister(BME280_HUMIDITY_MSB_REG) << 8) | ((uint32_t)readRegister(BME280_HUMIDITY_LSB_REG));
int32_t var1;
var1 = (t_fine - ((int32_t)76800));
var1 = (((((adc_H << 14) - (((int32_t)calibration.dig_H4) << 20) - (((int32_t)calibration.dig_H5) * var1)) +
((int32_t)16384)) >> 15) * (((((((var1 * ((int32_t)calibration.dig_H6)) >> 10) * (((var1 * ((int32_t)calibration.dig_H3)) >> 11) + ((int32_t)32768))) >> 10) + ((int32_t)2097152)) *
((int32_t)calibration.dig_H2) + 8192) >> 14));
var1 = (var1 - (((((var1 >> 15) * (var1 >> 15)) >> 7) * ((int32_t)calibration.dig_H1)) >> 4));
var1 = (var1 < 0 ? 0 : var1);
var1 = (var1 > 419430400 ? 419430400 : var1);
return (float)(var1>>12) / 1024.0;
}
//****************************************************************************//
//
// Temperature Section
//
//****************************************************************************//
float BME280::readTempC( void )
{
// Returns temperature in DegC, resolution is 0.01 DegC. Output value of “5123” equals 51.23 DegC.
// t_fine carries fine temperature as global value
//get the reading (adc_T);
int32_t adc_T = ((uint32_t)readRegister(BME280_TEMPERATURE_MSB_REG) << 12) | ((uint32_t)readRegister(BME280_TEMPERATURE_LSB_REG) << 4) | ((readRegister(BME280_TEMPERATURE_XLSB_REG) >> 4) & 0x0F);
//By datasheet, calibrate
int64_t var1, var2;
var1 = ((((adc_T>>3) - ((int32_t)calibration.dig_T1<<1))) * ((int32_t)calibration.dig_T2)) >> 11;
var2 = (((((adc_T>>4) - ((int32_t)calibration.dig_T1)) * ((adc_T>>4) - ((int32_t)calibration.dig_T1))) >> 12) *
((int32_t)calibration.dig_T3)) >> 14;
t_fine = var1 + var2;
float output = (t_fine * 5 + 128) >> 8;
output = output / 100;
return output;
}
float BME280::readTempF( void )
{
float output = readTempC();
output = (output * 9) / 5 + 32;
return output;
}
//****************************************************************************//
//
// Utility
//
//****************************************************************************//
void BME280::readRegisterRegion(uint8_t *outputPointer , uint8_t offset, uint8_t length)
{
//define pointer that will point to the external space
uint8_t i = 0;
char c = 0;
switch (settings.commInterface)
{
case I2C_MODE:
Wire.beginTransmission(settings.I2CAddress);
Wire.write(offset);
Wire.endTransmission();
// request bytes from slave device
Wire.requestFrom(settings.I2CAddress, length);
while ( (Wire.available()) && (i < length)) // slave may send less than requested
{
c = Wire.read(); // receive a byte as character
*outputPointer = c;
outputPointer++;
i++;
}
break;
case SPI_MODE:
// take the chip select low to select the device:
digitalWrite(settings.chipSelectPin, LOW);
// send the device the register you want to read:
SPI.transfer(offset | 0x80); //Ored with "read request" bit
while ( i < length ) // slave may send less than requested
{
c = SPI.transfer(0x00); // receive a byte as character
*outputPointer = c;
outputPointer++;
i++;
}
// take the chip select high to de-select:
digitalWrite(settings.chipSelectPin, HIGH);
break;
default:
break;
}
}
uint8_t BME280::readRegister(uint8_t offset)
{
//Return value
uint8_t result;
uint8_t numBytes = 1;
switch (settings.commInterface) {
case I2C_MODE:
Wire.beginTransmission(settings.I2CAddress);
Wire.write(offset);
Wire.endTransmission();
Wire.requestFrom(settings.I2CAddress, numBytes);
while ( Wire.available() ) // slave may send less than requested
{
result = Wire.read(); // receive a byte as a proper uint8_t
}
break;
case SPI_MODE:
// take the chip select low to select the device:
digitalWrite(settings.chipSelectPin, LOW);
// send the device the register you want to read:
SPI.transfer(offset | 0x80); //Ored with "read request" bit
// send a value of 0 to read the first byte returned:
result = SPI.transfer(0x00);
// take the chip select high to de-select:
digitalWrite(settings.chipSelectPin, HIGH);
break;
default:
break;
}
return result;
}
int16_t BME280::readRegisterInt16( uint8_t offset )
{
uint8_t myBuffer[2];
readRegisterRegion(myBuffer, offset, 2); //Does memory transfer
int16_t output = (int16_t)myBuffer[0] | int16_t(myBuffer[1] << 8);
return output;
}
void BME280::writeRegister(uint8_t offset, uint8_t dataToWrite)
{
switch (settings.commInterface)
{
case I2C_MODE:
//Write the byte
Wire.beginTransmission(settings.I2CAddress);
Wire.write(offset);
Wire.write(dataToWrite);
Wire.endTransmission();
break;
case SPI_MODE:
// take the chip select low to select the device:
digitalWrite(settings.chipSelectPin, LOW);
// send the device the register you want to read:
SPI.transfer(offset & 0x7F);
// send a value of 0 to read the first byte returned:
SPI.transfer(dataToWrite);
// decrement the number of bytes left to read:
// take the chip select high to de-select:
digitalWrite(settings.chipSelectPin, HIGH);
break;
default:
break;
}
}
+186
View File
@@ -0,0 +1,186 @@
/******************************************************************************
SparkFunBME280.h
BME280 Arduino and Teensy Driver
Marshall Taylor @ SparkFun Electronics
May 20, 2015
https://github.com/sparkfun/BME280_Breakout
Resources:
Uses Wire.h for i2c operation
Uses SPI.h for SPI operation
Development environment specifics:
Arduino IDE 1.6.4
Teensy loader 1.23
This code is released under the [MIT License](http://opensource.org/licenses/MIT).
Please review the LICENSE.md file included with this example. If you have any questions
or concerns with licensing, please contact techsupport@sparkfun.com.
Distributed as-is; no warranty is given.
******************************************************************************/
// Test derived class for base class SparkFunIMU
#ifndef __BME280_H__
#define __BME280_H__
#include "stdint.h"
#define I2C_MODE 0
#define SPI_MODE 1
//Register names:
#define BME280_DIG_T1_LSB_REG 0x88
#define BME280_DIG_T1_MSB_REG 0x89
#define BME280_DIG_T2_LSB_REG 0x8A
#define BME280_DIG_T2_MSB_REG 0x8B
#define BME280_DIG_T3_LSB_REG 0x8C
#define BME280_DIG_T3_MSB_REG 0x8D
#define BME280_DIG_P1_LSB_REG 0x8E
#define BME280_DIG_P1_MSB_REG 0x8F
#define BME280_DIG_P2_LSB_REG 0x90
#define BME280_DIG_P2_MSB_REG 0x91
#define BME280_DIG_P3_LSB_REG 0x92
#define BME280_DIG_P3_MSB_REG 0x93
#define BME280_DIG_P4_LSB_REG 0x94
#define BME280_DIG_P4_MSB_REG 0x95
#define BME280_DIG_P5_LSB_REG 0x96
#define BME280_DIG_P5_MSB_REG 0x97
#define BME280_DIG_P6_LSB_REG 0x98
#define BME280_DIG_P6_MSB_REG 0x99
#define BME280_DIG_P7_LSB_REG 0x9A
#define BME280_DIG_P7_MSB_REG 0x9B
#define BME280_DIG_P8_LSB_REG 0x9C
#define BME280_DIG_P8_MSB_REG 0x9D
#define BME280_DIG_P9_LSB_REG 0x9E
#define BME280_DIG_P9_MSB_REG 0x9F
#define BME280_DIG_H1_REG 0xA1
#define BME280_CHIP_ID_REG 0xD0 //Chip ID
#define BME280_RST_REG 0xE0 //Softreset Reg
#define BME280_DIG_H2_LSB_REG 0xE1
#define BME280_DIG_H2_MSB_REG 0xE2
#define BME280_DIG_H3_REG 0xE3
#define BME280_DIG_H4_MSB_REG 0xE4
#define BME280_DIG_H4_LSB_REG 0xE5
#define BME280_DIG_H5_MSB_REG 0xE6
#define BME280_DIG_H6_REG 0xE7
#define BME280_CTRL_HUMIDITY_REG 0xF2 //Ctrl Humidity Reg
#define BME280_STAT_REG 0xF3 //Status Reg
#define BME280_CTRL_MEAS_REG 0xF4 //Ctrl Measure Reg
#define BME280_CONFIG_REG 0xF5 //Configuration Reg
#define BME280_PRESSURE_MSB_REG 0xF7 //Pressure MSB
#define BME280_PRESSURE_LSB_REG 0xF8 //Pressure LSB
#define BME280_PRESSURE_XLSB_REG 0xF9 //Pressure XLSB
#define BME280_TEMPERATURE_MSB_REG 0xFA //Temperature MSB
#define BME280_TEMPERATURE_LSB_REG 0xFB //Temperature LSB
#define BME280_TEMPERATURE_XLSB_REG 0xFC //Temperature XLSB
#define BME280_HUMIDITY_MSB_REG 0xFD //Humidity MSB
#define BME280_HUMIDITY_LSB_REG 0xFE //Humidity LSB
//Class SensorSettings. This object is used to hold settings data. The application
//uses this classes' data directly. The settings are adopted and sent to the sensor
//at special times, such as .begin. Some are used for doing math.
//
//This is a kind of bloated way to do this. The trade-off is that the user doesn't
//need to deal with #defines or enums with bizarre names.
//
//A power user would strip out SensorSettings entirely, and send specific read and
//write command directly to the IC. (ST #defines below)
//
struct SensorSettings
{
public:
//Main Interface and mode settings
uint8_t commInterface;
uint8_t I2CAddress;
uint8_t chipSelectPin;
uint8_t runMode;
uint8_t tStandby;
uint8_t filter;
uint8_t tempOverSample;
uint8_t pressOverSample;
uint8_t humidOverSample;
};
//Used to hold the calibration constants. These are used
//by the driver as measurements are being taking
struct SensorCalibration
{
public:
uint16_t dig_T1;
int16_t dig_T2;
int16_t dig_T3;
uint16_t dig_P1;
int16_t dig_P2;
int16_t dig_P3;
int16_t dig_P4;
int16_t dig_P5;
int16_t dig_P6;
int16_t dig_P7;
int16_t dig_P8;
int16_t dig_P9;
uint8_t dig_H1;
int16_t dig_H2;
uint8_t dig_H3;
int16_t dig_H4;
int16_t dig_H5;
uint8_t dig_H6;
};
//This is the man operational class of the driver.
class BME280
{
public:
//settings
SensorSettings settings;
SensorCalibration calibration;
int32_t t_fine;
//Constructor generates default SensorSettings.
//(over-ride after construction if desired)
BME280( void );
//~BME280() = default;
//Call to apply SensorSettings.
//This also gets the SensorCalibration constants
uint8_t begin( void );
//Software reset routine
void reset( void );
//Returns the values as floats.
float readFloatPressure( void );
float readFloatAltitudeMeters( void );
float readFloatAltitudeFeet( void );
float readFloatHumidity( void );
//Temperature related methods
float readTempC( void );
float readTempF( void );
//The following utilities read and write
//ReadRegisterRegion takes a uint8 array address as input and reads
//a chunk of memory into that array.
void readRegisterRegion(uint8_t*, uint8_t, uint8_t );
//readRegister reads one register
uint8_t readRegister(uint8_t);
//Reads two regs, LSByte then MSByte order, and concatenates them
//Used for two-byte reads
int16_t readRegisterInt16( uint8_t offset );
//Writes a byte;
void writeRegister(uint8_t, uint8_t);
};
#endif // End of __BME280_H__ definition check