move to dynamic registration of converter functions

This commit is contained in:
andreas 2021-10-21 17:04:56 +02:00
parent f054413de4
commit c24e699874
3 changed files with 51 additions and 42 deletions

View File

@ -56,5 +56,6 @@ public:
}
virtual void loop();
virtual ~N2kDataToNMEA0183(){}
virtual const unsigned long* handledPgns()=0;
};
#endif

View File

@ -10,8 +10,10 @@
#include <NMEA0183Messages.h>
#include <math.h>
#include "N2kDataToNMEA0183.h"
#include <map>
class N2kToNMEA0183Functions : public N2kDataToNMEA0183
{
typedef void (N2kToNMEA0183Functions::*N2KConverter)(const tN2kMsg &N2kMsg);
private:
static const unsigned long RMCPeriod = 500;
static void setMax(GwBoatItem<double> *maxItem, GwBoatItem<double> *item)
@ -88,6 +90,28 @@ private:
unsigned long LastPosSend;
unsigned long NextRMCSend;
unsigned long lastLoopTime;
std::map<long,N2KConverter> converters;
/**
* register a n2k message converter
* each of the converter functions must be registered in the constructor
**/
void registerConverter(long pgn,N2KConverter converter){
converters[pgn]=converter;
}
virtual const unsigned long * handledPgns(){
logger->logString("CONV: # %d handled PGNS",(int)converters.size());
unsigned long *rt=new unsigned long[converters.size()+1];
int idx=0;
for (std::map<long,N2KConverter>::iterator it=converters.begin();
it != converters.end();it++){
rt[idx]=it->first;
idx++;
}
rt[idx]=0;
return rt;
}
void SetNextRMCSend() { NextRMCSend = millis() + RMCPeriod; }
//*************** the converters ***********************
@ -458,6 +482,23 @@ public:
tripLog = boatData->getUint32Item(F("TripLog"), true, 0, mtr2nm);
daysSince1970 = boatData->getUint32Item(F("DaysSince1970"), true, 4000);
secondsSinceMidnight = boatData->getDoubleItem(F("SecondsSinceMidnight"), true, 4000);
//register all converter functions
//for each vonverter you should have a member with the N2KMsg as parameter
//and register it here
//with this approach we easily have a list of all handled
//pgns
registerConverter(127250UL,&N2kToNMEA0183Functions::HandleMsg);
registerConverter(127258UL,&N2kToNMEA0183Functions::HandleVariation);
registerConverter(128259UL,&N2kToNMEA0183Functions::HandleBoatSpeed);
registerConverter(128267UL,&N2kToNMEA0183Functions::HandleDepth);
registerConverter(129025UL,&N2kToNMEA0183Functions::HandlePosition);
registerConverter(129026UL,&N2kToNMEA0183Functions::HandleCOGSOG);
registerConverter(129029UL,&N2kToNMEA0183Functions::HandleGNSS);
registerConverter(130306UL,&N2kToNMEA0183Functions::HandleWind);
registerConverter(128275UL,&N2kToNMEA0183Functions::HandleLog);
registerConverter(127245UL,&N2kToNMEA0183Functions::HandleRudder);
registerConverter(130310UL,&N2kToNMEA0183Functions::HandleWaterTemp);
}
virtual void loop()
{
@ -470,33 +511,14 @@ public:
}
virtual void HandleMsg(const tN2kMsg &N2kMsg)
{
switch (N2kMsg.PGN)
{
case 127250UL:
HandleHeading(N2kMsg);
case 127258UL:
HandleVariation(N2kMsg);
case 128259UL:
HandleBoatSpeed(N2kMsg);
case 128267UL:
HandleDepth(N2kMsg);
case 129025UL:
HandlePosition(N2kMsg);
case 129026UL:
HandleCOGSOG(N2kMsg);
case 129029UL:
HandleGNSS(N2kMsg);
case 130306UL:
HandleWind(N2kMsg);
case 128275UL:
HandleLog(N2kMsg);
case 127245UL:
HandleRudder(N2kMsg);
case 130310UL:
HandleWaterTemp(N2kMsg);
std::map<long,N2KConverter>::iterator it;
it = converters.find(N2kMsg.PGN);
if (it != converters.end()){
//logger->logString("CONV: handle PGN %ld",N2kMsg.PGN);
//call to member function - see e.g. https://isocpp.org/wiki/faq/pointers-to-members
((*this).*(it->second))(N2kMsg);
return;
}
}
private:
};
#endif

View File

@ -59,21 +59,7 @@ N2kDataToNMEA0183 *nmea0183Converter=N2kDataToNMEA0183::create(&logger, &boatDat
// Set the information for other bus devices, which messages we support
const unsigned long TransmitMessages[] PROGMEM = {127489L, // Engine dynamic
0
};
const unsigned long ReceiveMessages[] PROGMEM = {/*126992L,*/ // System time
127250L, // Heading
127258L, // Magnetic variation
128259UL,// Boat speed
128267UL,// Depth
129025UL,// Position
129026L, // COG and SOG
129029L, // GNSS
130306L, // Wind
128275UL,// Log
127245UL,// Rudder
0
};
};
// Forward declarations
void HandleNMEA2000Msg(const tN2kMsg &N2kMsg);
void SendNMEA0183Message(const tNMEA0183Msg &NMEA0183Msg);
@ -249,7 +235,7 @@ void setup() {
NMEA2000.SetMode(tNMEA2000::N2km_ListenAndNode, NodeAddress);
NMEA2000.ExtendTransmitMessages(TransmitMessages);
NMEA2000.ExtendReceiveMessages(ReceiveMessages);
NMEA2000.ExtendReceiveMessages(nmea0183Converter->handledPgns());
NMEA2000.AttachMsgHandler(nmea0183Converter); // NMEA 2000 -> NMEA 0183 conversion
NMEA2000.SetMsgHandler(HandleNMEA2000Msg); // Also send all NMEA2000 messages in SeaSmart format