MJRoBot (Marcelo Rovai)
Published © GPL3+

IoT Made Simple: Home Weather Station with NodeMCU and OLED

Weather station displaying indoor temp/hum, as well as climate conditions and present day/3-day forecast.

BeginnerFull instructions provided3 hours29,249
IoT Made Simple: Home Weather Station with NodeMCU and OLED

Things used in this project

Hardware components

NodeMCU ESP8266 Breakout Board
NodeMCU ESP8266 Breakout Board
×1
0.96" I2C IIC SPI Serial 128X64 White OLED LCD LED Display Module
×1
DHT22 Temperature Sensor
DHT22 Temperature Sensor
×1
DHT11 Temperature & Humidity Sensor (4 pins)
DHT11 Temperature & Humidity Sensor (4 pins)
×1
Resistor 10k ohm
Resistor 10k ohm
×1
Breadboard (generic)
Breadboard (generic)
×1

Software apps and online services

Arduino IDE
Arduino IDE
Weather Underground

Story

Read more

Schematics

Home Weather Station Electrical Diagram

Code

Code snippet #2

Plain text
void init(); // Initialize the display

void resetDisplay(void); // Cycle through the initialisation

void displayOn(void); // Turn the display on

void displayOff(void); // Turn the display offs

void clear(void); // Clear the local pixel buffer

void invertDisplay(void); // Inverted display mode

void normalDisplay(void); // Normal display mode

void setContrast(char contrast); // Set display contrast

void flipScreenVertically(); // Turn the display upside down

Code snippet #3

Plain text
void setColor(OLEDDISPLAY_COLOR color); // Sets the color of all pixel operations

void setPixel(int16_t x, int16_t y); // Draw a pixel at given position

void drawLine(int16_t x0, int16_t y0, int16_t x1, int16_t y1); // Draw a line from position 0 to position 1

void drawHorizontalLine(int16_t x, int16_t y, int16_t length); // Draw a line horizontally

void drawVerticalLine(int16_t x, int16_t y, int16_t length); // Draw a lin vertically
 
void drawFastImage(int16_t x, int16_t y, int16_t width, int16_t height, const char *image); // Draw a bitmap in the internal image format

Code snippet #4

Plain text
void drawString(int16_t x, int16_t y, String text); // Write the text at given position

uint16_t getStringWidth(const char* text, uint16_t length); // Returns the width of the const char* with the current font settings

uint16_t getStringWidth(String text); // Convenience method for the const char version

void setTextAlignment(OLEDDISPLAY_TEXT_ALIGNMENT textAlignment); // TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER, TEXT_ALIGN_RIGHT, TEXT_ALIGN_CENTER_BOTH

void setFont(const char* fontData); // Sets the current font. 

// Available default fonts: ArialMT_Plain_10, ArialMT_Plain_16, ArialMT_Plain_24

Code snippet #5

Plain text
void init(); // Initialise the display

void setTargetFPS(uint8_t fps); //Configure the internal used target FPS

void enableAutoTransition(); //Enable automatic transition to next frame

void disableAutoTransition(); // Disable automatic transition to next frame.

void setAutoTransitionForwards(); // Set the direction if the automatic transitioning

void setAutoTransitionBackwards(); // Set the direction if the automatic transitioning

void setTimePerFrame(uint16_t time); //Set the approx. time a frame is displayed

void setTimePerTransition(uint16_t time); //Set the approx. time a transition will take

void setFrameAnimation(AnimationDirection dir); //Configure what animation is used to transition

void setFrames(FrameCallback* frameFunctions, uint8_t frameCount); //Add frame drawing functions

int8_t update();  // This needs to be called in the main loop

Code snippet #6

Plain text
/* Hello World OLED Test */

#include   // Only needed for Arduino 1.6.5 and earlier
#include "SSD1306.h" // alias for `#include "SSD1306Wire.h"`
SSD1306  display(0x3c, 5, 4); // Initialize the OLED display using Wire library

void setup() 
{
  Serial.begin(115200);
  display.init(); // Initialising the UI will init the display too.
  display.flipScreenVertically();
  
  display.clear();
  drawHelloWorld(); 
  display.display();
}

void loop() 
{
  
}

void drawHelloWorld() 
{
    display.setTextAlignment(TEXT_ALIGN_LEFT);
    display.setFont(ArialMT_Plain_10);
    display.drawString(0, 0, "Hello world");
    display.setFont(ArialMT_Plain_16);
    display.drawString(0, 10, "Hello world");
    display.setFont(ArialMT_Plain_24);
    display.drawString(0, 26, "Hello world");
}

Code snippet #8

Plain text
/* DHT22 */
#include "DHT.h"
#define DHTPIN D3  
#define DHTTYPE DHT22 
DHT dht(DHTPIN, DHTTYPE);
int localHum = 0;
int localTemp = 0;

Code snippet #9

Plain text
/***************************************************
* Get indoor Temp/Hum data
****************************************************/
void getDHT()
{
  float tempIni = localTemp;
  float humIni = localHum;
  localTemp = dht.readTemperature();
  localHum = dht.readHumidity();
  if (isnan(localHum) || isnan(localTemp))   // Check if any reads failed and exit early (to try again).
  {
    Serial.println("Failed to read from DHT sensor!");
    localTemp = tempIni;
    localHum = humIni;
    return;
  }
}

Code snippet #10

Plain text
/***************************************************
* Draw Indoor Page
****************************************************/
void drawDHT() 
{
  int x=0;
  int y=0;
  display.setFont(ArialMT_Plain_10);
  display.setTextAlignment(TEXT_ALIGN_LEFT);
  display.drawString(0 + x, 5 + y, "Hum");
  
  display.setFont(ArialMT_Plain_10);
  display.setTextAlignment(TEXT_ALIGN_LEFT);
  display.drawString(43 + x, y, "INDOOR");

  display.setFont(ArialMT_Plain_24);
  String hum = String(localHum) + "%";
  display.drawString(0 + x, 15 + y, hum);
  int humWidth = display.getStringWidth(hum);

  display.setFont(ArialMT_Plain_10);
  display.setTextAlignment(TEXT_ALIGN_LEFT);
  display.drawString(95 + x, 5 + y, "Temp");

  display.setFont(ArialMT_Plain_24);
  String temp = String(localTemp) + "°C";
  display.drawString(70 + x, 15 + y, temp);
  int tempWidth = display.getStringWidth(temp);
}

Code snippet #11

Plain text
/* WIFI */
const char* WIFI_SSID = "YOUR SSID";
const char* WIFI_PWD = "YOUR PASSWORD";

/* Wunderground Settings */
const boolean IS_METRIC = true;
const String WUNDERGRROUND_API_KEY = "YOUR KEY";
const String WUNDERGRROUND_LANGUAGE = "EN";
const String WUNDERGROUND_COUNTRY = "CL";
const String WUNDERGROUND_CITY = "Santiago";

Github

https://github.com/squix78/esp8266-weather-station

Github

https://github.com/squix78/json-streaming-parser

Github file

https://github.com/Mjrovai/MJRoBot-Home-Weather-Station/tree/master/Home_Weather_Station_Final

Github

https://github.com/squix78/esp8266-oled-ssd1306

Github

https://github.com/adafruit/DHT-sensor-library

Credits

MJRoBot (Marcelo Rovai)

MJRoBot (Marcelo Rovai)

60 projects • 910 followers
Professor, Engineer, MBA, Master in Data Science. Writes about Electronics with a focus on Physical Computing, IoT, ML, TinyML and Robotics.
Thanks to Daniel Eichhorn.

Comments