Snorktracker
 All Data Structures Files Functions Variables Macros Pages
Gps.h
Go to the documentation of this file.
1 /*
2  Copyright (C) 2018 SFini
3 
4  This program is free software: you can redistribute it and/or modify
5  it under the terms of the GNU General Public License as published by
6  the Free Software Foundation, either version 3 of the License, or
7  (at your option) any later version.
8 
9  This program is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY; without even the implied warranty of
11  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  GNU General Public License for more details.
13 
14  You should have received a copy of the GNU General Public License
15  along with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
26 class MyDegrees
27 {
28 public:
29  uint16_t predecimal;
30  uint32_t billionths;
31  bool negative;
32 
33 public:
34  MyDegrees();
35  MyDegrees(const MyDegrees &myDegrees);
36 
37  void clear();
38 
39  double value();
40  bool set(const String &data);
41 };
42 
47 {
48 friend class MyGps;
49 protected:
52 
53 public:
54  static double distanceBetween(double lat1, double long1, double lat2, double long2);
55  static double courseTo(double lat1, double long1, double lat2, double long2);
56 
57 public:
58  void clear();
59 
60  double latitude();
61  double longitude();
62 
63  String longitudeString();
64  String latitudeString();
65 
67  double courseTo (MyLocation &location);
68 };
69 
73 class MyDate
74 {
75 friend class MyGps;
76 protected:
77  int date;
78 
79 public:
80  int year();
81  int month();
82  int day();
83 
84  MyDate()
85  : date(0)
86  {
87  }
88 
89  void clear();
90 
91  String dateString();
92 };
93 
97 class MyTime
98 {
99 friend class MyGps;
100 protected:
101  int time;
102 
103 public:
104  int hour();
105  int minute();
106  int second();
107 
108  MyTime()
109  : time(0)
110  {
111  }
112  MyTime(int t)
113  : time(t)
114  {
115  }
116 
117  void clear();
118 
119  String timeString();
120 
121  operator int() {
122  return time;
123  }
124 };
125 
129 class MyGps
130 {
131 public:
132  bool runStatus;
133  bool fixStatus;
137  double altitude;
138  double speed;
139  double course;
140  int fixMode;
141  double pdop;
142  double hdop;
143  double vdop;
146 
147 protected:
148  bool parse(bool &b, const String &data);
149  bool parse(int &i, const String &data);
150  bool parse(double &d, const String &data);
151 
152 public:
153  MyGps();
154 
155  void clear();
156 
157  bool setRunStatus (const String &data);
158  bool setFixStatus (const String &data);
159  bool setDateTime (const String &data);
160  bool setLatitude (const String &data);
161  bool setLongitude (const String &data);
162  bool setAltitude (const String &data);
163  bool setSpeed (const String &data);
164  bool setCourse (const String &data);
165  bool setFixMode (const String &data);
166  bool setHdop (const String &data);
167  bool setPdop (const String &data);
168  bool setVdop (const String &data);
169  bool setSatellitesInView(const String &data);
170  bool setSatellitesUsed (const String &data);
171 
172  String longitudeString ();
173  String latitudeString ();
174  String altitudeString ();
175  String kmphString ();
176  String satellitesString ();
177  String courseString ();
178 
179  bool getAsGpsJson(char *gpsJson);
180 };
181 
182 /* ******************************************** */
183 
186  : predecimal(0)
187  , billionths(0)
188  , negative(false)
189 {
190 }
191 
194  : predecimal(myDegrees.predecimal)
195  , billionths(myDegrees.billionths)
196  , negative(myDegrees.negative)
197 {
198 }
199 
202 {
203  predecimal = 0;
204  billionths = 0;
205  negative = false;
206 }
207 
210 {
211  double ret = predecimal + billionths / 1000000000.0;
212 
213  return negative ? -ret : ret;
214 }
215 
217 bool MyDegrees::set(const String &data)
218 {
219  const char *term = data.c_str();
220  uint32_t multiplier = 1000000000UL;
221  uint32_t leftOfDecimal = (uint32_t) atol(term);
222 
223  predecimal = (int16_t)leftOfDecimal;
224  billionths = 0;
225 
226  while (isdigit(*term)) {
227  ++term;
228  }
229 
230  if (*term == '.') {
231  while (isdigit(*++term)) {
232  multiplier /= 10;
233  billionths += (*term - '0') * multiplier;
234  }
235  }
236  negative = false;
237  return true;
238 }
239 
242 {
243  latitude_.clear();
244  longitude_.clear();
245 }
246 
248 double MyLocation::distanceBetween(double lat1, double long1, double lat2, double long2)
249 {
250  // returns distance in meters between two positions, both specified
251  // as signed decimal-degrees latitude and longitude. Uses great-circle
252  // distance computation for hypothetical sphere of radius 6372795 meters.
253  // Because Earth is no exact sphere, rounding errors may be up to 0.5%.
254  // Courtesy of Maarten Lamers
255  double delta = radians(long1 - long2);
256  double sdlong = sin(delta);
257  double cdlong = cos(delta);
258  lat1 = radians(lat1);
259  lat2 = radians(lat2);
260  double slat1 = sin(lat1);
261  double clat1 = cos(lat1);
262  double slat2 = sin(lat2);
263  double clat2 = cos(lat2);
264  delta = (clat1 * slat2) - (slat1 * clat2 * cdlong);
265  delta = sq(delta);
266  delta += sq(clat2 * sdlong);
267  delta = sqrt(delta);
268  double denom = (slat1 * slat2) + (clat1 * clat2 * cdlong);
269  delta = atan2(delta, denom);
270  return delta * 6372795;
271 }
272 
274 double MyLocation::courseTo(double lat1, double long1, double lat2, double long2)
275 {
276  // returns course in degrees (North=0, West=270) from position 1 to position 2,
277  // both specified as signed decimal-degrees latitude and longitude.
278  // Because Earth is no exact sphere, calculated course may be off by a tiny fraction.
279  // Courtesy of Maarten Lamers
280  double dlon = radians(long2 - long1);
281  lat1 = radians(lat1);
282  lat2 = radians(lat2);
283  double a1 = sin(dlon) * cos(lat2);
284  double a2 = sin(lat1) * cos(lat2) * cos(dlon);
285  a2 = cos(lat1) * sin(lat2) - a2;
286  a2 = atan2(a1, a2);
287  if (a2 < 0.0)
288  {
289  a2 += TWO_PI;
290  }
291  return degrees(a2);
292 }
293 
296 {
297  return latitude_.value();
298 }
299 
302 {
303  return longitude_.value();
304 }
305 
308 {
309  return String(longitude(), 6);
310 }
311 
314 {
315  return String(latitude(), 6);
316 }
317 
320 {
321  return distanceBetween(latitude(), longitude(), to.latitude(), to.longitude());
322 }
323 
326 {
327  return courseTo(latitude(), longitude(), to.latitude(), to.longitude());
328 }
329 
332 {
333  date = 0;
334 }
335 
338 {
339  return date / 10000;
340 }
341 
344 {
345  return (date / 100) % 100;
346 }
347 
350 {
351  return date % 100;
352 }
353 
356 {
357  return String(day()) + '-' + String(month()) + '-' + String(year());
358 }
359 
362 {
363  time = 0;
364 }
365 
368 {
369  return time / 10000;
370 }
371 
374 {
375  return (time / 100) % 100;
376 }
377 
380 {
381  return time % 100;
382 }
383 
386 {
387  return String(hour()) + ':' + String(minute()) + ':' + String(second());
388 }
389 
390 
393  : runStatus(false)
394  , fixStatus(false)
395  , altitude(0)
396  , speed(0)
397  , course(0)
398  , fixMode(0)
399  , hdop(0)
400  , pdop(0)
401  , vdop(0)
402  , satellitesInView(0)
403  , satellitesUsed(0)
404 {
405 }
406 
409 {
410  date.clear();
411  time.clear();
412  location.clear();
413  runStatus = false;
414  fixStatus = false;
415  altitude = 0.0;
416  speed = 0.0;
417  course = 0.0;
418  fixMode = 0;
419  pdop = 0.0;
420  hdop = 0.0;
421  vdop = 0.0;
422  satellitesInView = 0;
423  satellitesUsed = 0;
424 }
425 
427 bool MyGps::parse(bool &b, const String &data)
428 {
429  if (data == F("0")) {
430  b = false;
431  return true;
432  } else if (data == F("1")) {
433  b = true;
434  return true;
435  }
436  return false;
437 }
438 
440 bool MyGps::parse(int &i, const String &data)
441 {
442  i = atol(data.c_str());
443  return true;
444 }
445 
447 bool MyGps::parse(double &d, const String &data)
448 {
449  d = atof(data.c_str());
450  return true;
451 }
452 
454 bool MyGps::setRunStatus(const String &data)
455 {
456  return parse(runStatus, data);
457 }
458 
460 bool MyGps::setFixStatus(const String &data)
461 {
462  return parse(fixStatus, data);
463 }
464 
466 bool MyGps::setDateTime(const String &data)
467 {
468  parse(date.date, data.substring(0, 8));
469  parse(time.time, data.substring(8));
470  return true;
471 }
472 
474 bool MyGps::setLatitude(const String &data)
475 {
476  return location.latitude_.set(data);
477 }
478 
480 bool MyGps::setLongitude(const String &data)
481 {
482  return location.longitude_.set(data);
483 }
484 
486 bool MyGps::setAltitude(const String &data)
487 {
488  return parse(altitude, data);
489 }
490 
492 bool MyGps::setSpeed(const String &data)
493 {
494  return parse(speed, data);
495 }
496 
498 bool MyGps::setCourse(const String &data)
499 {
500  return parse(course, data);
501 }
502 
504 bool MyGps::setFixMode(const String &data)
505 {
506  return parse(fixMode, data);
507 }
508 
510 bool MyGps::setPdop(const String &data)
511 {
512  return parse(pdop, data);
513 }
514 
516 bool MyGps::setHdop(const String &data)
517 {
518  return parse(hdop, data);
519 }
520 
522 bool MyGps::setVdop(const String &data)
523 {
524  return parse(vdop, data);
525 }
526 
528 bool MyGps::setSatellitesInView(const String &data)
529 {
530  return parse(satellitesInView, data);
531 }
532 
534 bool MyGps::setSatellitesUsed(const String &data)
535 {
536  return parse(satellitesUsed, data);
537 }
538 
541 {
542  return location.longitudeString();
543 }
544 
547 {
548  return location.latitudeString();
549 }
550 
553 {
554  return String(altitude, 0);
555 }
556 
559 {
560  return String(speed, 0);
561 }
562 
565 {
566  return String(satellitesUsed);
567 }
568 
571 {
572  return String(course);
573 }
574 
576 bool MyGps::getAsGpsJson(char *gpsJson)
577 {
578  if (fixStatus) {
579  String gps;
580 
581  gps += "{";
582  gps += "\"long\":\"" + longitudeString() + "\",";
583  gps += "\"lat\":\"" + latitudeString() + "\",";
584  gps += "\"alt\":\"" + altitudeString() + "\",";
585  gps += "\"kmph\":\"" + kmphString() + "\"";
586  gps += "}";
587 
588  gps.toCharArray(gpsJson, (gps.length() + 1));
589  return true;
590  }
591  return false;
592 }
int second()
Definition: Gps.h:379
uint16_t predecimal
Value on the left side of the separator.
Definition: Gps.h:29
void clear()
Definition: Gps.h:361
bool set(const String &data)
Definition: Gps.h:217
bool setLongitude(const String &data)
Definition: Gps.h:480
bool setAltitude(const String &data)
Definition: Gps.h:486
double vdop
Vertical dilution of precision.
Definition: Gps.h:143
bool parse(bool &b, const String &data)
Definition: Gps.h:427
bool setHdop(const String &data)
Definition: Gps.h:516
uint32_t billionths
Value of the right side after the separator.
Definition: Gps.h:30
Definition: Gps.h:73
Definition: Gps.h:46
MyDegrees latitude_
Latitude.
Definition: Gps.h:50
bool setCourse(const String &data)
Definition: Gps.h:498
bool negative
Is the value negative?
Definition: Gps.h:31
bool setVdop(const String &data)
Definition: Gps.h:522
static double distanceBetween(double lat1, double long1, double lat2, double long2)
Definition: Gps.h:248
double altitude
The current height.
Definition: Gps.h:137
int time
Time in the form of HoursMinutesSecons i.e. 120135.
Definition: Gps.h:101
int month()
Definition: Gps.h:343
String latitudeString()
Definition: Gps.h:313
bool setRunStatus(const String &data)
Definition: Gps.h:454
int date
Date in the form of YearMonthDay i.e. 20170115.
Definition: Gps.h:77
int minute()
Definition: Gps.h:373
String altitudeString()
Definition: Gps.h:552
double pdop
Dilution of precision.
Definition: Gps.h:141
void clear()
Definition: Gps.h:408
String satellitesString()
Definition: Gps.h:564
bool setSatellitesInView(const String &data)
Definition: Gps.h:528
double longitude()
Definition: Gps.h:301
String dateString()
Definition: Gps.h:355
int fixMode
Precission of the gps data.
Definition: Gps.h:140
bool setDateTime(const String &data)
Definition: Gps.h:466
void clear()
Definition: Gps.h:331
double latitude()
Definition: Gps.h:295
String courseString()
Definition: Gps.h:570
String longitudeString()
Definition: Gps.h:540
String kmphString()
Definition: Gps.h:558
bool setSatellitesUsed(const String &data)
Definition: Gps.h:534
String longitudeString()
Definition: Gps.h:307
double hdop
Horizontal dilution of precision.
Definition: Gps.h:142
int satellitesInView
Sattelites in the View.
Definition: Gps.h:144
int day()
Definition: Gps.h:349
bool getAsGpsJson(char *gpsJson)
Definition: Gps.h:576
double distanceTo(MyLocation &location)
Definition: Gps.h:319
MyLocation location
The gps position.
Definition: Gps.h:136
int satellitesUsed
Sattelites used for gps position.
Definition: Gps.h:145
MyDegrees()
Definition: Gps.h:185
int hour()
Definition: Gps.h:367
MyDate date
The received gps utc date.
Definition: Gps.h:134
int year()
Definition: Gps.h:337
bool setFixMode(const String &data)
Definition: Gps.h:504
String latitudeString()
Definition: Gps.h:546
MyDegrees longitude_
Longitude.
Definition: Gps.h:51
double value()
Definition: Gps.h:209
void clear()
Definition: Gps.h:201
bool setSpeed(const String &data)
Definition: Gps.h:492
bool setLatitude(const String &data)
Definition: Gps.h:474
double speed
The detected moving speed.
Definition: Gps.h:138
Definition: Gps.h:26
bool setPdop(const String &data)
Definition: Gps.h:510
Definition: Gps.h:97
MyTime time
The received gps utc time.
Definition: Gps.h:135
bool fixStatus
Are the gps is valid received?
Definition: Gps.h:133
void clear()
Definition: Gps.h:241
static double courseTo(double lat1, double long1, double lat2, double long2)
Definition: Gps.h:274
bool setFixStatus(const String &data)
Definition: Gps.h:460
double course
The calculated course.
Definition: Gps.h:139
MyGps()
Definition: Gps.h:392
String timeString()
Definition: Gps.h:385
Definition: Gps.h:129
bool runStatus
Is the gps modul running?
Definition: Gps.h:132