GPS Monitor für Geo-Cacher - [Teil 1]

Hallo en welkom bij een nieuwe projectreeks.

Dit keer willen we omgaan met het spannende gebied van het Global Positioning System (GPS). In het eerste deel van de meerdelige serie bouwen we een kosteneffectief en mobiel LCD GPS-display dat een grote hulp is voor geocachers bij het zoeken naar geocaches.

Geocaching

Geocaching, ook bekend als GPS-speurtocht in Duitstalige landen, is een soort speurtocht die zich aan het einde van de 20e eeuw begon te verspreiden. De schuilplaatsen worden op internet gepubliceerd op basis van geografische coördinaten en kunnen vervolgens worden doorzocht met een GPS-ontvanger.

Bron: Wikipedia

De structuur bestaat uit de volgende 3 hoofdcomponenten:

Nummer

Component

Annotaties

1

HD44780 2004 LCD-displaybundel 4x20 tekens met I2C-interface voor Arduino

 

1

NEO-6M GPS-module

 

1

Nano V3.0 CH340-chip gesoldeerd, verbeterde versie met USB-kabel

 

 

De volgende tijd- en plaatsinformatie wordt op het display weergegeven:

 

Afkortingen

Benaming

Aanvullende informatie

Oud

Hoogte

Hoogte boven water

S

Satelliet

Satelliet in gebruik

C

Kurs

Cursus (graden)

LATT

Geografische breedte

 

LON

Geografische lengte

 

GS

Grundgeschwindigkeit

Snelheid

20.01.2010 19:49

Datum / tijd

 

 

LCD-scherm met GPS-gegevens

(Beeld LCD-weergave in gebruik (fictuele gegevens ( gewijzigde gegevens) )

Voordat de volgende code kan worden gecompileerd en uitgevoerd, hebben we twee nieuwe bibliotheken nodig.

De eerste bibliotheek, TinyGPS ++, is een Arduino-bibliotheek voor het ontleden van NMEA-gegevensstromen die worden geleverd door GPS-modules. Zoals al de voorganger van de bibliotheek, biedt TinyGPS veel eenvoudig te gebruiken methoden voor het extraheren van positie, datum, tijd, hoogte, snelheid en koers.

De bibliotheek TinyGPS ++ kan worden gedownload op GIT Hub: https://github.com/mikalhart/TinyGPSPlus/releases

De LiquidCrystal I2C-bibliotheek van Frank de Brabander is ook nodig om het IC2-LCD-scherm te besturen. Dit is direct te vinden en geïnstalleerd via de Bibiothek-beheerder onder de keu "LiquidCrystal I2C":

LiquidCrystal I2C van Frank de Brabander

Na de voorbereidingen van de IDE kan de hardware worden bekabeld:

Interconnectie van de afzonderlijke componenten

 

Daarna kan de volgende code worden geüpload:

 

#include <LiquidCrystal_I2C.h>
#include <Software.h>
#include <TinyGPS++.h>
LiquidCrystal_I2C lcd(0x27, 20, 4); // Stel het LCD-adres in op 0x27 voor een 20-gordel en 4-lijn display

TinyGPSPlus gps;
Software ss(4, 3);

leather instellen()
{   Serie.beginnen(9600);   lcd.init();                      // Initialiseer LCD   lcd.init();   lcd.achtergrondverlichting();   lcd.setCursor(0, 0);   lcd.duidelijk();   ss.beginnen(9600);   smartdelay(1);
}

nietig lus()
{   als (gps.hoogte.is geldig())   {     als (gps.hoogte.is bijgewerkt() || gps.satellieten.is bijgewerkt() || gps.natuurlijk.is bijgewerkt() )     {       lcd.setCursor(0, 0);       lcd.afdrukken("Oud:");       lcd.afdrukken(gps.hoogte.meter()); // Hoogte in meters (dubbel)       lcd.afdrukken("m");       lcd.afdrukken("S:");       lcd.afdrukken(gps.satellieten.waarde()); // Aantal gebruikte satellieten (u32)       lcd.afdrukken("C:");       lcd.afdrukken(gps.natuurlijk.deg()); // Cursus in graden (dubbel)     }   } anders   {     lcd.setCursor(0, 0);     lcd.afdrukken("Geen geldige gegevens");   }   als (gps.locatie.is geldig())   {     als (gps.locatie.is bijgewerkt())     {       lcd.setCursor(0, 1);       lcd.afdrukken("LAT:");       lcd.afdrukken(gps.locatie.lat(), 4); // Ruwe breedtegraad       lcd.afdrukken("LNG:");       lcd.afdrukken(gps.locatie.lng(), 4); // Ruwe lengtegraad     }   } anders   {     lcd.setCursor(0, 1);     lcd.afdrukken("Geen geldige locatie");   }   als (gps.date.is geldig() & gps.date.is geldig())   {     lcd.setCursor(0, 2);     lcd.afdrukken(gps.date.dag());     lcd.afdrukken(".");     lcd.afdrukken(gps.date.maand());     lcd.afdrukken(".");     lcd.afdrukken(gps.date.jaar());     lcd.afdrukken(" ");     lcd.afdrukken(gps.tijd.uur() + 1);     lcd.afdrukken(":");     lcd.afdrukken(gps.tijd.minuut());     lcd.afdrukken("    ");   } anders   {     lcd.setCursor(0, 2);     lcd.afdrukken("Geen geldige tijdstempel");   }   als (gps.snelheid.is geldig())   {     lcd.setCursor(0, 3);     lcd.afdrukken("GS:");     lcd.afdrukken(gps.snelheid.kmph());     lcd.afdrukken("km / h");     lcd.afdrukken(gps.snelheid.knopen()); // Snelheid in knopen (dubbel)     lcd.afdrukken("kt");   } anders   {     lcd.setCursor(0, 3);     lcd.afdrukken("Geen geldige snelheidsgegevens");   }   smartdelay(5000);
}

statisch nietig smartdelay(niet ondertekend lang ms)
{   niet ondertekend lang start = millis();   doen   {     terwijl (ss.beschikbaar())       gps.coderen(ss.lezen());   } terwijl (millis() - start < ms);
}

 

Na het inschakelen wordt een initialisatiescherm weergegeven:

Weergave tijdens initialisatie

 

Na ontvangst van een geldig GPS-signaal (blauwe LED van de GPS-module knippert), worden de geo-informatie en tijdgegevens weergegeven:

Weergave van de geëvalueerde GPS-gegevens

(fictieve gegevens / gegevens gewijzigd)

Ik hoop dat je geniet van de replica.

Zoals altijd kun je alle projecten vinden op de GitHub-pagina https://github.com/kuchto

 

DisplaysFür arduinoProjekte für anfänger

21 Kommentare

Ulrich Engel

Ulrich Engel

Ich habe das GPS-Modul gewechselt. Nun funktioniert es. Scheinbar ist der Chip kaputt und GPS-Daten werden nicht gelesen.
Nun habe ich auch ein Micro-SD-Card-Modul zugebaut und es werden jetzt zusätzlich die GPS-Daten (Long, Lat, Alt) auf SD geschrieben. Damit kann man dann die Route mit Google Earth darstellen.

Ulrich Engel

Ulrich Engel

Hallo, ich bin noch Programmierer-Einsteiger.
Nachdem ich das Projekt “Monitor 1” mit dem Nano erfolgreich nachgebaut habe (es funktioniert schnell und gut), habe ich nun den NANO durch einen UNO ersetzt. Plan ist: Noch ein Data-Logging mit SD-Card zu ergänzen.
Leider habe ich aber schon gleich ein Problem. Anders als mit dem Nano wird nur mit UNO Datum und Uhrzeit angezeigt. Bei den beiden anderen Zeilen steht weiter “No valid ………..”.
Mache ich etwas falsch? Der Sketch ist der gleiche, wie bei Monitor-1 (Teil1 ohne Target).
SCL→A5, SDA→A4 und UNO-RXPin D4 und UNO-TXPin D3.
Freue mich über zeitnahe Unterstützung.

Wolfhard Jording

Wolfhard Jording

Bei mir hat das erst funktioniert, als ich folgende Arduino IDE Einstellung gemacht habe:
Einstellungen unter Werkzeug
Board: Arduino Nano
Processor: Atmega328P (Old Bootloader)
Ich habe einen Az-Delivery Nano V3 benutzt. Vorher hatte ich immer ein Fehler beim hochladen des Sketches.

Thomas

Thomas

@Siegfried
Habe den Fehler gefunden.
Habe die Bibliothek gelöscht und noch mal installiert.
Jetzt gehts!

Siegfried Pappert

Siegfried Pappert

Nachtrag zum Nachtrag:
Jetzt gibt es das gleiche Problem wie bei Ralf:
Ich hatte im Nachtrag die ersten Zeilen von Tobias sketch eingefügt. Allerdings sieht das Ganze nach der Veröffentlichun hier im Blog genauso aus, wie bei Ralf: die Zeichen nach include fehlen einfach, obwohl diese hier im Eingabefenster zu sehen waren. Dies als Hinweis für den Administrator hier. Kann das behoben werden?
Ich tippe die Zeilen jetzt noch mal selber hier ab (also nicht copy paste). mal sehen, ob das dann funktionert.
#include
#include
#include <TinyGPS++.h>

und jetz nochmal copy paste (für den Admin zum Vergleich):
#include
#include
#include <TinyGPS++.h>

Siegfried Pappert

Siegfried Pappert

Nachtrag: Im Sketch von Ralf fehlen ein paar Zeichen oberhalb des #include <TinyGPS++.h>
müßte so lauten:
#include
#include
#include <TinyGPS++.h>
Siehe auch Original Sketch von Tobias.

Siegfried Pappert

Siegfried Pappert

@Thomas:
Hast du die “LiquidCrystal_I2C” ordnungsgemäß über den Bibliotheksverwalter (Menüpunkt Sketch) hinzugefügt?
In welchem Ordner steht denn das eigentliche Programm (sketch .ino)?
Was ist die “WProgramm.h”? Sollte so nicht im Sketch des eigentlichen Programms stehen. Finde ich zuminest nicht im Sketch von Ralf.
Hast du die Arduino IDE auf dem Rechner installiert oder startest du das Programm ohne Installation über die .exe (non admin) Installation?
Ich hatte ein ähnliches Problem, kann es aber momentan nicht mehr ganz nachstellen. Es hing damit zusammen, dass Arduino die libraries am liebsten im von der IDE vorgeschlagenen Ordner hat und ich die einzubindenden Bibliotheken woanders gespeichert hatte.

Thomas

Thomas

Hallo zusammen,
bekomme beim Kompilieren immer diese Fehlermeldung.
Arduino: 1.8.12 (Windows 7), Board: “Arduino Nano”

C:\Users\Thomas\Documents\Arduino\libraries\LiquidCrystal_I2C\LiquidCrystal_I2C.cpp:4:10: fatal error: WProgram.h: No such file or directory

#include “WProgram.h” ^~~~~~~~~~~~

compilation terminated.

exit status 1
Fehler beim Kompilieren für das Board Arduino Nano.

Was mache ich Falsch?

Siegfried Pappert

Siegfried Pappert

OK, ich denke ich habe den Fehler gefunden. 0,001 Minnuten entsprechen damit ca. 1,2 m (50° nördlicher Breite). Was dann wieder Sinn macht.

Siegfried Pappert

Siegfried Pappert

Hallo Ralf,
vielen Dank für die Anpassung des Sketches. Ich hab das mal so übernommen (nach etwas Formatierungsarbeit…). Mittelweile habe ich auch anhand deines Sketches verstanden, wie ich die Nachkommastellen ändern kann, was ich dann auch für die Geschwindigkeitsangabe gemacht habe (zwei Nachkommastellen braucht es nicht…).
Eine Frage zur Genauigkeit: Reichen den Geocachern 3 Nachkommastellen? Das ist eine Auflösung von ca. 70 Metern, wenn ich das richtig gerechnet habe. Kommt mir viel vor.
Gruß Siegfried

Ralf Kastmann

Ralf Kastmann

Hier ein Sketch mit Umrechnung der Breiten- und Längen in Grad und Minuten mit 3 Nachkommastellen, so wie es Geocacher (wie ich) gebrauchen.
Gruss Ralf

/*

Anzeige: LCD 20 Charakter/Zeile; 4 Zeilen Anschluss I2C über SDA auf A4 und SCL auf A5 Versorgung GND und VCC=5V GPS-Modul; NEO-6M NEMA-Datenströme über SoftwareSerial mit RX auf D3 und TX auf D4 Versorgung GND und VCC=5V Arduino Nano Definiert in IDE über “Duemilanove oder Diecimilia” auf COM10 (kann sich aber ändern) Gilt für Nördliche Breiten und östliche Längen. Nicht getestet für Südliche Breiten und westliche Längen. Ausgabe auf LCD-Display und Seriellen Monitor Aufgesetzt und getestet: 27.2.2020 R.Kastmann
*/

#include
#include
#include <TinyGPS++.h>

LiquidCrystal_I2C lcd(0×27, 20, 4); // LCD-Display auf Adresse 0×27 mit 20 Zeichen und 4 Zeilen

TinyGPSPlus gps;
SoftwareSerial ss(4, 3);

int Lat_Grad;
int Lon_Grad;
double Lat_Min;
double Lon_Min;

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

lcd.init(); // Initalisiere LCD lcd.backlight(); lcd.setCursor(0, 0); lcd.clear(); ss.begin(9600); smartdelay(1); Serial.println(""); Serial.println(""); Serial.println("");

}

void loop()
{
Serial.println("");

// Abfrage und Ausgabe von Datum und Uhrzeit -———————————————— if (gps.date.isValid() & gps.time.isValid()) { Serial.print(gps.date.day()); Serial.print(“/”); Serial.print(gps.date.month()); Serial.print(“/”); Serial.print(gps.date.year()); Serial.print(" "); Serial.print(gps.time.hour() + 1); //Winterzeit +1, Sommerzeit +2 Serial.print(“:”); Serial.print(gps.time.minute()); Serial.println(" "); lcd.setCursor(0, 0); lcd.print(gps.date.day()); lcd.print(“/”); lcd.print(gps.date.month()); lcd.print(“/”); lcd.print(gps.date.year()); lcd.print(" "); lcd.print(gps.time.hour() + 1); //Winterzeit lcd.print(“:”); lcd.print(gps.time.minute()); lcd.print(" "); } else { Serial.println(“No valid Timestamp”); lcd.setCursor(0, 0); lcd.print("No valid Timestamp "); } // Abfrage, Umrechnung und Ausgabe von Breite und Länge -———————————— if (gps.location.isValid()) { if (gps.location.isUpdated()) { Lat_Grad = gps.location.lat(); //Breite in Grad Lat_Min = ((gps.location.lat())-Lat_Grad)*60; //Breite in Minuten mit 3 Nachkommastellen Lon_Grad = gps.location.lng(); //Länge in Grad Lon_Min = ((gps.location.lng())-Lon_Grad)*60; //Länge in Minuten mit 3 Nachkommastellen Serial.print(“N”); Serial.print(Lat_Grad); Serial.print("° "); Serial.print(Lat_Min,3); Serial.print(" "); Serial.print(“E”); Serial.print(Lon_Grad); Serial.print("° "); Serial.print(Lon_Min,3); Serial.println(" "); lcd.setCursor(0, 1); lcd.print(“N”); lcd.print(Lat_Grad); lcd.print(" "); lcd.print(Lat_Min,3); lcd.print(" E"); lcd.print(Lon_Grad); lcd.print(" "); lcd.print(Lon_Min,3); } } else { Serial.println(“No valid Location”); lcd.setCursor(0, 1); lcd.print("No valid Location "); } // Abfrage und Ausgabe von Höhe, Anzahl gefundener Sateliten und Richtung -———————- if (gps.altitude.isValid()) { if (gps.altitude.isUpdated() || gps.satellites.isUpdated() || gps.course.isUpdated()) { Serial.print(“Alt:”); Serial.print(gps.altitude.meters(),0); // Altitude in meters (double) Serial.print(" m "); Serial.print(“Sat:”); Serial.print(gps.satellites.value()); // Number of satellites in use (u32) Serial.print(" Course:"); Serial.print(gps.course.deg(),0); // Course in degrees (double) Serial.println(“°”); lcd.setCursor(0, 2); lcd.print(“Alt:”); lcd.print(gps.altitude.meters(),0); // Altitude in meters (double) lcd.print(“m”); lcd.print(" S:"); lcd.print(gps.satellites.value()); // Number of satellites in use (u32) lcd.print(" C:"); lcd.print(gps.course.deg(),0); // Course in degrees (double) lcd.print(" "); } } else { Serial.println(“No valid Altitude”); lcd.setCursor(0, 2); lcd.print("No valid Altitude "); } // Abfrage und Ausgabe der Geschwindigkeit in km/h und Knoten -—————————- if (gps.speed.isValid()) { Serial.print("Speed: "); Serial.print(gps.speed.kmph()); Serial.print(" km/h / "); Serial.print(gps.speed.knots()); // Speed in knots (double) Serial.println(" knots"); lcd.setCursor(0, 3); lcd.print(“GS:”); lcd.print(gps.speed.kmph()); lcd.print("km/h "); lcd.print(gps.speed.knots()); // Speed in knots (double) lcd.print("kt "); } else { Serial.println(“No valid Speeddata”); lcd.setCursor(0, 3); lcd.print("No valid Speeddata "); } smartdelay(5000);

}

static void smartdelay(unsigned long ms)
{
unsigned long start = millis();
do
{
while (ss.available())
gps.encode(ss.read());
} while (millis() – start < ms);
}

Ralf Kastmann

Ralf Kastmann

Ich habe das mal nachgebaut und bin ein wenig enttäuscht über die Schluderigkeit, wie das Ganze aufgesetzt wurde.
1. Das fritzing-Model hat einige Fehler. Erstmal ist definitiv das I2C-Modul falsch herum an das LCD-Display geklemmt (siehe Claas) und das GPS-Modul hat die Kabelreihenfolge GND, TX, RX, VCC. Und TX wird auf D4 und RX auf D3 gelegt (wie bereits von Bernd bemerkt).
2. Im Sketch wurden Kommentare äusserst spartanisch – nach dem Motto: der Code erklärt sich von selbst – verteilt. Sprich: es wurde eigentlich nichts erklärt. Spätestens hier im oberen Teil hätte ein Block hingehört, welches genau die Kontaktbelegung am NanoV3 beschreibt.
Immerhin, nachdem das alles geklärt war, hat es auch bei mir so funktioniert wie beschrieben. Als Geocacher ist das alles aber noch weit entfernt von einem praxistauglichem Gerät, wie man es sich eigentlich wünscht. Das wäre: Eingabe der Sollkoordinaten, Messung der Istkoordinaten und Anzeige der Entfernung und der Richtung. Aber daran arbeite ich.

Rudolf Reiber

Rudolf Reiber

Wie schon Pappert anmerkte, ist die Genauigkeitsangabe auf zwei Dezimalen völliger Unsinn. Das Teil misst ja nicht mal auf Meter genau. Ich habe das Anzeigenproblem bei meinem GBS-Tracker für das WoMo folgendermaßen gelöst:
1. Runden des Höhenmesswertes auf Meter (Umwandlung in INT)
2. Mit z.B. diesem Code kann man eine stellenrichtige Anzeige auf dem LCD erreichen. (Und ja, ich war letztes Jahr auf unter 0 Meter :-))
###############################
lcd.setCursor(2,2);
if (hoehe >= 0)
{
if (hoehe < 10) lcd.print(" “);
else if (hoehe < 100) lcd.print(” “);
else if (hoehe < 1000) lcd.print(” “);
else if (hoehe < 10000) lcd.print(” “);
}
else
{
if (hoehe <= -10) lcd.print(” “);
else lcd.print(” ");
}
lcd.print(hoehe);

J. Schmidt

J. Schmidt

Das Projekt läßt sich gut nachbauen.
Die Daten werden nach dem Einschalten recht schnell gefunden.
Die Darstellung sollte aber in Grad und Bogenminute mit 3 Nachkommastellen erfolgen, so wie bei den meisten GPS-Geräten.
Die Erweiterung des Codes in dieser Richtung würde das Projekt perfekt machen.
Gruß

Pappert

Pappert

Schönes Projekt. Vielen Dank dafür. Aufbau hat prima geklappt.
Die Darstellung läßt sich sicher noch verbessern. Bei den Schwankungen der Höhenmeter reicht sicher die Genauigkeit in m und man könnte auf die beiden Nachkommastellen (also Genauigkeit cm) verzichten. Wäre ohne hin sinnvoll, da bei 3-stelligen Werten (vor dem Komma) beim Kurs (in der gleichen Zeile ganz rechts) dann nur noch 1 oder 2 Stellen angezeigt werden, statt der benötigten 3 Stellen. Weiß jemand, wo man da im sketch ansetzen muß? Ich denke der Wert wird aus der TinyGPS++.h übernommen.
Gleiches gilt für die Uhrzeit. EIne Darstellung der einstelligen Stunden und Minuten mit einer vorangestellten Null (also z.B. 08:01 statt 8:1) wäre schön.

Dieter Pahl

Dieter Pahl

Das ist ein wunderbares Projekt. War schnell aufgebaut und nach Monitoranpassung sofort lauffähig.
Die Genauigkeit ist erstaunlich: Lagefehler nach 30 Min. Laufzeit unter 10m; Höhenfehler ca. 5m.
Damit ist der Aufbau praxistauglich. Jetzt noch ein schickes Gehäuse und ab ins Gelände.
Danke für das Projekt!
mit freundlichen Grüßen – Dieter

Claas

Claas

Hallo,
ich habe die Teile gekauft. Bin aber jetzt verwirrt, da mein Eindruck ist, dass die Verkabelung zwischen FC-113 und dem Display in diesem Artikel falsch dargestellt ist. In der PDF Anleitung und auf anderen Seiten im Internet ist das FC-113 Modul anders gedreht verkabelt (I2C Anschlüsse sollten zur Seite schauen und nicht in die Mitte). Bitte überprüft das. Danke!

Bernd Markscheffel

Bernd Markscheffel

Das aktuell verkaufte Modul (14.02.20) hat eine rote LED, und blinkt nur bei Empfang eines gültigen Signals (kein Dauerleuchten, wie in einigen Beschreibungen, beim Warten auf das Signal) . Ich habe das Modul an einen Arduino UNO angeschlossen. RX des GPS an Pin 3 und TX an Pin 4. Funktioniert prima, Im Büro unterm Dach 9 Sats. Danke an Tobias fürs Teilen !

Viele Grüße
Bernd

Walter

Walter

Hallo Herr Kuch,
könnte man beide Anzeigen auch trennen ? Ich würde es besser finden, wenn man auf dem einen Display die Daten des/der Satelliten hätte, und auf dem 2 Display Zeit, Geschwindigkeit usw…..denn beim cachen ist mir der ORT wesentlich wichtiger.

Bernhard

Bernhard

Perfekt wäre der Code, wenn man die Längen- und Breitengrade noch in Grad/Minuten/Sekunden anzeigen könnte.

Also nicht 9.50000 Grad sondern 9° 30 min und so weiter.
Weiss jemand mehr dazu?

Hermann Zakovsek

Hermann Zakovsek

Ist die Zeile (ca 35 in loop()):
if (gps.date.isValid() & gps.date.isValid())
oder sollte es
if (gps.date.isValid() & gps.time.isValid())
heisen?

Einen Kommentar hinterlassen

Alle Kommentare werden vor der Veröffentlichung moderiert

Aanbevolen blog berichten

  1. Installeer ESP32 nu van de raad van bestuur
  2. Lüftersteuerung Raspberry Pi
  3. Arduino IDE - Programmieren für Einsteiger - Teil 1
  4. ESP32 - das Multitalent
  5. OTA - Over the Air - ESP Programmeren via Wi-Fi