# BMP280 weather station with pressure trend and altitude on Arduino: design worksheet and code

> A ₹1,160 design worksheet for a small weather station: temperature, pressure, altitude from the barometric formula and a three-hour pressure trend, with the pressure-to-height table worked out.

Canonical: https://roboticsengineering.in/projects/bmp280-weather-station-pressure-trend-arduino/ | Published: 2026-11-04 | Updated: 2026-11-04

**A ₹1,160 weather station that reads temperature and air pressure and tells you whether pressure is rising or falling. A BMP280 sensor does the measuring, an OLED shows it, and the sketch keeps a three-hour history so a falling trend can be flagged. The page shows how pressure converts to height, and why that same maths means weather moves your altitude readings.**

**Scope:** intermediate. This is a design worksheet with illustrative costs. It has not been bench-tested by this site. The table was computed by script from the standard barometric formula. A BMP280 measures temperature and pressure only; it has no humidity sensor (the BME280 does). Falling pressure often goes with unsettled weather, but this is a hint, not a forecast, and the page makes no forecasting claims. Pressure readings also depend on correct mounting away from heat.

## How it works

The standard barometric formula gives height from pressure: h = 44330 × (1 − (p / p0)^0.1903), with p0 = 1013.25 hPa at sea level. 1000 hPa works out near 111 m, 950 hPa near 540 m, 900 hPa near 989 m and 850 hPa near 1,457 m. As a rule of thumb pressure falls about 1 hPa for every 8 to 9 m near sea level.

Weather changes pressure too, by tens of hectopascals over days, which moves the computed altitude by hundreds of metres. For that reason the altitude is treated as relative only. The sketch stores one pressure reading every 30 minutes in a six-slot array and compares newest with oldest to show a three-hour trend.

## Bill of materials

| Part | Qty | Unit | Total |
| --- | --- | --- | --- |
| Arduino Uno R3 (or compatible) | 1 | ₹550 | ₹550 |
| BMP280 breakout (I2C, 3.3 V logic board) | 1 | ₹150 | ₹150 |
| 0.96 inch I2C OLED, SSD1306 | 1 | ₹250 | ₹250 |
| Breadboard | 1 | ₹60 | ₹60 |
| Jumper wires | 1 | ₹50 | ₹50 |
| Project box with vent holes | 1 | ₹100 | ₹100 |
| Parts total | ₹1,160 |  |  |

Scroll the table sideways to see every column.

Prices checked Nov 2026. Shipping and tools are not included.

Prices are illustrative figures for Indian sellers in November 2026, before shipping, and have not been checked against current listings.

## The numbers

| Pressure | Height by the formula |
| --- | --- |
| 1013.25 hPa | 0 m |
| 1000 hPa | 111 m |
| 950 hPa | 540 m |
| 900 hPa | 989 m |
| 850 hPa | 1458 m |

*h = 44330 × (1 − (p / 1013.25)^0.1903). Standard-atmosphere approximation; weather shifts the real value.*

The trend bands in the sketch (more than 1 hPa up or down over three hours) are rough conventions, not tuned values and not a guarantee of any weather.

## Power and wiring

| Part | Connects to | Note |
| --- | --- | --- |
| BMP280 VCC and GND | 3.3V and GND | Many breakouts also accept 5 V; check yours |
| BMP280 SDA / SCL | A4 / A5 | Address 0x76 or 0x77 |
| OLED VCC and GND | 5V or 3.3V and GND | Check the board |
| OLED SDA / SCL | A4 / A5 | Shares the I2C bus, address 0x3C |

*Mount the sensor in shade, away from the Arduino and any regulator, because self-heating biases the temperature.*

## The sketch

```
// BMP280 weather station: Uno + BMP280 + SSD1306 OLED
// Design worksheet: libraries are Adafruit_BMP280, Adafruit_SSD1306, Adafruit_GFX.

#include <Wire.h>
#include <Adafruit_BMP280.h>
#include <Adafruit_SSD1306.h>

Adafruit_BMP280 bmp;
Adafruit_SSD1306 oled(128, 64, &Wire, -1);

const unsigned long SAMPLE_MS = 1800000UL;     // one reading per 30 minutes
float history[6];
int count = 0;
unsigned long lastSample = 0;

void setup() {
  Serial.begin(9600);
  if (!bmp.begin(0x76)) { Serial.println("BMP280 not found (try 0x77)"); while (true) {} }
  oled.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  oled.setTextColor(WHITE);
  lastSample = millis() - SAMPLE_MS;            // sample straight away
}

void loop() {
  float t = bmp.readTemperature();              // degrees C
  float p = bmp.readPressure() / 100.0;         // hPa
  float h = 44330.0 * (1.0 - pow(p / 1013.25, 0.1903));

  if (millis() - lastSample >= SAMPLE_MS) {
    lastSample = millis();
    if (count < 6) history[count++] = p;
    else { for (int i = 0; i < 5; i++) history[i] = history[i + 1]; history[5] = p; }
  }

  const char* trend = "collecting";
  if (count == 6) {
    float d = history[5] - history[0];
    trend = d > 1.0 ? "rising" : (d < -1.0 ? "falling" : "steady");
  }

  oled.clearDisplay();
  oled.setTextSize(1);
  oled.setCursor(0, 0);  oled.print("Temp  "); oled.print(t, 1); oled.print(" C");
  oled.setCursor(0, 14); oled.print("Press "); oled.print(p, 1); oled.print(" hPa");
  oled.setCursor(0, 28); oled.print("Alt   "); oled.print(h, 0); oled.print(" m (rel)");
  oled.setCursor(0, 42); oled.print("3h    "); oled.print(trend);
  oled.display();
  delay(2000);
}
```

The history is lost when the board resets, so the trend takes about three hours to appear after every power-up; storing readings in EEPROM would fix that. The library address defaults to 0x77, which is why the sketch passes 0x76; use whichever your board needs. The sketch has been proofread but not compiled on this site.

## Test plan

1. **Sensor check:** print temperature and pressure and compare with a phone weather app for your town (expect a few hectopascals of difference unless you adjust for height).
2. **Height change:** carry it up a few floors and watch the altitude rise by about 3 m per floor.
3. **Self-heating:** compare readings near and far from the Arduino.
4. **Trend:** shorten SAMPLE_MS to one minute and move the sensor to confirm the maths runs.
5. **Drift:** log pressure over a week and compare with a published station nearby.
6. **Power cycle:** reset the board and note that the trend restarts.

## What usually goes wrong

| Symptom | Likely cause | Fix |
| --- | --- | --- |
| BMP280 not found | Wrong address or SDA/SCL swapped | Try 0x77, check wiring, run an I2C scanner |
| Temperature reads high | Self-heating from nearby parts | Move the sensor away and shade it |
| Altitude wanders | Weather changes pressure | Use altitude as relative only |
| Pressure far off | Sensor damaged by water or flux | Replace and keep it dry |
| OLED blank | Wrong address | Use 0x3C or 0x3D |

## Upgrades

- **BME280:** a humidity-capable sensor adds dew point.
- **EEPROM history:** keep the trend across resets.
- **Wi-Fi upload:** move to an ESP32 and post to a dashboard.
- **Rain gauge:** add a tipping bucket and count tips.

## Cost and parts notes

The ₹1,160 total is an illustration and does not include shipping. Use the [cost calculator](https://roboticsengineering.in/robotics-project-cost-calculator/) to compare sellers.

## Common questions

**What is the difference between BMP280 and BME280?**

The BME280 adds a humidity sensor; the BMP280 measures only pressure and temperature.

**Why does altitude change with weather?**

The formula assumes standard sea-level pressure; real weather moves it by tens of hectopascals.

**Is the trend a forecast?**

No. It shows pressure movement, which is only a hint about weather.

**Why shade the sensor?**

Sunlight and nearby electronics warm it and bias the temperature.

Last reviewed: November 2026. This is a design worksheet with illustrative costs. It has not been bench-tested by this site; library names, pins and limits must be checked against your board and the current library versions, and measurements from your build are welcome.
