diff --git a/lib/boatData/GwBoatData.cpp b/lib/boatData/GwBoatData.cpp index cc1c9be..e8ec13d 100644 --- a/lib/boatData/GwBoatData.cpp +++ b/lib/boatData/GwBoatData.cpp @@ -61,22 +61,3 @@ double mtr2nm(double m) return m / 1852; } -double kelvinToC(double v) -{ - return v - 273.15; -} -double formatLatitude(double v){ - return v; -} -double formatLongitude(double v){ - return v; -} -double formatFixed0(double v){ - return v; -} -double formatDepth(double v){ - return v; -} -uint32_t formatFixed0(uint32_t v){ - return v; -} \ No newline at end of file diff --git a/lib/boatData/GwBoatData.h b/lib/boatData/GwBoatData.h index ce1ef62..3023d82 100644 --- a/lib/boatData/GwBoatData.h +++ b/lib/boatData/GwBoatData.h @@ -6,14 +6,26 @@ #include #include #define GW_BOAT_VALUE_LEN 32 +#define GWSC(name) static constexpr const __FlashStringHelper* name=F(#name) class GwBoatItemBase{ public: static const unsigned long INVALID_TIME=60000; + //the formatter names that must be known in js + GWSC(formatCourse); + GWSC(formatKnots); + GWSC(formatWind); + GWSC(formatLatitude); + GWSC(formatLongitude); + GWSC(formatFixed0); + GWSC(formatDepth); + GWSC(kelvinToC); + GWSC(mtr2nm); typedef std::vector GwBoatItemMap; protected: unsigned long lastSet=0; unsigned long invalidTime=INVALID_TIME; String name; + String format; void uls(unsigned long ts=0){ if (ts) lastSet=ts; else lastSet=millis(); @@ -26,10 +38,11 @@ class GwBoatItemBase{ if (now == 0) now=millis(); return (lastSet + invalidTime) >= now; } - GwBoatItemBase(String name,unsigned long invalidTime=INVALID_TIME){ + GwBoatItemBase(String name,String format,unsigned long invalidTime=INVALID_TIME){ lastSet=0; this->invalidTime=invalidTime; this->name=name; + this->format=format; } virtual ~GwBoatItemBase(){} void invalidate(){ @@ -41,18 +54,12 @@ class GwBoatItemBase{ }; class GwBoatData; template class GwBoatItem : public GwBoatItemBase{ - public: - typedef T (*Formatter)(T); private: T data; - Formatter fmt; int lastUpdateSource; - String formatInfo; public: - GwBoatItem(String name,String formatInfo,unsigned long invalidTime=INVALID_TIME,Formatter fmt=NULL,GwBoatItemMap *map=NULL): - GwBoatItemBase(name,invalidTime){ - this->fmt=fmt; - this->formatInfo=formatInfo; + GwBoatItem(String name,String formatInfo,unsigned long invalidTime=INVALID_TIME,GwBoatItemMap *map=NULL): + GwBoatItemBase(name,formatInfo,invalidTime){ if (map){ map->push_back(this); } @@ -74,9 +81,8 @@ template class GwBoatItem : public GwBoatItemBase{ uls(now); return true; } - T getData(bool useFormatter=false){ - if (! useFormatter || fmt == NULL) return data; - return (*fmt)(data); + T getData(){ + return data; } T getDataWithDefault(T defaultv){ if (! isValid(millis())) return defaultv; @@ -84,11 +90,11 @@ template class GwBoatItem : public GwBoatItemBase{ } virtual void toJsonDoc(JsonDocument *doc, unsigned long minTime){ JsonObject o=doc->createNestedObject(name); - o[F("value")]=getData(true); + o[F("value")]=getData(); o[F("update")]=minTime-lastSet; o[F("source")]=lastUpdateSource; o[F("valid")]=isValid(minTime); - o[F("format")]=formatInfo; + o[F("format")]=format; } virtual int getLastSource(){return lastUpdateSource;} }; @@ -98,50 +104,45 @@ double formatWind(double cv); double formatKnots(double cv); uint32_t mtr2nm(uint32_t m); double mtr2nm(double m); -double kelvinToC(double v); -double formatLatitude(double v); -double formatLongitude(double v); -double formatFixed0(double v); -uint32_t formatFixed0(uint32_t v); -double formatDepth(double v); + #define GWBOATDATA(type,name,time,fmt) \ - GwBoatItem *name=new GwBoatItem(F(#name),F(#fmt),time,fmt,&values) ; + GwBoatItem *name=new GwBoatItem(F(#name),GwBoatItemBase::fmt,time,&values) ; class GwBoatData{ private: GwLog *logger; GwBoatItemBase::GwBoatItemMap values; public: - GWBOATDATA(double,COG,4000,&formatCourse) - GWBOATDATA(double,TWD,4000,&formatCourse) - GWBOATDATA(double,AWD,4000,&formatCourse) - GWBOATDATA(double,SOG,4000,&formatKnots) - GWBOATDATA(double,STW,4000,&formatKnots) - GWBOATDATA(double,TWS,4000,&formatKnots) - GWBOATDATA(double,AWS,4000,&formatKnots) - GWBOATDATA(double,MaxTws,0,&formatKnots) - GWBOATDATA(double,MaxAws,0,&formatKnots) - GWBOATDATA(double,AWA,4000,&formatWind) - GWBOATDATA(double,Heading,4000,&formatCourse) //true - GWBOATDATA(double,MagneticHeading,4000,&formatCourse) - GWBOATDATA(double,Variation,4000,&formatCourse) - GWBOATDATA(double,Deviation,4000,&formatCourse) - GWBOATDATA(double,RudderPosition,4000,&formatCourse) - GWBOATDATA(double,Latitude,4000,&formatLatitude) - GWBOATDATA(double,Longitude,4000,&formatLongitude) - GWBOATDATA(double,Altitude,4000,&formatFixed0) - GWBOATDATA(double,WaterDepth,4000,&formatDepth) - GWBOATDATA(double,SecondsSinceMidnight,4000,&formatFixed0) - GWBOATDATA(double,WaterTemperature,4000,&kelvinToC) - GWBOATDATA(double,XTE,4000,&formatFixed0) - GWBOATDATA(double,DTW,4000,&mtr2nm) - GWBOATDATA(double,BTW,4000,&formatCourse) - GWBOATDATA(double,WPLatitude,4000,&formatLatitude) - GWBOATDATA(double,WPLongitude,4000,&formatLongitude) - GWBOATDATA(uint32_t,Log,0,&mtr2nm) - GWBOATDATA(uint32_t,TripLog,0,&mtr2nm) - GWBOATDATA(uint32_t,DaysSince1970,4000,&formatFixed0) + GWBOATDATA(double,COG,4000,formatCourse) + GWBOATDATA(double,TWD,4000,formatCourse) + GWBOATDATA(double,AWD,4000,formatCourse) + GWBOATDATA(double,SOG,4000,formatKnots) + GWBOATDATA(double,STW,4000,formatKnots) + GWBOATDATA(double,TWS,4000,formatKnots) + GWBOATDATA(double,AWS,4000,formatKnots) + GWBOATDATA(double,MaxTws,0,formatKnots) + GWBOATDATA(double,MaxAws,0,formatKnots) + GWBOATDATA(double,AWA,4000,formatWind) + GWBOATDATA(double,Heading,4000,formatCourse) //true + GWBOATDATA(double,MagneticHeading,4000,formatCourse) + GWBOATDATA(double,Variation,4000,formatCourse) + GWBOATDATA(double,Deviation,4000,formatCourse) + GWBOATDATA(double,RudderPosition,4000,formatCourse) + GWBOATDATA(double,Latitude,4000,formatLatitude) + GWBOATDATA(double,Longitude,4000,formatLongitude) + GWBOATDATA(double,Altitude,4000,formatFixed0) + GWBOATDATA(double,WaterDepth,4000,formatDepth) + GWBOATDATA(double,SecondsSinceMidnight,4000,formatFixed0) + GWBOATDATA(double,WaterTemperature,4000,kelvinToC) + GWBOATDATA(double,XTE,4000,formatFixed0) + GWBOATDATA(double,DTW,4000,mtr2nm) + GWBOATDATA(double,BTW,4000,formatCourse) + GWBOATDATA(double,WPLatitude,4000,formatLatitude) + GWBOATDATA(double,WPLongitude,4000,formatLongitude) + GWBOATDATA(uint32_t,Log,0,mtr2nm) + GWBOATDATA(uint32_t,TripLog,0,mtr2nm) + GWBOATDATA(uint32_t,DaysSince1970,4000,formatFixed0) public: GwBoatData(GwLog *logger); ~GwBoatData(); diff --git a/web/index.js b/web/index.js index 12358c2..c8db1b8 100644 --- a/web/index.js +++ b/web/index.js @@ -447,13 +447,50 @@ function createDashboard() { }); } let valueFormatters = { - formatCourse: function (v) { let x = parseFloat(v); return x.toFixed(0); }, - formatKnots: function (v) { let x = parseFloat(v); return x.toFixed(2); }, - formatWind: function (v) { let x = parseFloat(v); return x.toFixed(0); }, - mtr2nm: function (v) { let x = parseFloat(v); return x.toFixed(2); }, - kelvinToC: function (v) { let x = parseFloat(v); return x.toFixed(0); }, - formatFixed0: function (v) { let x = parseFloat(v); return x.toFixed(0); }, - formatDepth: function (v) { let x = parseFloat(v); return x.toFixed(1); }, + formatCourse: function (v) { + let x = parseFloat(v); + let rt=x*180.0 / Math.PI; + if (rt > 360) rt -= 360; + if (rt < 0) rt += 360; + return rt.toFixed(0); + }, + formatKnots: function (v) { + let x = parseFloat(v); + x=x *3600.0/1852.0; + return x.toFixed(2); + }, + formatWind: function (v) { + let x = parseFloat(v); + x=x*180.0 / Math.PI; + if (x > 180) x=180-x; + return x.toFixed(0); + }, + mtr2nm: function (v) { + let x = parseFloat(v); + x=x/1852.0; + return x.toFixed(2); + }, + kelvinToC: function (v) { + let x = parseFloat(v); + x=x-273.15; + return x.toFixed(0); + }, + formatFixed0: function (v) { + let x = parseFloat(v); + return x.toFixed(0); + }, + formatDepth: function (v) { + let x = parseFloat(v); + return x.toFixed(1); + }, + formatLatitude: function(v){ + let x = parseFloat(v); + return x.toFixed(4); + }, + formatLongitued: function(v){ + let x = parseFloat(v); + return x.toFixed(4); + }, } function updateDashboard(data) { for (let n in data) {