TinyGPS++

A *NEW* Full-featured GPS/NMEA Parser for Arduino

TinyGPS++ is a new Arduino library for parsing NMEA data streams provided by GPS modules.

Like its predecessor, TinyGPS, this library provides compact and easy-to-use methods for extracting position, date, time, altitude, speed, and course from consumer GPS devices. 

However, TinyGPS++’s programmer interface is considerably simpler to use than TinyGPS, and the new library can extract arbitrary data from any of the myriad NMEA sentences out there, even proprietary ones.

Download and Installation

To install this library, download here, unzip the archive into the Arduino “libraries” folder, and restart Arduino. You should rename the folder “TinyGPSPlus”.
Download

History

TinyGPS++ is the immediate inheritor of TinyGPS, a popular compact parser that is used in Arduino installations around the world.  TinyGPS++ is not quite as ‘tiny’ as its older sibling, but its powerful and extremely easy-to-use new object model and useful new feature set make it an attractive alternative.

Usage

Let’s say you have an Arduino hooked to an off-the-shelf GPS device and you want to display your altitude.  You would simply create a TinyGPS++ instance like this:

#include "TinyGPS++.h"
TinyGPSPlus gps;

Repeatedly feed it characters from your GPS device:

while (ss.available() > 0)
  gps.encode(ss.read());

Then query it for the desired information:

if (gps.altitude.isUpdated())
  Serial.println(gps.altitude.meters());

Differences from TinyGPS

Although TinyGPS++ shares much the same compact parsing engine with TinyGPS, its programmer interface is somewhat more intuitive.  As a simple example, here’s how easy it is to print out the current latitude, longitude, and altitude in TinyGPS++:

Serial.print("LAT=");  Serial.println(gps.location.lat(), 6);
Serial.print("LONG="); Serial.println(gps.location.lng(), 6);
Serial.print("ALT=");  Serial.println(gps.altitude.meters());

Both libraries extract basic position, altitude, course, time, and date, etc. from two common NMEA sentences, $GPGGA and $GPRMC. But there are a number of other interesting sentences out there, both NMEA-defined and vendor-proprietary, just waiting to be harvested.

Consider the obscure $GPRMB, for example, which provides “recommended minimum navigation information” if you have a destination waypoint defined.

$GPRMB,A,4.08,L,EGLL,EGLM,5130.02,N,00046.34,W,004.6,213.9,122.9,A*3D

With TinyGPS++ it is now possible to extract just the “L” in the third field (it means “steer Left!”). It’s easy with the new TinyGPSCustom watcher object:

TinyGPSCustom steerDirection(gps, "GPRMB", 3);
...
Serial.print(steerDirection.value()); // prints "L" or "R"

Naturally, this extra functionality comes at some cost.  TinyGPS++ consumes somewhat more memory than TinyGPS, and it’s interface is incompatible.  So how to decide whether to update?  Here’s a guide:

Consider TinyGPS++ over TinyGPS if:

  • Compatibility with existing code (using TinyGPS) isn’t necessary.
  • Your sketch is not close to reaching RAM or flash resource limits.
  • You are running on Due or processor which can take advantage of the higher precision of 64-bit “double” floating-point.
  • You prefer the more intuitive object model.
  • You need to query for NMEA data beyond the basic location, date, time, altitude, course, speed, satellites or hdop.

Feeding the Hungry Object

To get TinyGPS++ to work, you have to repeatedly funnel the characters to it from the GPS module using the encode() method. For example, if your GPS module is attached to pins 4(RX) and 3(TX), you might write code like this:

SoftwareSerial ss(4, 3);
void loop()
{
  while (ss.available() > 0)
    gps.encode(ss.read);
  ...

After the object has been “fed” you can query it to see if any data fields have been updated:

  if (gps.location.isUpdated())
  {
    Serial.print("LAT="); Serial.print(gps.location.lat(), 6);
    Serial.print("LNG="); Serial.println(gps.location.lng(), 6);
  }
} // end loop()

The TinyGPS++ Object Model

The main TinyGPS++ object contains several core sub-objects:

  • location – the latest position fix
  • date – the latest date fix (UT)
  • time – the latest time fix (UT)
  • speed – current ground speed
  • course – current ground course
  • altitude – latest altitude fix
  • satellites – the number of visible, participating satellites
  • hdop – horizontal diminution of precision

Each provides methods to examine its current value, sometimes in multiple formats and units. Here’s a complete list:

Serial.println(gps.location.lat(), 6); // Latitude in degrees (double)
Serial.println(gps.location.lng(), 6); // Longitude in degrees (double)
Serial.print(gps.location.rawLat().negative ? "-" : "+");
Serial.println(gps.location.rawLat().deg); // Raw latitude in whole degrees
Serial.println(gps.location.rawLat().billionths);// ... and billionths (u16/u32)
Serial.print(gps.location.rawLng().negative ? "-" : "+");
Serial.println(gps.location.rawLng().deg); // Raw longitude in whole degrees
Serial.println(gps.location.rawLng().billionths);// ... and billionths (u16/u32)
Serial.println(gps.date.value()); // Raw date in DDMMYY format (u32)
Serial.println(gps.date.year()); // Year (2000+) (u16)
Serial.println(gps.date.month()); // Month (1-12) (u8)
Serial.println(gps.date.day()); // Day (1-31) (u8)
Serial.println(gps.time.value()); // Raw time in HHMMSSCC format (u32)
Serial.println(gps.time.hour()); // Hour (0-23) (u8)
Serial.println(gps.time.minute()); // Minute (0-59) (u8)
Serial.println(gps.time.second()); // Second (0-59) (u8)
Serial.println(gps.time.centisecond()); // 100ths of a second (0-99) (u8)
Serial.println(gps.speed.value()); // Raw speed in 100ths of a knot (i32)
Serial.println(gps.speed.knots()); // Speed in knots (double)
Serial.println(gps.speed.mph()); // Speed in miles per hour (double)
Serial.println(gps.speed.mps()); // Speed in meters per second (double)
Serial.println(gps.speed.kmph()); // Speed in kilometers per hour (double)
Serial.println(gps.course.value()); // Raw course in 100ths of a degree (i32)
Serial.println(gps.course.deg()); // Course in degrees (double)
Serial.println(gps.altitude.value()); // Raw altitude in centimeters (i32)
Serial.println(gps.altitude.meters()); // Altitude in meters (double)
Serial.println(gps.altitude.miles()); // Altitude in miles (double)
Serial.println(gps.altitude.kilometers()); // Altitude in kilometers (double)
Serial.println(gps.altitude.feet()); // Altitude in feet (double)
Serial.println(gps.satellites.value()); // Number of satellites in use (u32)
Serial.println(gps.hdop.value()); // Horizontal Dim. of Precision (100ths-i32)

Validity, Update status, and Age

You can examine an object’s value at any time, but unless TinyGPS++ has recently been fed from the GPS, it should not be considered valid and up-to-date. The isValid() method will tell you whether the object contains any valid data and is safe to query.

Similarly, isUpdated() indicates whether the object’s value has been updated (not necessarily changed) since the last time you queried it.

Lastly, if you want to know how stale an object’s data is, call its age() method, which returns the number of milliseconds since its last update. If this returns a value greater than 1500 or so, it may be a sign of a problem like a lost fix.

Debugging

When a TinyGPS++ sketch fails, it’s usually because the object received an incomplete NMEA stream, or perhaps none at all.

Fortunately, it’s pretty easy to determine what’s going wrong using some built-in diagnostic methods:

  • charsProcessed() – the total number of characters received by the object
  • sentencesWithFix() – the number of $GPRMC or $GPGGA sentences that had a fix
  • failedChecksum() – the number of sentences of all types that failed the checksum test
  • passedChecksum() – the number of sentences of all types that passed the checksum test

If your sketch has been running a while but charsProcessed() is returning 0, you likely have a problem with your wiring or serial connection. (If data never arrives from the GPS unit, it stands to reason it’s not getting to TinyGPS++.) I often insert a little debug clause into my GPS sketches detects this condition then prints out the incoming stream:

// Debug: if we haven't seen lots of data in 5 seconds, something's wrong.
if (millis() > 5000 && gps.charsProcessed() < 10) // uh oh
{
  Serial.println("ERROR: not getting any GPS data!");
  // dump the stream to Serial
  Serial.println("GPS stream dump:");
  while (true) // infinite loop
    if (ss.available() > 0) // any data coming in?
      Serial.write(ss.read());
}

Another common failure is when the sentences sent to TinyGPS++ are incomplete. This usually happens when you retrieve the characters from the GPS so slowly or infrequently that some are lost. The symptom is easy to spot: checksum failure.

Explanation: Every NMEA sentence ends with a numeric field that represents a mathematical summing of all the characters in the sentence. It’s there to ensure data integrity. If this number doesn’t match the actual sum (perhaps because some characters went awry), TinyGPS++ simply discards the entire sentence and increments an internal “checksum failed” counter. You can read this counter with:

Serial.print("Sentences that failed checksum=");
Serial.println(gps.failedChecksum());

// Testing overflow in SoftwareSerial is sometimes useful too.
Serial.print("Soft Serial device overflowed? ");
Serial.println(ss.overflow() ? "YES!" : "No");

If the checksum counter is continually incrementing, you have a problem. (Hint: don’t use delay() in your sketch.)

Custom NMEA Sentence Extraction

One of the great new features of TinyGPS++ is the ability to extract arbitrary data from any NMEA or NMEA-like sentence. Read up on some of the interesting sentences there are out there, then check to make sure that your GPS receiver can generate them.

The idea behind custom extraction is that you tell TinyGPS++ the sentence name and the field number you are interested in, like this:

TinyGPSCustom magneticVariation(gps, "GPRMC", 10)

This instructs TinyGPS++ to keep an eye out for $GPRMC sentences, and extract the 10th comma-separated field each time one flows by. At this point, magneticVariation is a new object just like the built-in ones. You can query it just like the others:

if (magneticVariation.isUpdated())
{
  Serial.print("Magnetic variation is ");
  Serial.println(magneticVariation.value());
}

Establishing a fix

TinyGPS++ objects depend on their host sketch to feed them valid and current NMEA GPS data. To ensure their world-view is continually up-to-date, three things must happen:

  1. You must continually feed the object serial NMEA data with encode().
  2. The NMEA sentences must pass the checksum test.
  3. For built-in (non-custom) objects, the NMEA sentences must self-report themselves as valid. That is, if the $GPRMC sentence reports a validity of “V” (void) instead of “A” (active), or if the $GPGGA sentence reports fix type “0″ (no fix), then the position and altitude information is discarded (though time and date are retained).

It may take several minutes for a device to establish a fix, especially it has traveled some distance or a long time has elapsed since its last use.

Distance and Course

If your application has some notion of a “waypoint” or destination, it is sometimes useful to be able to calculate the distance to that waypoint and the direction, or “course”, you must travel to get there. TinyGPS++ provides two methods to get this information, and a third (cardinal()) to display the course in friendly, human-readable compass directions.

const double EIFFEL_TOWER_LAT = 48.85826;
const double EIFFEL_TOWER_LNG = 2.294516;
double distanceKm =
  TinyGPSPlus.distanceBetween(
    gps.location.lat(),
    gps.location.lng(),
    EIFFEL_TOWER_LAT,
    EIFFEL_TOWER_LNG) / 1000.0;
double courseTo =
  TinyGPSPlus.courseTo(
    gps.location.lat(),
    gps.location.lng(),
    EIFFEL_TOWER_LAT,
    EIFFEL_TOWER_LNG);
Serial.print("Distance (km) to Eiffel Tower: ");
Serial.println(distanceKm);
Serial.print("Course to Eiffel Tower: ");
Serial.println(courseTo);
Serial.print("Human directions: ");
Serial.println(TinyGPSPlus.cardinal(courseTo));

Library Version

You can retrieve the version of the TinyGPS++ library by calling the static member libraryVersion().

Serial.println(TinyGPSPlus::libraryVersion());

Sample Sketches

TinyGPS++ ships with several sample sketch which range from the simple to the more elaborate. Start with BasicExample, which demonstrates library basics without even requiring a GPS device, then move onto FullExample and KitchenSink. Later, see if you can understand how to do custom extractions with some of the other examples.

Acknowledgements

Thanks go out to the many Arduino forum users for outstanding help in testing and popularizing TinyGPS, this library’s predecessor. Thanks especially to Maarten Lamers, who wrote the wiring library that originally gave me the idea of how to organize TinyGPS++.

All input is appreciated.

Mikal Hart

Page last updated on September 28, 2014 at 11:35 am
429 Responses → “TinyGPS++”

  1. Mikal

    9 years ago

    @Gilles, the accuracy of the built-in data types float and double is a function of the processor. There’s nothing that SW can do to alleviate that I’m afraid. If you need higher precision, you might check out processors which use 64-bit doubles instead of 32, like the Due…?


  2. Mikal

    9 years ago

    @TommiP,

    Yes, you should copy the files to a new folder called TinyGPSPlus in the Arduino/libraries folder. Then make sure you exit and re-enter the Arduino IDE before running the examples.


  3. Mikal

    9 years ago

    @Pete B, thanks for the nice words. I believe the Adafruit library uses the fact that the Adafruit Ultimate GPS module (great module by the way!) has an asynchronous “FIX” output. You could simply watch that signal. I don’t want TinyGPS++ to depend on a feature that isn’t present in all GPS devices, but there’s no reason you can watch it asynchronously.


  4. Mikal

    9 years ago

    @flydr2, Thanks! Very cool.


  5. Mikal

    9 years ago

    @Costin, a trick to reset the GPS object is:

    TinyGPSPlus gps;
    
    ...
    
    {
    ...
       gps = TinyGPSPlus(); // reset with new object.
    ...
    }
    

  6. Mikal

    9 years ago

    @Jay Be, are you running the examples? What is the refresh rate of the GPS? 10Hz?


  7. Jay Be

    9 years ago

    yes, i’m running the “FullExample” and just changed this two lines:

    static const int RXPin = 10, TXPin = 9;
    static const uint32_t GPSBaud = 9600;

    refresh rate is 1hz.
    i also get checksum errors between 1 and 6…
    thanks!


  8. Makis

    9 years ago

    Hi is it posible to use the GPS++ To Serial.println only the $GPRMC sentence? in raw format as it came from GPS.

    Thanks in advance!


  9. Diego

    9 years ago

    How can I can do to get into a string frame the entire $ GPRMC frame , ie complete. I do not want to get only one field , I want to get the full frame and store it in a string variable . Thank you very much .


  10. Mikal

    9 years ago

    @Makis, no the library (purposefully) does not store complete sentences. But you know, you are completely in control of the byte stream before you send it to TinyGPS++’s encode() method. Why not simply look for that yourself?


  11. Mikal

    9 years ago

    @Diego, since you control the stream of data before it gets sent to TinyGPS++, just capture all the characters up until the newline terminator, beginning each time you see the characters “$GPRMC”.


  12. Brian

    9 years ago

    Hi!

    The isValid() test seems a little odd if all the NMEA strings are checksum-verified. Does isValid() check for usable data versus empty fields?

    Also, I need to save some of the NMEA data to an SD card, are the currently validated NMEA strings stored anywhere so I don’t need to recreate them from the object data?


  13. Ron Koval

    9 years ago

    I have run your example program which extracts R and L from the $GPRMB sentence and it works just fine. I have tried to work with conditional statements with steerDirection.value() without any success. I have added a few lines to your example and tried to assign steerDirection.value() to an integer variable, it compiles fine, but all I get is R575 or L575 for the program below. Can you direct me as how to get the steerDirection.value to work with other functions than Serial.print ? Thanks.

    Here is the section of code with // added for the 3 lines I have added

    void loop()
    {
    int dir; // added declaration of integer called dir
    {
    Serial.print(steerDirection.value());
    dir = int(steerDirection.value()); // added
    Serial.print(dir); // added, prints 575 no matter if L or R
    Serial.println();
    }

    while (ss.available() > 0)
    gps.encode(ss.read());
    }


  14. Mikal

    9 years ago

    @Brian, it possibly could have been better named, but isValid simply means that at least one sentence has set the value correctly. Initially all values are NOT valid, but as soon as the first legal sentence sets it, that value is valid forever. It does not currently sense empty fields.

    It’s one of TinyGPS++’s design goals to be very stingy with memory consumption, and accordingly, complete NMEA sentences are never stored. If you want to store complete sentences you will have to do it yourself.


  15. Mikal

    9 years ago

    @Ron, the line beginning “dir = …” converts a character pointer into an int. That’s not what you want for dir. Either directly use the string

    Serial.println(steerDirection.value());
    

    or calculate dir correctly

    dir = strcmp(steerDirection.value(), "L") == 0 ? -1 : 1; // -1 for L, 1 for R
    

  16. Brian

    9 years ago

    Good to know that the “validated” NMEA strings are not available, but for others to note, it is quite easy to simply re-create the strings by using custom objects.

    You probably would not want to re-create a lot of them, but the basic GPRMC and GPGGA (Google Earth basics) share a lot of the same data, and could be easily re-assembled from custom strings, then have a valid checksum calculated and appended to the end.

    I’m in the midst of testing, but I have my doubts that the isUpdated() function works properly on custom objects. It seems to be firing about 10x as often as possible (1Hz uBlox update rate). More to follow…


  17. Brian

    9 years ago

    FYI, HDOP is Horizontal -Dilution- of Position, you use “diminution” which is the French equivalent, and not really correct.


  18. Brian

    9 years ago

    Solved the “issue” of rapid updates, my fault! ;)

    I’ve got the “re-assembly” of a GPRMC string going fine, with a recalculated checksum added to the end (some unused parameters are dummy data, so it will be different), but I’ve run into an issue in GPGGA where a custom object can be a variable length, like altitude.

    I use this technique to utilize the custom object (display on LCD, write to SD, etc): (Not in the order below. just the concept, which works fine…)

    - TinyGPSCustom GGAalt(gps, “GPGGA”, 9);
    - strncpy(GPSaltArrayText,GGAalt.value(),4);

    The issue is with altitude, I can’t predict how many bytes the custom object will contain, and something like: arraySize = sizeof(GGAalt); seems to crash the AVR

    1) Is there a better way to move the contents of a custom object into a char array?

    2) Is there some way to determine how many bytes a custom object contains?

    Thanks!


  19. Mikal

    9 years ago

    @Brian, are you familiar with the strcpy() function? The value() method of TinyGPSCustom returns a true C-style string, so you should be able to simply:

    strcpy(GPSaltArrayText, GGAalt.value());
    

    Alternatively, if you want to make sure it fits before you copy:

    int len = strlen(GGAalt.value());
    if (len < sizeof(GPSaltArrayText))
       strcpy(GPSaltArrayText, GGAalt.value());
    

  20. Brian

    9 years ago

    Still a little fuzzy on “isValid()”…

    This is a completely “valid” NMEA string:

    $GPGGA,033219.00,,,,,0,00,99.99,,,,,,*6C

    It’s essentially what you get before the GPS has a fix, but is tracking satellites (thus the time is correct, valid, and incrementing; therefore “updating”).

    Would TinyGPS++ consider the above sentence “valid” and “updating”? If so, I need to do a lot more field validations!

    Thanks.


  21. Daniel C

    9 years ago

    Mikal,

    Great Library, thanks for the great work. I have been using it with Hardware Serial and a Mega, but I have found that the hardware serial only works with the older versions of the Arduino IDE, and now I need to be able to use the later version. I have the GPS chip (Adafruit) hooked up properly and I launch the 1.0.5 IDE and use your DeviceExample script, replacing the software serial with hardware serial, change BAUS to 9600 and it works great. I then close that and open the 1.6.0 IDE and and do the same thing and get “No GPS data received: check wiring”. Any thoughts on why I might be seeing this?

    Thanks.


  22. Ronaldo

    9 years ago

    Dear Mikal,
    How do I record only $GPRMC on the memory card?


  23. Shelley

    8 years ago

    I have gps and openlog attached to the hardware serial pins and 16×2 lcd on other pins. Everything is running at baud rate of 57600 (I need a 5 Hz updated speed readings). Data is coming through ok but there is duplicate data showing up…for every 1/5 sec I get the same reading 20x’s. Is this a baud rate issue?


  24. W1BMW

    8 years ago

    Thanks for all your hard work on the libraries offered here! I’m using TinyGPS++ and an Argent Data radio shield for an APRS tracker. Your library made coding a snap!

    I had some problems initially that turned out to be a baud rate issue. The default value of 4800 baud must be changed to 9600 for the Adafruit Ultimate GPS Breakout Board, but the code worked right out of the box!

    73 de W1BMW


  25. Georges Payne

    8 years ago

    Hello Mikal,

    Noob here, in dire need of help!

    I have a Arduino Uno rev.3 and a Garmin 72 GPS unit. I familiarized myself with the Arduino environment by playing around with a few examples and by writing my own (simple) code also. Now I am trying to run the TinyGPSPlus DeviceExample code in order to grab data from the GPS. I have connected the Tx line from the GPS to pin #3 on the Arduino and the ground wire from the GPS to the GND pin next to pin 13. The GPS is correctly setup and using a terminal program on my PC, I can read the sentences just fine at 4800 baud.

    With the GPS unit connected to the Arduino, and without any modifications in the code, The program seems to hang after the credits in the beginning, right after “By Mikal Hart”. It does not say “No GPS, check wiring…” but it doesn’t proceed to the DisplayInfo loop either, because it doesn’t print “Location: “.

    The while loop doesn’t seem to be working, because if I disconnect the GPS it doesn’t go to “No GPS”.

    If I reset the Arduino with the GPS disconnected, it says “No GPS…” but if I reconnect the GPS without resetting the Arduino, nothing happens.

    I tried the debugging lines of code you provided in this page and I can see waves after waves of gibberish characters on the serial monitor.

    I also tried the checksum line, but wasn’t able to get any results with it.

    I have banged my head against this four nights in a row, but I am stuck. I live in a somewhat remote location, and I tried to see if there are any robotics clubs around, but couldn’t find anything.

    So I’m desperate. Any help, any help at all, would be greatly appreciated.

    Cheers!
    Georges


  26. Georges Payne

    8 years ago

    Hello Mikal,

    Never mind. A noob mistake, the Garmin GPS 72 output is Serial RS232, and the Arduino serial is TTL. I bought a 7$ RS232-TTL converter, and now I can read the phrases all right.

    Thanks anyway, your page was a tremendous help.

    Cheers!
    Georges


  27. Mikal

    8 years ago

    @Daniel C, are you sure the program you’re compiling is identical when you make the transition to 1.6.0? And all the libraries?


  28. Mikal

    8 years ago

    @Ronaldo, I think I would do that outside of TinyGPS. You are capturing the raw stream: just write what you need to SD.


  29. Mikal

    8 years ago

    @Shelley, depending on which sample app you’re running, it may print data every time a new sentence is parsed. But not every sentence brings fresh instances of the data you’re looking for. It’s not an error really, just a quirk. You could modify the sample to print only when the datum you seek actually changes.


  30. Mikal

    8 years ago

    @W1BMW, hey, thanks!


  31. Lespaul

    8 years ago

    Hello Mikal (Sorry, not good at English)
    I have used gr83 mudule gps with mega1280.
    I have taken from gr83 NEMA codes to enter the gps stream.

    const char * gpsStream =
      “$ GPRMC, 000118.050, V, 1335.5938, N, 10044.9498, E ,,, 160406 ,,, N * 70 \ r \ n”.
      “$ GPGGA, 000118.050,1335.5938, N, 10044.9498, E, 0,00 ,, – 25.9, M, -27.0, M ,, 0000 * 4B \ r \ n”;

    But the result is

    BasicExample.ino
    Basic demonstration of TinyGPS ++ (no device needed).
    Testing TinyGPS ++ library v. 0.92.
    by Mikal Hart

    Location: INVALID Date / Time: 4/16/2006 00: 01: 18.05.
    Location: INVALID Date / Time: 4/16/2006 00: 01: 18.05.

    Done.

    Help me please.


  32. KP

    8 years ago

    I want to just take some time to thank you for the great library! I’ve been using this library to parse non standard (custom) NMEA data from a weather station sensor (also includes a GPS in it).


  33. kostas stefani

    8 years ago

    Hello, i want to build a project that will have an arduino gps module on it, propably a shield that would also log the gps data. I would like to ask about the accuracy of the gps,is it a matter of hardware or software?? I mean if i use this library with a gps module that says it has an accuracy of 3m or an accuracy of 10m, will i get a much better accuracy with this library and a help of a magnetometer?


  34. Mikal

    8 years ago

    @KP, hey, thanks for that! So glad it’s useful for you.


  35. Mikal

    8 years ago

    Hi @Lespaul,

    The problem is that your two NMEA sentences indicate that you don’t have a good fix.

    The ‘V’ in field 3 of $GPRMC means “invalid”.
    The ’0′ in field 7 of $GPGGA means “no fix”.

    In this case TinyGPS++ discards all position, speed, course, or altitude data.


  36. Mikal

    8 years ago

    @kostas stefani,

    The software neither adds or subtracts accuracy. It reports exactly what the GPS module is reporting, only in a more convenient form.


  37. KP

    8 years ago

    Mikal,

    Is there already a built in function to get gps data (lat and lng) with 6 decimal as unsigned number? such as 90.123111 to 90123111?

    Thanks.


  38. Mikal

    8 years ago

    @KP, no, but you could synthesize it pretty closely with

    Serial.print(gps.location.rawLat().negative ? “-” : “+”);
    Serial.println(gps.location.rawLat().deg); // Raw latitude in whole degrees
    Serial.println(gps.location.rawLat().billionths);// … and billionths (u16/u32)

    This won’t be exactly correct, because small billionths” values won’t be left padded with zeros, but you could create this pretty easily.


  39. KP

    8 years ago

    Hey Mikal,

    Thanks for the information.

    This is what I ended up doing.

    latitudeUINT = (gps.location.rawLat().deg * pow(10, 6)) + (round((gps.location.rawLat().billionths) / 1000.000)) ; // combine degree and decimal
    longitudeUINT = (gps.location.rawLng().deg * pow(10, 6)) + (round((gps.location.rawLng().billionths) / 1000.000));


  40. artem

    8 years ago

    Hi.
    Try to use your library.
    I receive from GPS:
    5245.94146 —- 05548.84800
    but your library converts it to:
    52.765663 —- 55.814132

    I need original GPS strings. How to get it? Make example please.


  41. Mikal

    8 years ago

    @artem,

    The original strings contain the latitude and longitude in degrees/minutes form, or more precisely, DDMM.MMMMM. The library converts the values to decimal degrees.

    Always remember that you control the GPS strings before you send them to TinyGPS++. If you want the raw GPS string, just save it yourself before you send it on to TinyGPS.


  42. Mikal

    8 years ago

    @KP. Perfect. Although I would use the integral constant 1000000UL instead of the function pow(10, 6), which is a floating point number.


  43. Ron Koval

    8 years ago

    Mikal,

    I have been trying to use TinyGPSCustom steerDirection(gps, “GPRMB, 3); to get the R and L from my Garmin GPS. Indeed R and L are read, but the GPS seems extremely slow to update, indicate a necessary change from R to L or L to R.

    I see I can extract “course” (which I assume is the equivalent to “Track” on the Garmin display, but is there a way to extract “Bearing” which is the goto heading? I would hope that these would update very quickly as I notice on the Garmin display.

    Thanks in advance to your reply.


  44. Ron Koval

    8 years ago

    Mikal,

    I asked too quickly. Bearing is the 11th field of the $GPRMB sentence. So using Bearing and Course, I can determine R and L and hopefully much quicker than my Garmin analyzes and updates it.


  45. KP

    8 years ago

    Mikal,

    Is there any specific reason I should avoid using the pow other than it is a floating point? What does 1000000UL do and why declare as such?

    Also if it is better or more effective, could I replace all my pow usage to XXXUL?


  46. Sergey

    8 years ago

    Hello Help me pls i made sketch to extract depth value from nmea sentence:

    #include
    #include
    #include “TM1637.h”
    #define CLK 2
    #define DIO 3
    TM1637 disp(CLK,DIO);

    static const int RXPin = 10, TXPin = 11;
    static const uint32_t GPSBaud = 4800;

    // The TinyGPS++ object
    TinyGPSPlus gps;

    // The serial connection to the GPS device
    SoftwareSerial ss(RXPin, TXPin);

    TinyGPSCustom SDDPT(gps, “SDDPT”, 1); // $SDDPT sentence, 1 element

    void setup()
    {
    Serial.begin(4800);
    ss.begin(GPSBaud);

    disp.set(5);
    disp.init(D4056A);

    }

    void loop()
    {

    Serial.println(SDDPT.value());
    while (ss.available() > 0)
    gps.encode(ss.read());

    delay(20);
    }

    everything work fine but how can i extract numerical value of depth inside program to operate with it (i’m making downrigger)


  47. AlexTadeo

    8 years ago

    Hi mikal.
    I would like to know if ur library works with the gps A2235-H.


  48. Mikal

    8 years ago

    @Sergey, you should be able to add:

    long depth = atol(SDDPT.value());
    

  49. Mikal

    8 years ago

    @AlexTadeo,
    If that device uses the NMEA protocol, specifically GPGLL and GPRMC, I think it will work.


  50. Mitch

    8 years ago

    Thanks for this great library. It has saved countless hours on my Arduino based seven digit Nixie clock project. Timing is an issue here, I’m “feeding” for about 50ms for each loop. Then isValid() is checked until valid date and time data is available and if not, more feeding on the next loop. Baud rate for the GPS is 9600. The display is updated every 100ms now, but when I implement crossfading, display updating frequency will have to increase. Occasionally the display is interrupted by GPS data gathering. Is there a better way to do this? Thanks in advance.

29 Trackbacks For This Post
  1. TinyGPS++ to the Rescue | Stainless Steelhead

    [...] to the brains behind Arduiniana, Mikal Hart, Poolbot has moved to the brand-new GPS library set, TinyGPS++.  This saved enormous time in developing custom code to process and check the validity of NMEA [...]

  2. Antenna tracker, first steps | kolin's

    [...] or none, I made simple arduino program for parsing NMEA crap and encoding it in LTM packets. I used TinyGPS++ library for parsing NMEA and few lines from TauLabs [...]

  3. GPS Ublox Neo-6M cu Arduino Uno | ArduHobby

    [...] Descarcati biblioteca tinyGPS sau tinyGPS++. [...]

  4. GPS-Logger | Pascal's Königreich

    [...] Card Breakout Board gibt’s bei Adafruit, um mit dem GPS Modul zu sprechen wurde die Library TinyGPS++ [...]

  5. GPS Distance Calculator (for golf) -Use Arduino for Projects

    [...] Tiny GPS++ [...]

  6. Arduino GPS with OLED Display | Home of Benty

    [...] OLED from Adafruit. It’s still a work in progress just squishing together code from the TinyGPS++ library and using the Adafruit GFX [...]

  7. SpainLabs - Mantener tus proyectos en hora

    [...] Con Arduino puedes usar la librería tyniGPS++. [...]

  8. Prototype 1 – GPS Module | A Mean Center

    [...] something useful with it. This isn’t due to any competence on my part, but because of  the TinyGPS++ library by Mikal Hart which is just amazing. There are many examples included with the library, so it is [...]

  9. Unexpected behavior of sprintf with i32/u32 | CL-UAT

    [...] trying to build a string of characters from several elements given by the TinyGPS++ library with the use of [...]

  10. Connecting u-blox NEO-6M GPS to Arduino | Big Dan the Blogging Man

    [...] http://arduiniana.org/libraries/tinygpsplus/ [...]

  11. LatLong to XY | Rocket Project

    [...] the same. latlon2xy is the doc with the Arduino code. Since I last looked at GPS, Mikal Hart has an updated GPS library that computes distanceBetween() and courseTo(). It might be worth pursuing. Share [...]

  12. با برد آردوینو و شیلد GPRS دستگاه ردیاب کوچک و کارآمد بسازید | رایانش نیوز

    [...] این کتابخانه را برای استفاده از برد GPS دانلود کنید. سپس کدهای [...]

  13. Shield GPS Ublox NEO-6M – Programación con Arduino MEGA 2560 – Tecno-fly C.A

    [...] http://arduiniana.org/libraries/tinygpsplus/ [...]

  14. Leyendo datos del GPS – OCEANO ABIERTO

    [...] Arduino que nos permite convertir esas cadenas de caracteres en valores fácilmente interpretables: TinyGPSplus. Tendremos que descargar el archivo .zip de la última versión e instalarlo manualmente en nuestro [...]

  15. Lightweight Module for Collecting Stratospheric Microbes | HENRY-1 HAB MISSION

    [...] RBBB was programmed with Arduino’s IDE and includes both the TinyGPS++ and Arduino Servo libraries. The TinyGPS library is very effective at parsing NMEA GPS data [...]

  16. How to make a GPS Speedometer? – DFRobot

    [...] following library ‘s in your Arduino Library Folder. U8glib – For the oled display. TinyGps++ – For the GPS. The code is “printing” the speed, course, number of satellites, [...]

  17. IoT WiFi Boat Monitor | Mechinations

    [...] Next, grab the starting source code. You will also need to install the TinyGPS++ library. [...]

  18. Adding Location to Microcontroller Projects: GPS Tutorial | Teach Me Micro

    [...] levels hence a voltage divider is needed to step down the voltage from the Arduino.You can use the TinyGPS++ library for easier Arduino GPS interfacing. Here's an example sketch from the library (modified to fit [...]

  19. Using Seeeduino LoRaWAN with GPS and Loriot.io – Squix – TechBlog

    [...] temperature and humidity we have to install two libraries. Download the TinyGpsPlus library from http://arduiniana.org/libraries/tinygpsplus/ Then install also the DHT library from Adafruit from the library manager in the Sketch > [...]

  20. GPS CLOCK with M5STACK | macsbug

    [...]  TinyGPS++ [...]

  21. Guide to NEO-6M GPS Module Arduino | Random Nerd Tutorials

    [...] to get information on location in a format that is useful and easy to understand. You can click here for more information about the TinyGPS++ [...]

  22. GPS With Arduino Tutorial | How To Interface GPS With Arduino using tiny gps++

    [...] Tiny GPS Library Download Table of Contents1 How to Interface GPS with Arduino Uno2 GPS  Arduino Code Display on Serial Monitor3 How to Display Longitude and Latitude on LCD3.1 16×2 LCD and Arduino Connection4 Arduino GPS LCD Code5 GPS Arduino Projects [...]

  23. GPS Tutorial–Sending GPS Coordinates over GSM | alselectro

    [...] http://arduiniana.org/libraries/tinygpsplus/ [...]

  24. GY-NEO6MV2 GPS Module – Mr. Robotrick

    [...] tiny GPS Module can connect to 4 Sattelite and it is pretty accurate. The library I use to interact with this module makes getting coordinates very easy., just add it to your [...]

  25. GPS Neo-6M com Arduino - Aprenda a usar - Blog Eletrogate

    [...] Biblioteca TinyGPS++ Avaliações: 5.0. de 1 voto. Por favor, aguarde…{"item":{"entity":"posts","name":"post","id":3185,"item_id":74,"nonce":"60e8e7599d"},"render":{"args":{"echo":false,"entity":"posts","name":"post","item_id":null,"id":3185,"method":"stars-rating","series":null},"method":{"disable_rating":false,"allow_super_admin":true,"allow_user_roles":["administrator","editor","author","contributor","subscriber"],"allow_visitor":true,"allow_author":false,"template":"default","alignment":"center","responsive":true,"distribution":"normalized","rating":"average","style_type":"font","style_name":"star","style_size":30,"font_color_empty":"#cccccc","font_color_current":"#ffcb05","font_color_active":"#ffd016","style_class":"","labels":["Pu00e9ssimo","Ruim","Bom","u00d3timo","Excelente"]}},"stars":{"max":5,"resolution":100,"responsive":true,"current":100,"char":"s","name":"star","size":30,"type":"font"},"labels":["Pu00e9ssimo","Ruim","Bom","u00d3timo","Excelente"]} [...]

  26. Wio LTEで遊んでみる(その5:3軸デジタル加速度センサーとGPS) | IT技術情報局

    [...] が、これだけだと読みにくい。 なので、上記のサイトをそのまま参考にTinyGPS++」を使用して読みやすくする。 [...]

  27. Cara Menggunakan GPS Ublox Neo 6M + Arduino – Coretan Aja

    [...] http://arduiniana.org/libraries/tinygpsplus/ http://geekistuff.blogspot.com/2014/06/advance-u-blox-neo-6m-gps-module.html Bagikan ini:TwitterFacebookGoogleSukai ini:Suka Memuat… [...]

  28. Using the GT-U7 GPS module based on u-blox 7th generation GPS chip – Pseudo Random

    [...] http://arduiniana.org/libraries/tinygpsplus/ [...]

  29. In-Depth: Interface ublox NEO-6M GPS Module with Arduino

    [...] to Mikal Hart for his great contribution. His website Arduiniana.org has a full overview of all of the capabilities of the TinyGPS++ [...]

Leave a Reply