Arduino Uno with NEO GPS and OLED

to-show-sections.jpg

This project displays the latitude and longitude from a GPS sensor on an OLED display using the I2C protocol.

In the video below you can see a splash screen is displayed with some information while the GPS is getting a fix on your location. When your location is known the screen updates to show the number of satellites in the fix and your latitude and longitude.

Below you can see the I2C OLED and the blox GPS sensor I used.

OLED

Blox Neo-7m

For the software I used probably the best GPS and display libraries. NeoGPS for GPS signal processing and the U8g2  monochrome graphics library for outputting to the OLED display. I used the U8x8 version of U8g2 as I only needed simple text and it’s also faster.

These are both easy to install into the Arduino IDE as they are available in the Library Manager. You also need to install the Altsoftserial.h library. To do this open the library manager (Sketch > Include Library > Manage Libraries) and search for and then install each of the following: NeoGPS, Altsoftserial and U8g2.

To see the Satellites tracked (TKD), Available (AVL) and the time (TME)  at the bottom of the screen a few edits have to be made to one of the configuration files, In Windows, find this file:
C:\Users\#YourUserName#\Documents\Arduino\libraries\NeoGPS\src\NMEAGPS_cfg.h, or just search your PC for NMEAGPS_cfg.h and uncomment the following three items (remove the preceding //):
//#define NMEAGPS_PARSE_GSV
//#define NMEAGPS_PARSE_SATELLITES
//#define NMEAGPS_PARSE_SATELLITE_INFO
and save the file.

The wiring is pretty simple as well.



Wiring for UNO, GPS and OLED

Wiring diagram for the UNO, GPS and OLED

Photo of the wiring

Photo of the wiring

The code is below

#include <NMEAGPS.h>
#include <U8x8lib.h>

//-------------------------------------------------------------------------
//  The GPSport.h include file tries to choose a default serial port
//  for the GPS device.  If you know which serial port you want to use,
//  edit the GPSport.h file.
#include <GPSport.h>


//------------------------------------------------------------
// This object parses received characters
//   into the gps.fix() data structure
static NMEAGPS  gps;


//------------------------------------------------------------
//  Define a set of GPS fix information.  It will
//  hold on to the various pieces as they are received from
//  an RMC sentence.  It can be used anywhere in your sketch.
static gps_fix  fix;

// the OLED used
U8X8_SSD1306_128X64_NONAME_HW_I2C u8x8(/* reset=*/ U8X8_PIN_NONE);


uint32_t timer;
bool screencleared = false;

void setup() {
  gpsPort.begin( 9600 );

  u8x8.begin();
  u8x8.setFont(u8x8_font_chroma48medium8_r);

  // Start up screen on OLED
  u8x8.fillDisplay();
  delay(1000);
  for (uint8_t r = 0; r < u8x8.getRows(); r++ )
  {
    u8x8.clearLine(r);
    delay(100);
  }
  delay(100);
  u8x8.println("Doing");
  delay(500);
  u8x8.println("Some");
  delay(500);
  u8x8.print("Stuff");

  timer = millis();
}

//----------------------------------------------------------------
//  This function gets called about once per second, during the GPS
//  quiet time. 

static void doSomeWork()
{
  timer = millis(); // reset the timer

  //----------------------------------------------------------------
  //  This section is run before a fix is made to show sat info (Available, Tracked, Time)

  // Count how satellites are being received for each GNSS
  int totalSatellites, trackedSatellites;
  totalSatellites = gps.sat_count;
  for (uint8_t i = 0; i < totalSatellites; i++) {
    if (gps.satellites[i].tracked) {
      trackedSatellites++;
    }
  }

  u8x8.inverse();

  u8x8.drawString(0, 6, "TKD");
  u8x8.drawString(5, 6, "AVL");
  u8x8.drawString(10, 6, "TME");

  u8x8.noInverse();

  enum {BufSizeTracked = 3}; //Space for 2 characters + NULL
  char trackedchar[BufSizeTracked];
  snprintf (trackedchar, BufSizeTracked, "%d", trackedSatellites);
  u8x8.drawString(0, 7, "  ");
  u8x8.drawString(0, 7, trackedchar);

  enum {BufSizeTotal = 3};
  char availchar[BufSizeTotal];
  snprintf (availchar, BufSizeTotal, "%d", totalSatellites);
  u8x8.drawString(5, 7, "  ");
  u8x8.drawString(5, 7, availchar);

  if (fix.valid.time) {

    enum {BufSizeTime = 3};
    int hour = fix.dateTime.hours + 2;
    int minute = fix.dateTime.minutes;

    char hourchar[BufSizeTime];
    char minutechar[BufSizeTime];
    snprintf (hourchar, BufSizeTime, "%d", hour);
    snprintf (minutechar, BufSizeTime, "%d", minute);
    if ( hour < 10 )
    {
      snprintf (hourchar, BufSizeTime, "%02d", hour);
    }
    if ( minute < 10 )
    {
      snprintf (minutechar, BufSizeTime, "%02d", minute);
    }

    u8x8.drawString(10, 7, hourchar);
    u8x8.drawString(12, 7, ":");
    u8x8.drawString(13, 7, minutechar);
  }

  //----------------------------------------------------------------

  // Once the location is found the top part of the screen is cleared and the fix data is shown
  if (fix.valid.location) {

    if (!screencleared) // do once
    {
      int r;
      for ( int r = 0; r < 5; r++ )
      {
        u8x8.clearLine(r);
      }
      screencleared = true;
    }

    u8x8.inverse();

    u8x8.drawString(0, 0, "FIX");
    u8x8.drawString(0, 2, "LAT");
    u8x8.drawString(0, 4, "LNG");
    u8x8.noInverse();

    enum {BufSize = 3}; // Space for 2 digits
    char satchar2[BufSize];
    snprintf (satchar2, BufSize, "%d", fix.satellites);
    u8x8.drawString(4, 0, "  ");
    u8x8.drawString(4, 0, satchar2);

    char latchar[10]; // Buffer big enough for 9-character float
    dtostrf(fix.latitude() + 23, 3, 7, latchar); // Leave room for large numbers
    dtostrf(77.848544, 3, 7, latchar); // Leave room for large numbers
    u8x8.drawString(4, 2, latchar);
    char longchar[10];
    dtostrf(fix.longitude() + 137, 3, 7, longchar);
    dtostrf(166.680378, 3, 7, longchar);

    u8x8.drawString(4, 4, longchar);

  }

}


//  This is the main GPS parsing loop.
static void GPSloop()
{
  while (gps.available( gpsPort )) {
    fix = gps.read();
    doSomeWork();
  }
}

void loop()
{
  GPSloop();

  // until we get a fix, print a dot every second
  if (millis() - timer > 2000 && !screencleared) {
    timer = millis(); // reset the timer
    u8x8.print(".");
  }
}



16 Replies to “Arduino Uno with NEO GPS and OLED”

  1. Gabe Noriega says:

    hi, mine is getting stuck on the “Doing Some stuff” part. i am not sure whats going on here.

    1. WordBot says:

      Hi, Is the same hardware? You can use this software to test you are receiving data – u-blox.com/en/product/u-center-windows

      1. Gabe Noriega says:

        yeah i have the same hardware but its stil not working. do i need the software in order for this to work? im a little confused on what the software doe. thanks

        1. WordBot says:

          The software takes a reading from the GPS and shows you all sorts of information. It’s the best way to check the GPS is working.

          1. Gabe Noriega says:

            ok thanks

  2. Gabe Noriega says:

    hey i got U-Center, but its not displaying anything. do you think my gps is not working?

    1. WordBot says:

      Does it show anything when you have the GPS connected? How are you connecting it?

      1. Gabe Noriega says:

        no nothing is shown. i dont think its connecting

        1. Gabe Noriega says:

          how should i connect it?

          1. WordBot says:

            You need a USB to Serial converter. I used one of these: https://www.ebay.co.uk/itm/For-Arduino-Serial-FT232RL-USB-HOT-Converter-3-3V-to-Module-Adapter-TTL-FTDI-5V-/222898816179. I chose ‘Receiver > Port’ in U-Center and it started working. There are other USB to Serial converters around but they sometimes have driver problems. You’ll see this in device manager in Windows.

  3. Abhishek says:

    Hi
    I followed through every single steps as you described using same hardware but I got an error.
    exit status 1
    ‘class NMEAGPS’ has no member named ‘sat_count’
    can you help me solving this plzz

    1. WordBot says:

      You probably just need to do this…

      find this file:
      C:\Users\#YourUserName#\Documents\Arduino\libraries\NeoGPS\src\NMEAGPS_cfg.h, or just search your PC for NMEAGPS_cfg.h and uncomment the following three items (remove the preceding //):
      //#define NMEAGPS_PARSE_GSV
      //#define NMEAGPS_PARSE_SATELLITES
      //#define NMEAGPS_PARSE_SATELLITE_INFO
      and save the file.

  4. Abhishek says:

    C:\Users\#YourUserName#\Documents\Arduino\libraries\NeoGPS\src
    After this src folder shows empty
    no idea what to do

    1. WordBot says:

      What happens if you search your PC for NMEAGPS_cfg.h ? Is it Windows 10 you are using? Maybe the files are being hidden.

      You could try reinstalling the NeoGPS library.

      1. Abhishek says:

        Plzz reply something
        It is important project for me
        Thanks

        1. WordBot says:

          I can only suggest that you remove the NeoGPS folder from here: C:\Users\YOURUSERNAME\Documents\Arduino\libraries, Then install it again. I’ve posted the NMEAGPS_cfg.h file that works for me here: https://robotzero.one/wp-content/uploads/2018/04/NMEAGPS_cfg.h

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.

scroll to top