Category: Arduino

  • How to make a GPS with Arduino

    This guide will show you how to make a simple GPS with Arduino.

    What you will need

    GPS Neo-6M

    This will be used to determine the location.

    Arduino UNO Rev3

    This will be what we use to control all the other components. Think of this as the motherboard of the build.

    Arduino IDE

    This will be used to program the Arduino

    About GPS

    Before we start this project, you need to know a little bit about GPS. Satellites will send signals on their distance from the module. Once four or more satellites are connected and giving out this data, the receiver can then use the data to figure out the exact location of the user.

    Credits: https://www.scienceabc.com/innovation/how-gps-global-positioning-system-works-satellite-smartphone.html

    The receiver will then present this data in the form of NMEA sentences. This is a standard communication developed by the National Marine Electronics Association. We will be using TinyGPS++ to parse these.

    Using the GPS with Arduino

    For this part, you don’t need the LCD. This will show you how to log the GPS output to the serial monitor. We will then parse this data using TinyGPS++.

    Preparations

    First, open Arduino IDE and you will be greeted with a blank sketch.

    At the top toolbar, click Ctrl + Shift + I to bring up the library manager and type “TinyGPSPlus” and install the top result.

    Sign up for our newsletter!

    Code

    Now that we are all prepared, lets start writing the code. First, we include the library that helps us communicate with the GPS.

    #include <SoftwareSerial.h>

    Next, we include the library that parses NMEA sentences.

    #include <TinyGPSPlus.h>

    Now, declare the communication between the Arduino and the GPS and then the parser.

    SoftwareSerial ss(4,3);
    TinyGPSPlus gps;

    After that, we go inside the void setup() function and we initiate the communication between the computer and the Arduino and the GPS and Arduino.

    Serial.begin(9600);
    ss.begin(9600);

    Next, we go into void loop() and specify that whatever is below this line of code should only happen when the Arduino receives a signal.

    while (ss.available() > 0)

    Then, we encode the data in a format that the GPS can then parse.

    gps.encode(ss.read());

    Then, we create an if block so the serial monitor only displays our data when the data the GPS is outputting is valid.

    if (gps.location.isUpdated()) {
    
    }

    Now, inside the if block, we can access all the data and print it to the serial monitor.

    Serial.print("Latitude= ");
    Serial.print(gps.location.lat(), 6); //6 for 6 decimal places
    Serial.print("Longitude= ");
    Serial.print(gps.location.lng(), 6); //6 for 6 decimal places

    Your full code should look like this:

    #include <SoftwareSerial.h>
    #include <TinyGPSPlus.h>
    
    SoftwareSerial ss(4,3);
    TinyGPSPlus gps;
    
    void setup() {
      // put your setup code here, to run once:
      Serial.begin(9600);
      ss.begin(9600);
    }
    
    void loop() {
      // put your main code here, to run repeatedly:
      while (ss.available() > 0)
      gps.encode(ss.read());
    
      if (gps.location.isUpdated()) {
        Serial.print("Latitude= ");
        Serial.print(gps.location.lat(), 6); //6 for 6 decimal places
        Serial.print("Longitude= ");
        Serial.print(gps.location.lng(), 6); //6 for 6 decimal places
      }
    }
    

    Wiring

    The wiring is shown below:

    • GPS RX > Digital 4 on Arduino
    • GPS TX > Digital 3 on Arduino
    • GPS VCC > Power 3.3V on Arduino
    • GPS GND > Power GND on Arduino

    Uploading

    Now, with the Arduino IDE opened and the code ready, press Ctrl + U on your keyboard. The code will write and start outputting to the serial monitor, which you can access by pressing Ctrl + Shift + M on your keyboard or by going to the top toolbar and clicking Tools > Serial Monitor. The GPS will take a couple minutes to get its location. You may want to stick the antenna outside for this, as it will take a long time to get its location indoors.

    Soon, you will be able to view the data coming in.

  • How to make an IoT fire alarm.

    If you are looking for a nice fire solution in a place where false alarms happen a lot, this is by far the cheapest, best solution I know.

    What you will need – Hardware

    What you will need – Software

    How to create – Step 1: Setting up Blynk

    First, make sure you have the app on your phone.

    Now create an account or log in.

    Click “New Project”.

    Give an appropriate project name. I thought that the name “Fire Sensor” would be reasonable.

    Choose the device name of “ESP8266” or, more preferably, “NodeMCU”.

    An auth token will be sent to your email. Keep this safe, you are going to need it later on.

    Drag and drop the “Push Notification” widget and press the play icon at the far top, far right corner.

    How to create – Step 2: Getting the hardware right

    Here are the schematics:

    • AO on the flame sensor should not be connected to anything
    • G or GND on the flame sensor should go to GND on the ESP8266
    • + or VCC on the flame sensor should go to VIN on the ESP8266
    • DO on the flame sensor should go to D1 on the ESP8266

    How to create – Step 3: Getting the software right

    First, install the library from this URL:

    https://github.com/blynkkk/blynk-library

    Now, in the IDE, go to File > Preferences.

    When it says “Additional Board Manager URL’s”, paste in this:

    URL LIST
    
    https://dl.espressif.com/dl/package_esp32_index.json, http://arduino.esp8266.com/stable/package_esp8266com_index.json

    Now go to Boards > Board Manager.

    Search “ESP8266” and install “esp8266 by ESP8266 Community”.

    Now go to Boards > NodeMCU 1.0 (ESP-12E Module) or more preferably, Boards > Generic ESP8266 Module.

    Upload the following code, replacing certain things:

    C#, C++, C
    
    #define BLYNK_PRINT Serial
    #include 
    #include  
    BlynkTimer timer;
    char auth[] = "No!"; //Replace with auth code sent via Email
    char ssid[] = "hacked"; //Replace with wifi name
    char pass[] = "123456789"; //Replace with Wifi Password
    int flag=0;
    void notifyOnFire()
    {
    int isButtonPressed = digitalRead(D1); // falme sensor connected D1 pin
    if (isButtonPressed==1 && flag==0) 
    {
    Serial.println("Fire DETECTED");
    Blynk.notify("Alert : Fire detected");
    flag=1;
    }
    else if (isButtonPressed==0)
    {
    flag=0;
    }
    }
    void setup()
    {
    Serial.begin(9600);
    Blynk.begin(auth, ssid, pass);
    pinMode(D1,INPUT_PULLUP);
    timer.setInterval(1000L,notifyOnFire); 
    }
    void loop()
    {
    Blynk.run();
    timer.run();
    }

    DONE!

  • How to use the DHT11/22 sensor to log data to Google Sheets

    By this time, you’d probably want a temperature sensor in the house – one less than $25. If you have one, you are probably wanting a better one. Here is an easy solution to this problem.

    Things that you’ll need – Hardware

    Things that you’ll need – Software

    Creating And Deploying The Script

    Create a new spreadsheet as shown below:

    Once you have got that down go to Tools > Script Editor. We’ll continue from there.

    Name the sheet below TempSheet

    In the script editor, copy and paste the code given here. Edit the script ID in the code. The script ID is found in the place where “vbn” is in the given URL:

    URL
    
    https://docs.google.com/spreadsheets/d/vbn/edit#gid=0

    Now go to Publish > Deploy as a web app. The “Project version” will be “New”. Select “your email id” in the “Execute the app as” field. Choose “Anyone, even anonymous” in the “Who has access to the app” field. And then click on “Deploy”. Note that When republishing please select the latest version and then Deploy again. Type “New Script Created” in the “Project Version” field.

    You will have to give Google permission to deploy it as a web app. Just click on “Review Permissions”. Then choose your Email ID here using which you have created the spreadsheet.

    Click on “Advanced”.

    And then click on Go to your_script_name(unsafe). Here in my case, it is “TempLog_Script”.

    Click on “Allow” and this will give permission to deploy it as a web app.

    Now you can see the new screen with a given link and named “Current web app URL”. This URL contains Google Script ID. Just copy the URL and save it somewhere.

    Testing the DHT11/22

    Use the given circuit diagram and code:

    Diagram:

    Code:

    C#, C++, C
    
    #include "DHT.h"
    
    #define dht_apin A0
    
    DHT dht;
    
    #define DHTTYPE DHT22 //Change this to any type of DHT Sensor you're Using!
    
    DHT(dht_apin, DHTTYPE);
    
    void setup() {
    
    // put your setup code here, to run once:
    
    Serial.begin(9600); //Starts serial
    
    delay(5000); //Waits before reading from sensor
    
    Serial.println("DHT22 Temp. And Humi. Test"); //Prints the intro
    
    }
    
    void loop() {
    
    // put your main code here, to run repeatedly:
    
    dht.read11(dht_apin); //Reads from the sensor
    
    Serial.println("Humi. ---------- "); //Prints humidity
    
    Serial.print(DHT.humidity); //Prints humidity
    
    Serial.print("% "); //Marks the humidity as %
    
    Serial.print("Temp. ------------ "); //Prints temperature
    
    Serial.print(DHT.temperature); //Prints temperature
    
    Serial.print("℃") //Marks the temperature unit
    
    delay(2000); //Waits 2 seconds before doing the loop again fastest is once evrey 2 seconds
    
    } //end loop

    It should be printing the temperature and humidity. If it is not, try running this code at rate 9600 that will print “Hello!” every second to see if you are getting any serial communication at all:

    C#, C++, C
    
    #define one_second 1000
    
    #define the_word_hello "Hello!"
    
    void setup() {
    
    // put your setup code here, to run once:
    
    Serial.begin(9600);
    
    delay(5000);
    
    }
    
    void loop() {
    
    // put your main code here, to run repeatedly:
    
    Serial.print(the_word_hello);
    
    delay(one_second);
    
    }

    If it is all working, we can move on.

    Sign up for our newsletter!

    Schematics

    As you can see in the picture:

    • D4 pin on the NODEMCU > DATA pin on the DHT11/22
    • GND pin on the NODEMCU > GND pin on the DHT11/22
    • 5V pin on the NODEMCU > VCC pin on the DHT11/22

    Using the Arduino IDE, upload the following code:

    Programming language(s) C#, C++, C: ***{Code starts after this line}***
    
    #include <ESP8266WiFi.h>
    #include "HTTPSRedirect.h"
    #include "DebugMacros.h"
    #include <DHT.h>
    
    #define DHTPIN D4                                                           // what digital pin we're connected to
    #define DHTTYPE DHT11                                                       // select dht type as DHT 11 or DHT22
    DHT dht(DHTPIN, DHTTYPE);
    
    float h;
    float t;
    String sheetHumid = "";
    String sheetTemp = "";
    
    const char* ssid = "";                //replace with our wifi ssid
    const char* password = "";         //replace with your wifi password
    
    const char* host = "script.google.com";
    const char *GScriptId = "AKfycbxy9wAZKoPIpPq5AvqYTFFn5kkqK_-avacf2NU_w7ycoEtlkuNt"; // Replace with your own google script id
    const int httpsPort = 443; //the https port is same
    
    // echo | openssl s_client -connect script.google.com:443 |& openssl x509 -fingerprint -noout
    const char* fingerprint = "";
    
    //const uint8_t fingerprint[20] = {};
    
    String url = String("/macros/s/") + GScriptId + "/exec?value=Temperature";  // Write Teperature to Google Spreadsheet at cell A1
    // Fetch Google Calendar events for 1 week ahead
    String url2 = String("/macros/s/") + GScriptId + "/exec?cal";  // Write to Cell A continuosly
    
    //replace with sheet name not with spreadsheet file name taken from google
    String payload_base =  "{\"command\": \"appendRow\", \
                        \"sheet_name\": \"TempSheet\", \
                           \"values\": ";
    String payload = "";
    
    HTTPSRedirect* client = nullptr;
    
    // used to store the values of free stack and heap before the HTTPSRedirect object is instantiated
    // so that they can be written to Google sheets upon instantiation
    
    void setup() {
      delay(1000);
      Serial.begin(115200);
      dht.begin();     //initialise DHT11
    
      Serial.println();
      Serial.print("Connecting to wifi: ");
      Serial.println(ssid);
      
      WiFi.begin(ssid, password);
      while (WiFi.status() != WL_CONNECTED) {
        delay(500);
        Serial.print(".");
      }
      Serial.println("");
      Serial.println("WiFi connected");
      Serial.println("IP address: ");
      Serial.println(WiFi.localIP());
    
      // Use HTTPSRedirect class to create a new TLS connection
      client = new HTTPSRedirect(httpsPort);
      client->setInsecure();
      client->setPrintResponseBody(true);
      client->setContentTypeHeader("application/json");
      Serial.print("Connecting to ");
      Serial.println(host);          //try to connect with "script.google.com"
    
      // Try to connect for a maximum of 5 times then exit
      bool flag = false;
      for (int i = 0; i < 5; i++) {
        int retval = client->connect(host, httpsPort);
        if (retval == 1) {
          flag = true;
          break;
        }
        else
          Serial.println("Connection failed. Retrying...");
      }
    
      if (!flag) {
        Serial.print("Could not connect to server: ");
        Serial.println(host);
        Serial.println("Exiting...");
        return;
      }
    // Finish setup() function in 1s since it will fire watchdog timer and will reset the chip.
    //So avoid too many requests in setup()
    
      Serial.println("\nWrite into cell 'A1'");
      Serial.println("------>");
      // fetch spreadsheet data
      client->GET(url, host);
      
      Serial.println("\nGET: Fetch Google Calendar Data:");
      Serial.println("------>");
      // fetch spreadsheet data
      client->GET(url2, host);
    
     Serial.println("\nStart Sending Sensor Data to Google Spreadsheet");
    
      
      // delete HTTPSRedirect object
      delete client;
      client = nullptr;
    }
    
    void loop() {
    
      h = dht.readHumidity();                                              // Reading temperature or humidity takes about 250 milliseconds!
      t = dht.readTemperature();                                           // Read temperature as Celsius (the default)
      if (isnan(h) || isnan(t)) {                                                // Check if any reads failed and exit early (to try again).
        Serial.println(F("Failed to read from DHT sensor!"));
        return;
      }
      Serial.print("Humidity: ");  Serial.print(h);
      sheetHumid = String(h) + String("%");                                         //convert integer humidity to string humidity
      Serial.print("%  Temperature: ");  Serial.print(t);  Serial.println("°C ");
      sheetTemp = String(t) + String("°C");
    
      static int error_count = 0;
      static int connect_count = 0;
      const unsigned int MAX_CONNECT = 20;
      static bool flag = false;
    
      payload = payload_base + "\"" + sheetTemp + "," + sheetHumid + "\"}";
    
      if (!flag) {
        client = new HTTPSRedirect(httpsPort);
        client->setInsecure();
        flag = true;
        client->setPrintResponseBody(true);
        client->setContentTypeHeader("application/json");
      }
    
      if (client != nullptr) {
        if (!client->connected()) {
          client->connect(host, httpsPort);
          client->POST(url2, host, payload, false);
          Serial.print("Sent : ");  Serial.println("Temp and Humid");
        }
      }
      else {
        DPRINTLN("Error creating client object!");
        error_count = 5;
      }
    
      if (connect_count > MAX_CONNECT) {
        connect_count = 0;
        flag = false;
        delete client;
        return;
      }
    
    //  Serial.println("GET Data from cell 'A1':");
    //  if (client->GET(url3, host)) {
    //    ++connect_count;
    //  }
    //  else {
    //    ++error_count;
    //    DPRINT("Error-count while connecting: ");
    //    DPRINTLN(error_count);
    //  }
    
      Serial.println("POST or SEND Sensor data to Google Spreadsheet:");
      if (client->POST(url2, host, payload)) {
        ;
      }
      else {
        ++error_count;
        DPRINT("Error-count while connecting: ");
        DPRINTLN(error_count);
      }
    
      if (error_count > 3) {
        Serial.println("Halting processor...");
        delete client;
        client = nullptr;
        Serial.printf("Final free heap: %u\n", ESP.getFreeHeap());
        Serial.printf("Final stack: %u\n", ESP.getFreeContStack());
        Serial.flush();
        ESP.deepSleep(0);
      }
      
      delay(3000);    // keep delay of minimum 2 seconds as dht allow reading after 2 seconds interval and also for google sheet
    }