1

I have the MKR 1010 and am working on a circuit that needs realtime GPS positioning. I bought the MKR GPS Shield, and am using it on the I2C bus (attached via cable to the 1010 board), and am using the Arduino_MKRGPS library in my sketch.

I am attempting VERY basic interaction with the board at the moment, and basically just want to print out the GPS coordinates to the serial.

I am using the GPSLocation sample from the Arduino_MKRGPS library (see here):

  /*
  GPS Location

  This sketch uses the GPS to determine the location of the board
  and prints it to the Serial monitor.

  Circuit:
   - MKR board
   - MKR GPS attached via I2C cable

  This example code is in the public domain.
*/

#include <Arduino_MKRGPS.h>

void setup() {
  // initialize serial communications and wait for port to open:
  Serial.begin(9600);
  while (!Serial) {
    ; // wait for serial port to connect. Needed for native USB port only
  }

  // If you are using the MKR GPS as shield, change the next line to pass
  // the GPS_MODE_SHIELD parameter to the GPS.begin(...)
  if (!GPS.begin()) {
    Serial.println("Failed to initialize GPS!");
    while (1);
  }
}

void loop() {
  // check if there is new GPS data available
  if (GPS.available()) {
    // read GPS values
    float latitude   = GPS.latitude();
    float longitude  = GPS.longitude();
    float altitude   = GPS.altitude();
    float speed      = GPS.speed();
    int   satellites = GPS.satellites();

    // print GPS values
    Serial.print("Location: ");
    Serial.print(latitude, 7);
    Serial.print(", ");
    Serial.println(longitude, 7);

    Serial.print("Altitude: ");
    Serial.print(altitude);
    Serial.println("m");

    Serial.print("Ground speed: ");
    Serial.print(speed);
    Serial.println(" km/h");

    Serial.print("Number of satellites: ");
    Serial.println(satellites);

    Serial.println();
  }

  delay(100);
}

What I'm seeing is that the GPS takes on the order of 30-90 secs to initialize, and then only provides new updated coords every 20-30 secs. This is all with a clear view of the sky.

Is that really what to expect from this module? I was under the impression that it could provide several samples per second. Documentation seems to be very lacking for the Arduino_MKRGPS library. Anyone else have insights or experience with this module?

Thanks!

1 Answer 1

1

It seems that the problem with the GPS was caused by my usage of the arduino delay(...) method in my loop.

I'm assuming that by using delay, the connection to the GPS module was being severed, and in effect, every loop was forcing a reconnect and a new download of satellite details.

In summary, when needing high sample frequency interaction with the GPS, using delay in the sketch won't work.

EDIT:

I've done a lot of digging since originally posting this question/answer and wanted to add my findings for others that are struggling to make the MKR GPS module work for higher than 1Hz sample rate use cases.

I had to make the following two changes to the Arduino_MKRGPS library:

  1. increase baud rate of the GPS connection. In the very last line of GPS.cpp...
GPSClass GPS(Serial1, 460800, serialDDC, 400000, 7);
  1. In GPS.h, make the sendUbx method a public member of the GPS class. This allows me to send low-level commands to the SAM-M8Q from my sketch.

After this, I can construct low-level messages in my sketch and configure the GPS to my liking. Here's what I did to increase the sample rate to 3Hz in my sketch's setup method:

  Serial.println("Configuring GPS refresh rate...");

  //  UBX-CFG-RATE (0x06 0x08) Navigation/Measurement Rate Settings
  //  See UBX-13003221 section 32.10.23.1
  byte payload[6];

  memset(payload, 0x00, sizeof(payload));

  uint16_t measRate = 333;    // ms between gps data publish  (min of 100)
  uint16_t navRate  =   1;    // ratio between measurements and nav solution calculations
  uint16_t timeRef  =   1;    // The time system to which measurements are aligned (0: UTC, 1:GPS, ...)

  // write out the unsigned shorts in little-endian form
  payload[0] = measRate & 0xff;   
  payload[1] = (measRate >> 8) & 0xff;   
  payload[2] = navRate & 0xff;
  payload[3] = (navRate >> 8) & 0xff;
  payload[4] = timeRef & 0xff;
  payload[5] = (timeRef >>8) && 0xff;

  GPS.sendUbx(0x06, 0x08, payload, sizeof(payload));

  Serial.println("  > done");

Hope this helps someone else struggling with higher data rate use cases. There's still room for improvement, I think, in particular by reducing the number of sentences returned by the GPS. I haven't been able to get the sample rate higher than 5Hz, while technically the GPS is supposed to be capable of doing 10Hz. I'm not sure where the bottleneck is.

2
  • Can you post your entire code. The delay can cause some problems mainly because the data is streaming into a buffer and it is supposed to be either read or processed almost immediately depending on the buffer size. I checked the library and the I2C example is built over the UART library and it might be acting up. With UART it is usually pretty straightforward and you should be able to see streaming data coming from the GPS multiple times a second
    – karan
    Sep 23, 2019 at 8:33
  • I edited my original post to include the entire sketch. It's the sample called "GPSLocation" included in the Arduino_MKRGPS library, with the simple addition of the delay statement at the end of the loop. Sep 25, 2019 at 15:31

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.