Barometric Pressure Sensor (SPI)
Read air pressure and temperature from a sensor using the SPI protocol.
Last revision 2018/05/17 by SM
This example shows how to use the SPI (Serial Peripheral Interface) Communications Library to read data from a SCP1000 Barometric Pressure sensor.
Hardware Required
- Arduino board
- SCP1000 Pressure Sensor Breakout Board
- hook-up wires
Circuit
Schematic
The SCP1000 barometric pressure sensor can read both air pressure and temperature and report them via the SPI connection. For details of the control registers, see the SCP1000 data sheet.
Code
The code below starts out by setting the SCP1000's configuration registers in the
setup()
. In the main loop, it sets the sensor to read in high resolution mode, meaning that it will return a 19-bit value, for the pressure reading, and 16 bits for the temperature. The actual reading in degrees Celsius is the 16-bit result divided by 20.Then it reads the temperature's two bytes. Once it's got the temperature, it reads the pressure in two parts. First it reads the highest three bits, then the lower 16 bits. It combines these two into one single long integer by bit shifting the high bits then using a bitwise OR to combine them with the lower 16 bits. The actual pressure in Pascal is the 19-bit result divide by 4.
1/*2
3 SCP1000 Barometric Pressure Sensor Display4
5 Shows the output of a Barometric Pressure Sensor on a6
7 Uses the SPI library. For details on the sensor, see:8
9 http://www.sparkfun.com/commerce/product_info.php?products_id=816110
11 http://www.vti.fi/en/support/obsolete_products/pressure_sensors/12
13 This sketch adapted from Nathan Seidle's SCP1000 example for PIC:14
15 http://www.sparkfun.com/datasheets/Sensors/SCP1000-Testing.zip16
17 Circuit:18
19 SCP1000 sensor attached to pins 6, 7, 10 - 13:20
21 DRDY: pin 622
23 CSB: pin 724
25 MOSI: pin 1126
27 MISO: pin 1228
29 SCK: pin 1330
31 created 31 July 201032
33 modified 14 August 201034
35 by Tom Igoe36
37 */38
39// the sensor communicates using SPI, so include the library:40#include <SPI.h>41
42//Sensor's memory register addresses:43
44const int PRESSURE = 0x1F; //3 most significant bits of pressure45
46const int PRESSURE_LSB = 0x20; //16 least significant bits of pressure47
48const int TEMPERATURE = 0x21; //16 bit temperature reading49
50const byte READ = 0b11111100; // SCP1000's read command51
52const byte WRITE = 0b00000010; // SCP1000's write command53
54// pins used for the connection with the sensor55// the other you need are controlled by the SPI library):56
57const int dataReadyPin = 6;58
59const int chipSelectPin = 7;60
61void setup() {62
63 Serial.begin(9600);64
65 // start the SPI library:66
67 SPI.begin();68
69 // initialize the data ready and chip select pins:70
71 pinMode(dataReadyPin, INPUT);72
73 pinMode(chipSelectPin, OUTPUT);74
75 //Configure SCP1000 for low noise configuration:76
77 writeRegister(0x02, 0x2D);78
79 writeRegister(0x01, 0x03);80
81 writeRegister(0x03, 0x02);82
83 // give the sensor time to set up:84
85 delay(100);86}87
88void loop() {89
90 //Select High Resolution Mode91
92 writeRegister(0x03, 0x0A);93
94 // don't do anything until the data ready pin is high:95
96 if (digitalRead(dataReadyPin) == HIGH) {97
98 //Read the temperature data99
100 int tempData = readRegister(0x21, 2);101
102 // convert the temperature to celsius and display it:103
104 float realTemp = (float)tempData / 20.0;105
106 Serial.print("Temp[C]=");107
108 Serial.print(realTemp);109
110 //Read the pressure data highest 3 bits:111
112 byte pressure_data_high = readRegister(0x1F, 1);113
114 pressure_data_high &= 0b00000111; //you only needs bits 2 to 0115
116 //Read the pressure data lower 16 bits:117
118 unsigned int pressure_data_low = readRegister(0x20, 2);119
120 //combine the two parts into one 19-bit number:121
122 long pressure = ((pressure_data_high << 16) | pressure_data_low) / 4;123
124 // display the temperature:125
126 Serial.println("\tPressure [Pa]=" + String(pressure));127
128 }129}130
131//Read from or write to register from the SCP1000:132unsigned int readRegister(byte thisRegister, int bytesToRead) {133
134 byte inByte = 0; // incoming byte from the SPI135
136 unsigned int result = 0; // result to return137
138 Serial.print(thisRegister, BIN);139
140 Serial.print("\t");141
142 // SCP1000 expects the register name in the upper 6 bits143
144 // of the byte. So shift the bits left by two bits:145
146 thisRegister = thisRegister << 2;147
148 // now combine the address and the command into one byte149
150 byte dataToSend = thisRegister & READ;151
152 Serial.println(thisRegister, BIN);153
154 // take the chip select low to select the device:155
156 digitalWrite(chipSelectPin, LOW);157
158 // send the device the register you want to read:159
160 SPI.transfer(dataToSend);161
162 // send a value of 0 to read the first byte returned:163
164 result = SPI.transfer(0x00);165
166 // decrement the number of bytes left to read:167
168 bytesToRead--;169
170 // if you still have another byte to read:171
172 if (bytesToRead > 0) {173
174 // shift the first byte left, then get the second byte:175
176 result = result << 8;177
178 inByte = SPI.transfer(0x00);179
180 // combine the byte you just got with the previous one:181
182 result = result | inByte;183
184 // decrement the number of bytes left to read:185
186 bytesToRead--;187
188 }189
190 // take the chip select high to de-select:191
192 digitalWrite(chipSelectPin, HIGH);193
194 // return the result:195
196 return (result);197}198
199//Sends a write command to SCP1000200
201void writeRegister(byte thisRegister, byte thisValue) {202
203 // SCP1000 expects the register address in the upper 6 bits204
205 // of the byte. So shift the bits left by two bits:206
207 thisRegister = thisRegister << 2;208
209 // now combine the register address and the command into one byte:210
211 byte dataToSend = thisRegister | WRITE;212
213 // take the chip select low to select the device:214
215 digitalWrite(chipSelectPin, LOW);216
217 SPI.transfer(dataToSend); //Send register location218
219 SPI.transfer(thisValue); //Send value to record into register220
221 // take the chip select high to de-select:222
223 digitalWrite(chipSelectPin, HIGH);224}
Suggest changes
The content on docs.arduino.cc is facilitated through a public GitHub repository. If you see anything wrong, you can edit this page here.
License
The Arduino documentation is licensed under the Creative Commons Attribution-Share Alike 4.0 license.