The best tools to make your project dreams come true

Login or Signup


By Adafruit Industries

Monitor your Environmental Sensors from the Cloud Using a Feather or PI

Courtesy of Adafruit

Overview

Figure 1

Knowing what's in the air you breathe is important - and building an environmental monitor is a way to visualize the invisible properties of the air you inhale.

This guide covers building a small, internet-enabled environmental monitor which can track a range of data such from temperature to UV-level to the amount of total-volatile-organic-compounds present in the air.

Build it, place it in a location you'd like to log, and then monitor it from anywhere in the world using our Internet-of-Things platform - Adafruit IO.

Figure 1a

This project can be done with either Arduino or CircuitPython, too!

Figure 2

Parts

We'll need a Feather HUZZAH and a handful of sensors to build our own environmental monitor.

Monitor Enclosure

If you'd like to enclosure your environmental monitor, consider picking up the following parts:

  • Small Plastic Project Enclosure - Weatherproof with Clear Top
  • 1 x Cable Gland: Cable Gland PG-7 size - 0.118" to 0.169" Cable Diameter
  • 4 x Stranded-Core Wire - 2m 26AWG

Adafruit IO Setup

After logging into Adafruit IO, click the VIEW AIO KEY button on the left-sidebar.

Figure 3

A window will pop up with your Adafruit IO key and username. Keep a copy of them in a safe place, we'll need it later.

Figure 4

Create Feeds

We're going to have a lot of sources of data. Our three sensors generate seven different types of data.

Luckily for us, Adafruit IO is excellent at tracking data. It keeps data in elements called Feeds, with one feed per each unique source of data.

If you do not know how to create feeds, head over to the Adafruit IO Basics: Feeds for a quick overview of this process.

We're going to create seven unique feeds to hold and display data generated by the BME280, SGP30, and VEML6070 sensors:

  • temperature
  • humidity
  • pressure
  • altitude
  • uv
  • tvoc
  • ecO2

Figure 5

IO+ Only

If you have Adafruit IO Plus (unlimited feeds), we'll set up seven additional feeds which will be used to specify what will be displayed using icon blocks:

  • temperature-block
  • humidity-block
  • pressure-block
  • altitude-block
  • uv-block
  • tvoc-block
  • ecO2-block

Create a Dashboard

Now that we have feeds to hold data and display the type of data, we need a way to consolidate these feeds in one place. Dashboards are a feature of Adafruit IO which allow us to display and control feeds using widgets called Blocks.

We're going to navigate to the Dashboards page and click Create a new Dashboard. You can name it anything you'd like but we'll name it Environmental Monitor.

Figure 6

Adding Icon Blocks

Blocks are widgets which you can add to your dashboard. We're going to first add some icon blocks, a new type of output block which displays an icon specified by a feed.

On the dashboard, click the green plus icon to add a new block. Click on the Icon Block to configure it:

Figure 7

We'll select the temperature-block feed we created earlier:

Figure 8

Next, we're going to configure the color of the block, and pick an icon type. We're using w:thermometer for the temperature block, but you can pick any icon on the Icons FAQ page. You can also configure the color of the icon using the color-picker from the Block Settings.

Figure 9

After adding the block to the dashboard, you'll notice there's no icon on the dashboard. That's because the feed is currently empty - there's no icon to display.

Let's fix that by specifying an icon for the feed. Navigate to the Feeds page and click on the temperature-block feed. From the feed, we're going to click Actions -> Add Data and add a the value w:thermometer to set the icon block on the dashboard.

Figure 10

If you navigate back to the dashboard, you'll notice the thermometer icon is now displayed. We're going to repeat this process for each feed we'd like to display.

We set up a dashboard using the following icons, but you can use anything from the Icon Listing page you'd like:

  • Humidity, by setting the feed value to w:humidity
  • Temperature, w:thermometer
  • Pressure, w:barometer
  • Altitude, bar-chart
  • eCO2, w:smoke
  • TVOC, tvoc-icon
  • UV, uv-feed-block

Our dashboard uses the values above. We also added two histogram blocks to take a peek at some of the values over an hour.

Figure 11

Adding Text Blocks

The icon block is a great way to graphically display what types of data are associated with a feed. We need a way to add the data from the sensors. To do this, we'll need to add seven text blocks to hold feeds for our sensor data.

Let's start by creating a text block to hold the temperature data from the BME280 sensor. From the dashboard, add a block and select the text block.

Figure 12

Choose the data feed (we're going to use the temperature feed) to display:

Figure 13

Then, select a large font size.

Figure 14

Repeat this for the humidity, pressure, altitude, temperature, uv, tvoc, and eco2 feeds.

While you can't "see" them on the background (since those feeds are currently empty), we can view them by clicking the green gear on the dashboard.

Figure 15

The outlines of the text blocks should now be visible. Reorganize the blocks however you'd like - we can always change them later.

Figure 16

Next, let's wire everything up!

Arduino Wiring and Assembly

Wiring

We will be connecting multiple I2C devices to a single I2C controller using only two wires - SCL and SDA.

Figure 17

Make the following connections between the Adafruit Feather Huzzah and the BME280:

  • Feather 3V to BME280 Vin
  • Feather GND to BME280 GND
  • Feather SCL to BME280 SCK
  • Feather SDI to BME280 SDI

Make the following connections between the BME280 and the SGP30:

  • BME280 SCK to SGP30 SCL
  • BME280 SDI to SGP30 SDA
  • Feather 3V to SGP30 Vin
  • Feather GND to SGP30 GND

Make the following connections between the VEML6070 and the SGP30

  • SGP30 SCL to VEML6070 SCL
  • SGP30 SDA to VEML6070 SDA
  • Feather 3V to VEML6070 Vin
  • Feather GND to VEML6070 GND

Assembly

If you'd like to make this portable using the Adafruit Featherwing Proto and a project enclosure, we have some great news, You can fit all the sensors on the FeatherWing Proto. The wiring between the sensors and the feather are identical to the connections made above.

Note: The ACK pin for the VEML6070 is unused, so we're going to hang it off the side so we can fit everything on the board.

Figure 18

The small plastic project enclosure is the perfect size for a feather and a medium-sized LiPo battery. It's also rugged and has a waterproof gasket seal.

Connect the Feather Huzzah's JST port to a lipo battery using the included JST connector on the battery:

Figure 19

Next, we're going to test-fit the feather and the lipo battery in the project enclosure. Use a non-permanent marker to outline the positions of the battery and the feather on the bottom of the case.

Figure 20

Put the lid on the box and screw it down to ensure everything fits correctly. Use a ruler and a marker to mark locations for holes on the plastic lid of your project box. Be sure to mark the locations closer to the sensors.

Figure 21

Let's drill some holes! I used a rotary tool with a 4mm drill bit mounted to a drill press. Be sure to hold the lid tightly, use a low RPM on your tool, and watch your fingers!

Figure 22

Next, we're going to attach a cable gland to seal off the USB cable from the elements. Drill a 5/8" hole on the side of the enclosure where the Feather HUZZAH's USB port is located. The cable gland has integrated screw threads - twist it into the hole you drilled and attach the retaining nut.

Figure 23

You'll need to cut and splice the Micro USB cable to fit it into the enclosure through the cable gland. Plug a Micro-USB cable into the Feather HUZZAH and your computer. The green CHG LED should turn on to indicate the lipo is charging.

Figure 24

Next, we're going to load the environmental monitoring code on your Feather.

Arduino Setup

You should first go through the setup guide associated with your selected hardware, and make sure you have internet connectivity before continuing. The following links will take you to the guides for your selected platform:

To read sensor data from the SGP30, you will need to install the Adafruit_SGP30 library (code on our github repository). It is available from the Arduino library manager so we recommend using that.

From the Arduino IDE, open the Library Manager

Figure 25

Enter Adafruit MQTT into the search box, and click Install on the Adafruit MQTT library option to install version 0.20.2 or higher.

Figure 26

Enter ArduinoHttpClient into the search box, and click Install on the ArduinoHttpClient library option to install version 0.3.0 or higher.

Figure 27

If you haven't installed our Adafruit IO Arduino Library or if you have an older version of this library, you will need to make sure you install version 2.7.15 of the Adafruit IO Arduino library installed before continuing:

Figure 28

Type in Adafruit SGP30 to search for the library. Click Install.

Figure 29

Next, we're going to install the Adafruit BME280 Sensor Library. In the Library Manager, type in Adafruit BME280 to search for the library. Click Install.

Figure 30

Finally, we'll install the Adafruit VEML6070 library. In the Library Manager, type in Adafruit VEML6070 to search for the library. Then, click Install.

Figure 31

The code for this learn guide is contained within the Adafruit IO Arduino Library's examples.

To open it from the Arduino IDE, navigate to: File -> Examples -> Adafruit IO Arduino -> adafruitio_22_environmental_monitor

Figure 32

At this point, you should see two tabs open on your Arduino IDE: adafruitio_22_environmental_monitor and config.h

Figure 33

Next, we're going to configure our Feather for use with Adafruit IO.

Arduino Network Config

To configure the network settings, click on the config.h tab in the sketch. You will need to set your Adafruit IO username in the IO_USERNAME define, and your Adafruit IO key in the IO_KEY define.

Figure 34

WiFi Config

WiFi is enabled by default in config.h so if you are using one of the supported WiFi boards, you will only need to modify the WIFI_SSID and WIFI_PASS options in the config.h tab.

Figure 35

FONA Config

If you wish to use the FONA 32u4 Feather to connect to Adafruit IO, you will need to first comment out the WiFi support in config.h

Figure 36

Next, remove the comments from both of the FONA config lines in the FONA section of config.h to enable FONA support.

Figure 37

Ethernet Config

If you wish to use the Ethernet Wing to connect to Adafruit IO, you will need to first comment out the WiFi support in config.h

Figure 38

Next, remove the comments from both of the Ethernet config lines in the Ethernet section of config.h to enable Ethernet Wing support.

Figure 39

Next, we will look at how the example sketch works.

Arduino Code

The code waits ten seconds between sensor reads and publishing to Adafruit IO. We can adjust this by increasing or decreasing the READ_DELAY variable at the top of our code.

Copy Code
// Delay between sensor reads, in seconds
#define READ_DELAY 10

The next chunk of code sets up feed instances to hold the data produced by the sensors.

Copy Code
// set up the feeds for the BME280
AdafruitIO_Feed *temperatureFeed = io.feed("temperature");
AdafruitIO_Feed *humidityFeed = io.feed("humidity");
AdafruitIO_Feed *pressureFeed = io.feed("pressure");
AdafruitIO_Feed *altitudeFeed = io.feed("altitude");
// set up feed for the VEML6070
AdafruitIO_Feed *uvFeed = io.feed("uv");
// set up feeds for the SGP30
AdafruitIO_Feed *tvocFeed = io.feed("tvoc");
AdafruitIO_Feed *ecO2Feed = io.feed("ecO2");

In the setup function, we make calls to setupBME280() and setupSGP30(), which set up both of these sensors. We're also going to set up the VEML6070 by calling uv.begin(), then connect to Adafruit IO. The code will wait until you have a valid connection to Adafruit IO before continuing with the sketch.

If you have any issues connecting, check config.h for any typos in your username, key, or WiFi credentials.

Copy Code
void setup() {
// start the serial connection
Serial.begin(9600);

// wait for serial monitor to open
while (!Serial);

Serial.println("Adafruit IO Environmental Logger");

// set up BME280
setupBME280();
// set up SGP30
setupSGP30();
// setup VEML6070
uv.begin(VEML6070_1_T);

// connect to io.adafruit.com
Serial.print("Connecting to Adafruit IO");
io.connect();

// wait for a connection
while (io.status() < AIO_CONNECTED)
{
Serial.print(".");
delay(500);
}

// we are connected
Serial.println();
Serial.println(io.statusText());
}

The code inside the loop() obtains values from the sensors and saves their current state. The SGP30 sometimes fails on read (due to timing). If this occurs, we'll set the measurements of tvocReading and ECO2Reading to -1 so we can catch this type of error in our dashboard.

Copy Code
Serial.println("Reading Sensors...");

// Read the temperature from the BME280
temperatureReading = bme.readTemperature();

// convert from celsius to degrees fahrenheit
temperatureReading = temperatureReading * 1.8 + 32;

Serial.print("Temperature = "); Serial.print(temperatureReading); Serial.println(" *F");

// Read the pressure from the BME280
pressureReading = bme.readPressure() / 100.0F;
Serial.print("Pressure = "); Serial.print(pressureReading); Serial.println(" hPa");

// Read the altitude from the BME280
altitudeReading = bme.readAltitude(SEALEVELPRESSURE_HPA);
Serial.print("Approx. Altitude = "); Serial.print(altitudeReading); Serial.println(" m");

// Read the humidity from the BME280
humidityReading = bme.readHumidity();
Serial.print("Humidity = "); Serial.print(humidityReading); Serial.println("%");

// VEML6070
uvReading = uv.readUV();
Serial.print("UV Light Level: "); Serial.println(uvReading);
if(! sgp.IAQmeasure()){
tvocReading = -1;
ecO2Reading = -1;
} else {
tvocReading = sgp.TVOC;
ecO2Reading = sgp.eCO2;
}

The final chunk of the loop() function sends sensor data to the feeds associated with that data. We also delay the polled loop to wait for the temperature to change.

Copy Code
  // send data to Adafruit IO feeds
temperatureFeed->save(temperatureReading);
humidityFeed->save(humidityReading);
altitudeFeed->save(altitudeReading);
pressureFeed->save(pressureReading);
uvFeed->save(uvReading);
ecO2Feed->save(ecO2Reading);
tvocFeed->save(tvocReading);

 

Upload the sketch to your board and open the Arduino Serial Monitor (Tools -> Serial Monitor). You should see the board connecting to Adafruit IO, obtain sensor readings, and send them to Adafruit IO:

Copy Code
Adafruit IO Environmental Logger
BME Sensor is set up!
Found SGP30 serial #064F41A
Connecting to Adafruit IOAdafruitIO::connect()
.
Adafruit IO connected.
Reading Sensors...
Temperature = 82 *F
Pressure = 1006 hPa
Approx. Altitude = 56 m
Humidity = 43%
UV Light Level: 3
TVOC: 0 ppb eCO2: 400 ppm

 

Check your Dashboard on Adafruit IO and you should see your dashboard populated with values. You should also see them change every ten seconds.

Figure 40

Python Wiring and Assembly

Figure 41

We're going to make an environmental monitor using a Raspberry Pi Zero W and a Perma Proto Bonnet. We'll wire it up, build an enclosure for it, install dependencies, and program it with Python & CircuitPython

The Pi Zero W has built-in WiFi - which is great for connecting our environmental monitor to Adafruit IO. It's also smaller than a regular Raspberry Pi 3, making it the perfect size to bring with you (monitor the air in the subway station) or stick it in a small corner of your room.

We're going to be building our own pHAT for monitoring environmental data by using a Perma Proto Bonnet.

Wiring

First, solder the included 20x2 GPIO Header to the Perma Proto Bonnet

Figure 42

We will be connecting multiple I2C devices to a single I2C controller using only two wires - SCL and SDA.

Figure 43

Note: The SDA and SCL lines are located at the top- of the Proto-Bonnet and do not run down the side.

Make the following connections between the Raspberry Pi and the VEML6070:

  • Pi 3V to VEML6070 Vin
  • Pi GND to VEML6070 GND
  • Pi SCL to VEML6070 SCK
  • Pi SDI to VEML6070 SDI

Make the following connections between the VEML6070 and the SGP30:

  • VEML6070 SCL to SGP30 SCL
  • VEML6070 SDA to SGP30 SDA
  • Pi 3V to SGP30 Vin
  • Pi GND to SGP30 GND

Make the following connections between the SGP30 and the BME280:

  • VEML 6070 SCL to BME280 SCK
  • VEML 6070 SDA to BME280 SDI
  • Pi 3V to VEML6070 Vin
  • Pi GND to VEML6070 GND

Assembly

The small plastic project enclosure is the perfect size for a Pi Zero W and Environmental Logger Bonnett.

  • Small Plastic Project Enclosure - Weatherproof with Clear Top

We're going to test-fit the Pi in the project enclosure. Use a non-permanent marker to outline the positions of the Pi on the bottom of the case.

Figure 44

Put the lid on the box and screw it down to ensure everything fits correctly. Use a ruler and a marker to mark locations for holes on the plastic lid of your project box. Be sure to mark the locations closer to the sensors.

Figure 45

Let's drill some holes! I used a rotary tool with a 4mm drill bit mounted to a drill press. Be sure to hold the lid tightly, use a low RPM on your tool, and watch your fingers!

Figure 46

Next, let's set up our Raspberry Pi to be used with both CircuitPython and our sensors.

Next, we're going to attach a cable gland to seal off the USB cable from the elements. Drill a 5/8" hole on the side of the enclosure where the Pi's USB port is located. The cable gland has integrated screw threads - twist it into the hole you drilled and attach the retaining nut.

You'll need to cut and splice the Micro USB cable to fit it into the enclosure through the cable gland. Plug a Micro-USB cable into the Pi Zero W.

Making it Portable

If you want to take your Environmental Monitor on-the-go, you might want to add a Rechargeable USB Battery Pack. We used a smaller rechargeable model with a 2200mAh capacity. Charge up your battery pack, and then plug it into the Pi's PWR_IN port.

Python Setup

If you're following along with a Raspberry Pi, Beaglebone or any other supported small linux computer, we'll use a special library called adafruit_blinka (named after Blinka, the CircuitPython mascot) to provide the layer that translates the CircuitPython hardware API to whatever library the Linux board provides. It's CircuitPython, on Pi!

If you haven't set up Blinka and the Adafruit IO Python Library yet on your Raspberry Pi, follow our guide:

Enable I2C

We use two pins on the Pi (SDA/SCL) to communicate over I2c with the PCA9685. You only have to do this step once per Raspberry Pi, the I2C interface is disabled by default.

Once you're done with this and have rebooted, verify you have the SPI devices with the command:

sudo i2cdetect -y 1

The output from running this command should look like the following:

Figure 47

Installing required CircuitPython Libraries

You'll need libraries to communicate with the VEML6070, SGP30, and BME280 sensors. Since we're using Adafruit Blinka (CircuitPython), we can install CircuitPython libraries straight to our Raspberry Pi.

Run the following command from your terminal to install the  Adafruit_CircuitPython_VEML6070 Library:

sudo pip3 install adafruit-circuitpython-veml6070

Next, install the Adafruit_CircuitPython_SGP30 library

sudo pip3 install adafruit-circuitpython-sgp30

Then, install the Adafruit_CircuitPython_BME280 library

sudo pip3 install adafruit-circuitpython-bme280

Python Code

First, we're going to import the libraries used by our code to read sensor values, use CircuitPython on our Pi, and read/write to Adafruit IO using the REST client.

Copy Code
# Import standard python modules
import time

# import Adafruit Blinka
import board
import busio

# import sensor libraries
import adafruit_sgp30
import adafruit_veml6070
import adafruit_bme280

# import Adafruit IO REST client
from Adafruit_IO import Client, Feed, RequestError

Next, we'll set up our code with our Adafruit IO username and secret key. If you need these values, navigate to your Adafruit IO profile. We'll also create an instance of the REST client with these values.

Copy Code
# Set to your Adafruit IO key.
# Remember, your key is a secret,
# so make sure not to publish it when you publish this code!
ADAFRUIT_IO_KEY = 'YOUR_AIO_KEY'

# Set to your Adafruit IO username.
# (go to https://accounts.adafruit.com to find your username)
ADAFRUIT_IO_USERNAME = 'YOUR_AIO_USERNAME'

# Create an instance of the REST client
aio = Client(ADAFRUIT_IO_USERNAME, ADAFRUIT_IO_KEY)

The code next assigns feeds, or creates and assigns them. Then, we create an I2C busio object and create objects for the VEML6070, BME280, and SGP30 sensors.

Copy Code
# Create busio I2C
i2c = busio.I2C(board.SCL, board.SDA, frequency=100000)
# Create VEML6070 object.
uv = adafruit_veml6070.VEML6070(i2c)
# Create BME280 object.
bme280 = adafruit_bme280.Adafruit_BME280_I2C(i2c)
bme280.sea_level_pressure = 1013.25
# Create SGP30 object using I2C.
sgp30 = adafruit_sgp30.Adafruit_SGP30(i2c)
sgp30.iaq_init()
sgp30.set_iaq_baseline(0x8973, 0x8aae)

in the while True loop, we read data from the SGP30, VEML6070, and the BME280. The VEML6070 samples ten times before arriving at a final data.

Copy Code
    # Read SGP30.
eCO2_data = sgp30.co2eq
tvoc_data = sgp30.tvoc

# Read VEML6070, sample ten times.
for j in range(10):
uv_data = uv.read

# Read BME280.
temp_data = bme280.temperature
# convert temperature (C->F)
temp_data = int(temp_data) * 1.8 + 32
humid_data = bme280.humidity
pressure_data = bme280.pressure
alt_data = bme280.altitude

Then, we send our data to Adafruit IO. Since we'll be sending a lot of data to our feeds, we added a pause between sending each sensor's data to its corresponding Adafruit IO Feeds.

Copy Code
 # Send SGP30 Data to Adafruit IO.
print('eCO2:', eCO2_data)
aio.send(eCO2_feed.key, eCO2_data)
print('tvoc:', tvoc_data)
aio.send(tvoc_feed.key, tvoc_data)
time.sleep(SENSOR_DELAY)

Finally, we wait for LOOP_DELAY minutes. If you want to report data more quickly or slowly, adjust the LOOP_DELAY variable at the start of the code.

Make sure you have your Adafruit IO Username and Key set up and that your Pi is connected to the internet. Then, enter the following in your terminal to run the code:

python3 environmental_monitor.py

You should see the following output in your terminal:

Copy Code
Reading sensors...
sending data to adafruit io...
eCO2: 400
tvoc: 0
UV Level: 3
Temperature: 75.2 C
Humidity: 54.8 %
Pressure: 1008.1 hPa
Altitude = 42.68 meters

Your dashboard should populate with values. Note that it will take the SGP30 at least ten reads before it obtains a baseline measurement.

Figure 48

Code

Copy Code
"""
'environmental_monitor.py'
===============================================================================
Example of sending I2C sensor data
from multiple sensors to Adafruit IO.

Tutorial Link: https://learn.adafruit.com/adafruit-io-air-quality-monitor

Adafruit invests time and resources providing this open source code.
Please support Adafruit and open source hardware by purchasing
products from Adafruit!

Author(s): Brent Rubell for Adafruit Industries
Copyright (c) 2018 Adafruit Industries
Licensed under the MIT license.
All text above must be included in any redistribution.

Dependencies:
- Adafruit_Blinka (CircuitPython, on Pi.)
(https://github.com/adafruit/Adafruit_Blinka)
- Adafruit_CircuitPython_SGP30.
(https://github.com/adafruit/Adafruit_CircuitPython_SGP30)
- Adafruit_CircuitPython_VEML6070.
(https://github.com/adafruit/Adafruit_CircuitPython_VEML6070)
- Adafruit_CircuitPython_BME280.
(https://github.com/adafruit/Adafruit_CircuitPython_BME280)
"""

# Import standard python modules
import time

# import Adafruit Blinka
import board
import busio

# import sensor libraries
import adafruit_sgp30
import adafruit_veml6070
import adafruit_bme280

# import Adafruit IO REST client
from Adafruit_IO import Client, Feed, RequestError

# loop timeout, in seconds.
LOOP_DELAY = 10

# Set to your Adafruit IO key.
# Remember, your key is a secret,
# so make sure not to publish it when you publish this code!
ADAFRUIT_IO_KEY = 'YOUR_AIO_KEY'

# Set to your Adafruit IO username.
# (go to https://accounts.adafruit.com to find your username)
ADAFRUIT_IO_USERNAME = 'YOUR_AIO_USERNAME'

# Create an instance of the REST client
aio = Client(ADAFRUIT_IO_USERNAME, ADAFRUIT_IO_KEY)

try: # if we already have the feeds, assign them.
tvoc_feed = aio.feeds('tvoc')
eCO2_feed = aio.feeds('eco2')
uv_feed = aio.feeds('uv')
temperature_feed = aio.feeds('temperature')
humidity_feed = aio.feeds('humidity')
pressure_feed = aio.feeds('pressure')
altitude_feed = aio.feeds('altitude')
except RequestError: # if we don't, create and assign them.
tvoc_feed = aio.create_feed(Feed(name='tvoc'))
eCO2_feed = aio.create_feed(Feed(name='eco2'))
uv_feed = aio.create_feed(Feed(name='uv'))
temperature_feed = aio.create_feed(Feed(name='temperature'))
humidity_feed = aio.create_feed(Feed(name='humidity'))
pressure_feed = aio.create_feed(Feed(name='pressure'))
altitude_feed = aio.create_feed(Feed(name='altitude'))

# Create busio I2C
i2c = busio.I2C(board.SCL, board.SDA, frequency=100000)
# Create VEML6070 object.
uv = adafruit_veml6070.VEML6070(i2c)
# Create BME280 object.
bme280 = adafruit_bme280.Adafruit_BME280_I2C(i2c)
bme280.sea_level_pressure = 1013.25
# Create SGP30 object using I2C.
sgp30 = adafruit_sgp30.Adafruit_SGP30(i2c)
sgp30.iaq_init()
sgp30.set_iaq_baseline(0x8973, 0x8aae)

# Sample VEML6070
def sample_VEML():
for j in range(10):
uv_raw = uv.read
return uv_raw


while True:
print('Reading sensors...')
# Read SGP30.
eCO2_data = sgp30.co2eq
tvoc_data = sgp30.tvoc

# Read VEML6070.
uv_data = sample_VEML()

# Read BME280.
temp_data = bme280.temperature
# convert temperature (C->F)
temp_data = int(temp_data) * 1.8 + 32
humid_data = bme280.humidity
pressure_data = bme280.pressure
alt_data = bme280.altitude

print('sending data to adafruit io...')
# Send SGP30 Data to Adafruit IO.
print('eCO2:', eCO2_data)
aio.send(eCO2_feed.key, eCO2_data)
print('tvoc:', tvoc_data)
aio.send(tvoc_feed.key, tvoc_data)
time.sleep(2)
# Send VEML6070 Data to Adafruit IO.
print('UV Level: ', uv_data)
aio.send(uv_feed.key, uv_data)
time.sleep(2)
# Send BME280 Data to Adafruit IO.
print('Temperature: %0.1f C' % temp_data)
aio.send(temperature_feed.key, temp_data)
print("Humidity: %0.1f %%" % humid_data)
aio.send(humidity_feed.key, int(humid_data))
time.sleep(2)
print("Pressure: %0.1f hPa" % pressure_data)
aio.send(pressure_feed.key, int(pressure_data))
print("Altitude = %0.2f meters" % alt_data)
aio.send(altitude_feed.key, int(alt_data))
# avoid timeout from adafruit io
time.sleep(LOOP_DELAY * 60)

 

Key Parts and Components

Add all Digi-Key Parts to Cart
  • 1528-1530-ND
  • 1528-1359-ND
  • 1528-2531-ND
  • 1528-1694-ND
  • 1528-1622-ND
  • 1528-1838-ND
  • 1528-2013-ND
  • 1528-1622-ND
  • 1528-1857-ND
  • 1528-2041-ND
  • 1528-2181-ND
  • 1528-1580-ND
  • 1528-1653-ND
  • 1910-1000-ND