Capability - NMEA
Capability Identifier:
https://tildagon.badge.emfcamp.org/capabilities/registry/nmea/
Gives access to NMEA 0183 sentences, detailing GPS fix information.
Note: Do not use this for finding user position in general, use the position capability instead. This is only for detailed introspection of GPS data.
The sentences attribute contains a non-exhaustive list of received NMEA sentences, with the checksums stripped.
Consumers
Find an implementor of the nmea capability from the currently running apps. This application will have a sentences attribute, which contains a list of recently recevied sentences. You must not modify that list.
class NMEAConsumerApp(App):
def __init__(self):
pass
def update(self, delta):
position = None
gps_apps = get_running_apps_by_capability(
"https://tildagon.badge.emfcamp.org/capabilities/registry/"
"nmea/"
)
if not gps_apps:
return
# We only need to consider a single GPS receiver
gps_app = gps_apps[0]
for sentence in gps_app.sentences:
fields = sentence.split(",")
# Ignore the talker id prefix
sentence_type = fields[0][-3:]
if sentence_type == "RMC" and fields[2] == "A":
# Status "A" means the fields below are valid (not "V" = void).
time_field = fields[1] # hhmmss(.sss)
date_field = fields[9] # ddmmyy
hour = time_field[0:2]
minute = time_field[2:4]
second = time_field[4:6]
day = date_field[0:2]
month = date_field[2:4]
year = date_field[4:6]
print("UTC: 20{}-{}-{} {}:{}:{}".format(
year, month, day, hour, minute, second
))
elif sentence_type == "GGA" and fields[6] != "0":
# Fix quality "0" means no fix, so the count would be empty.
locked_satellites = int(fields[7])
print("Locked satellites: {}".format(locked_satellites))
elif sentence_type == "GSV" and fields[2] == "1":
satellites_in_view = int(fields[3])
print("Satellites in view: {}".format(satellites_in_view))
Providers
Strip the checksum from received sentences, and place them in a ring-buffer.
class LocationProviderApp:
def __init__(self):
self.sentences = []
def update(self, delta):
raw = self.uart.readline()
if raw:
try:
line = raw.decode().strip()
self.sentences.append(line.split('*')[0])
if len(self.sentences) > 40:
self.sentences = self.sentences[-40:]
except Exception:
pass