optimize boat data string handling
This commit is contained in:
		
							parent
							
								
									e08bcf1009
								
							
						
					
					
						commit
						de04e5443b
					
				| 
						 | 
				
			
			@ -7,14 +7,14 @@
 | 
			
		|||
#define GWTYPE_INT16 4
 | 
			
		||||
#define GWTYPE_USER 100
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class GwBoatItemTypes{
 | 
			
		||||
    public:
 | 
			
		||||
        static int getType(const uint32_t &x){return GWTYPE_UINT32;}
 | 
			
		||||
        static int getType(const uint16_t &x){return GWTYPE_UINT16;}
 | 
			
		||||
        static int getType(const int16_t &x){return GWTYPE_INT16;}
 | 
			
		||||
        static int getType(const double &x){return GWTYPE_DOUBLE;}
 | 
			
		||||
        static int getType(const GwSatInfoList &x){ return GWTYPE_USER+1;}
 | 
			
		||||
class GwBoatItemTypes
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
    static int getType(const uint32_t &x) { return GWTYPE_UINT32; }
 | 
			
		||||
    static int getType(const uint16_t &x) { return GWTYPE_UINT16; }
 | 
			
		||||
    static int getType(const int16_t &x) { return GWTYPE_INT16; }
 | 
			
		||||
    static int getType(const double &x) { return GWTYPE_DOUBLE; }
 | 
			
		||||
    static int getType(const GwSatInfoList &x) { return GWTYPE_USER + 1; }
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
bool GwBoatItemBase::isValid(unsigned long now) const
 | 
			
		||||
| 
						 | 
				
			
			@ -34,62 +34,83 @@ GwBoatItemBase::GwBoatItemBase(String name, String format, unsigned long invalid
 | 
			
		|||
    this->name = name;
 | 
			
		||||
    this->format = format;
 | 
			
		||||
    this->type = 0;
 | 
			
		||||
    this->lastUpdateSource=-1;
 | 
			
		||||
    this->lastUpdateSource = -1;
 | 
			
		||||
}
 | 
			
		||||
size_t GwBoatItemBase::getJsonSize(){return JSON_OBJECT_SIZE(10);}
 | 
			
		||||
size_t GwBoatItemBase::getJsonSize() { return JSON_OBJECT_SIZE(10); }
 | 
			
		||||
#define STRING_SIZE 40
 | 
			
		||||
GwBoatItemBase::StringWriter::StringWriter(){
 | 
			
		||||
    buffer=new uint8_t[STRING_SIZE];
 | 
			
		||||
    wp=buffer;
 | 
			
		||||
    bufferSize=STRING_SIZE;
 | 
			
		||||
    buffer [0]=0;
 | 
			
		||||
GwBoatItemBase::StringWriter::StringWriter()
 | 
			
		||||
{
 | 
			
		||||
    buffer = new uint8_t[STRING_SIZE];
 | 
			
		||||
    wp = buffer;
 | 
			
		||||
    bufferSize = STRING_SIZE;
 | 
			
		||||
    buffer[0] = 0;
 | 
			
		||||
};
 | 
			
		||||
const char *GwBoatItemBase::StringWriter::c_str() const{
 | 
			
		||||
const char *GwBoatItemBase::StringWriter::c_str() const
 | 
			
		||||
{
 | 
			
		||||
    return (const char *)buffer;
 | 
			
		||||
}
 | 
			
		||||
int GwBoatItemBase::StringWriter::getSize() const{
 | 
			
		||||
    return wp-buffer;
 | 
			
		||||
int GwBoatItemBase::StringWriter::getSize() const
 | 
			
		||||
{
 | 
			
		||||
    int rt=wp - buffer;
 | 
			
		||||
    if (rt >= baseOffset) rt-=baseOffset;
 | 
			
		||||
    return rt;
 | 
			
		||||
}
 | 
			
		||||
void GwBoatItemBase::StringWriter::reset(){
 | 
			
		||||
    wp=buffer;
 | 
			
		||||
    *wp=0;
 | 
			
		||||
void GwBoatItemBase::StringWriter::setBase()
 | 
			
		||||
{
 | 
			
		||||
    baseOffset = wp - buffer;
 | 
			
		||||
}
 | 
			
		||||
void GwBoatItemBase::StringWriter::ensure(size_t size){
 | 
			
		||||
    size_t fill=wp-buffer;
 | 
			
		||||
    size_t newSize=bufferSize;
 | 
			
		||||
    while ((fill+size) >= (newSize-1) ){
 | 
			
		||||
        newSize+=STRING_SIZE;       
 | 
			
		||||
bool GwBoatItemBase::StringWriter::baseFilled()
 | 
			
		||||
{
 | 
			
		||||
    return baseOffset != 0;
 | 
			
		||||
}
 | 
			
		||||
void GwBoatItemBase::StringWriter::reset()
 | 
			
		||||
{
 | 
			
		||||
    wp = buffer + baseOffset;
 | 
			
		||||
    *wp = 0;
 | 
			
		||||
}
 | 
			
		||||
void GwBoatItemBase::StringWriter::ensure(size_t size)
 | 
			
		||||
{
 | 
			
		||||
    size_t fill = wp - buffer;
 | 
			
		||||
    size_t newSize = bufferSize;
 | 
			
		||||
    while ((fill + size) >= (newSize - 1))
 | 
			
		||||
    {
 | 
			
		||||
        newSize += STRING_SIZE;
 | 
			
		||||
    }
 | 
			
		||||
    if (newSize != bufferSize){
 | 
			
		||||
        uint8_t *newBuffer=new uint8_t[newSize];
 | 
			
		||||
        memcpy(newBuffer,buffer,fill);
 | 
			
		||||
        newBuffer[fill]=0;
 | 
			
		||||
    if (newSize != bufferSize)
 | 
			
		||||
    {
 | 
			
		||||
        uint8_t *newBuffer = new uint8_t[newSize];
 | 
			
		||||
        memcpy(newBuffer, buffer, fill);
 | 
			
		||||
        newBuffer[fill] = 0;
 | 
			
		||||
        delete buffer;
 | 
			
		||||
        buffer=newBuffer;
 | 
			
		||||
        wp=newBuffer+fill;
 | 
			
		||||
        bufferSize=newSize;
 | 
			
		||||
        buffer = newBuffer;
 | 
			
		||||
        wp = newBuffer + fill;
 | 
			
		||||
        bufferSize = newSize;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
size_t GwBoatItemBase::StringWriter::write(uint8_t c){
 | 
			
		||||
size_t GwBoatItemBase::StringWriter::write(uint8_t c)
 | 
			
		||||
{
 | 
			
		||||
    ensure(1);
 | 
			
		||||
    *wp=c;
 | 
			
		||||
    *wp = c;
 | 
			
		||||
    wp++;
 | 
			
		||||
    *wp=0;
 | 
			
		||||
    *wp = 0;
 | 
			
		||||
    return 1;
 | 
			
		||||
}
 | 
			
		||||
size_t GwBoatItemBase::StringWriter::write(const uint8_t* s, size_t n){
 | 
			
		||||
size_t GwBoatItemBase::StringWriter::write(const uint8_t *s, size_t n)
 | 
			
		||||
{
 | 
			
		||||
    ensure(n);
 | 
			
		||||
    memcpy(wp,s,n);
 | 
			
		||||
    wp+=n;
 | 
			
		||||
    *wp=0;
 | 
			
		||||
    memcpy(wp, s, n);
 | 
			
		||||
    wp += n;
 | 
			
		||||
    *wp = 0;
 | 
			
		||||
    return n;
 | 
			
		||||
}
 | 
			
		||||
template<class T> GwBoatItem<T>::GwBoatItem(String name,String formatInfo,unsigned long invalidTime,GwBoatItemMap *map):
 | 
			
		||||
    GwBoatItemBase(name,formatInfo,invalidTime){
 | 
			
		||||
template <class T>
 | 
			
		||||
GwBoatItem<T>::GwBoatItem(String name, String formatInfo, unsigned long invalidTime, GwBoatItemMap *map) : GwBoatItemBase(name, formatInfo, invalidTime)
 | 
			
		||||
{
 | 
			
		||||
    T dummy;
 | 
			
		||||
            this->type=GwBoatItemTypes::getType(dummy);
 | 
			
		||||
            if (map){
 | 
			
		||||
                (*map)[name]=this;
 | 
			
		||||
    this->type = GwBoatItemTypes::getType(dummy);
 | 
			
		||||
    if (map)
 | 
			
		||||
    {
 | 
			
		||||
        (*map)[name] = this;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -140,59 +161,76 @@ void GwBoatItem<T>::toJsonDoc(GwJsonDocument *doc, unsigned long minTime)
 | 
			
		|||
    o[F("format")] = format;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class WriterWrapper
 | 
			
		||||
{
 | 
			
		||||
    GwBoatItemBase::StringWriter *writer = NULL;
 | 
			
		||||
 | 
			
		||||
class WriterWrapper{
 | 
			
		||||
    GwBoatItemBase::StringWriter *writer=NULL;
 | 
			
		||||
    public:
 | 
			
		||||
        WriterWrapper(GwBoatItemBase::StringWriter *w){
 | 
			
		||||
            writer=w;
 | 
			
		||||
public:
 | 
			
		||||
    WriterWrapper(GwBoatItemBase::StringWriter *w)
 | 
			
		||||
    {
 | 
			
		||||
        writer = w;
 | 
			
		||||
    }
 | 
			
		||||
        size_t write(uint8_t c){
 | 
			
		||||
            if (! writer) return 0;
 | 
			
		||||
    size_t write(uint8_t c)
 | 
			
		||||
    {
 | 
			
		||||
        if (!writer)
 | 
			
		||||
            return 0;
 | 
			
		||||
        return writer->write(c);
 | 
			
		||||
    }
 | 
			
		||||
        size_t write(const uint8_t* s, size_t n){
 | 
			
		||||
            if (! writer) return 0;
 | 
			
		||||
            return writer->write(s,n);
 | 
			
		||||
    size_t write(const uint8_t *s, size_t n)
 | 
			
		||||
    {
 | 
			
		||||
        if (!writer)
 | 
			
		||||
            return 0;
 | 
			
		||||
        return writer->write(s, n);
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
typedef ARDUINOJSON_NAMESPACE::TextFormatter<WriterWrapper> GwTextWriter;
 | 
			
		||||
 | 
			
		||||
static void writeToString(GwTextWriter *writer,const double &value){
 | 
			
		||||
static void writeToString(GwTextWriter *writer, const double &value)
 | 
			
		||||
{
 | 
			
		||||
    writer->writeFloat(value);
 | 
			
		||||
}
 | 
			
		||||
static void writeToString(GwTextWriter *writer,const uint16_t &value){
 | 
			
		||||
static void writeToString(GwTextWriter *writer, const uint16_t &value)
 | 
			
		||||
{
 | 
			
		||||
    writer->writeInteger(value);
 | 
			
		||||
}
 | 
			
		||||
static void writeToString(GwTextWriter *writer,const uint32_t &value){
 | 
			
		||||
static void writeToString(GwTextWriter *writer, const uint32_t &value)
 | 
			
		||||
{
 | 
			
		||||
    writer->writeInteger(value);
 | 
			
		||||
}
 | 
			
		||||
static void writeToString(GwTextWriter *writer,const int16_t &value){
 | 
			
		||||
static void writeToString(GwTextWriter *writer, const int16_t &value)
 | 
			
		||||
{
 | 
			
		||||
    writer->writeInteger(value);
 | 
			
		||||
}
 | 
			
		||||
static void writeToString(GwTextWriter *writer,GwSatInfoList &value){
 | 
			
		||||
static void writeToString(GwTextWriter *writer, GwSatInfoList &value)
 | 
			
		||||
{
 | 
			
		||||
    writer->writeInteger(value.getNumSats());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
template <class T>
 | 
			
		||||
void GwBoatItem<T>::fillString(){
 | 
			
		||||
    bool valid=isValid();
 | 
			
		||||
    if (writer.getSize() && (valid == lastStringValid)) return;
 | 
			
		||||
    lastStringValid=valid;
 | 
			
		||||
void GwBoatItem<T>::fillString()
 | 
			
		||||
{
 | 
			
		||||
    bool valid = isValid();
 | 
			
		||||
    if (writer.getSize() && (valid == lastStringValid))
 | 
			
		||||
        return;
 | 
			
		||||
    lastStringValid = valid;
 | 
			
		||||
    writer.reset();
 | 
			
		||||
    WriterWrapper wrapper(&writer);
 | 
			
		||||
    GwTextWriter stringWriter(wrapper);
 | 
			
		||||
    if (!writer.baseFilled())
 | 
			
		||||
    {
 | 
			
		||||
        stringWriter.writeRaw(name.c_str());
 | 
			
		||||
        stringWriter.writeChar(',');
 | 
			
		||||
    stringWriter.writeInteger(valid?1:0);
 | 
			
		||||
        stringWriter.writeRaw(format.c_str());
 | 
			
		||||
        stringWriter.writeChar(',');
 | 
			
		||||
        writer.setBase();
 | 
			
		||||
    }
 | 
			
		||||
    stringWriter.writeInteger(valid ? 1 : 0);
 | 
			
		||||
    stringWriter.writeChar(',');
 | 
			
		||||
    stringWriter.writeInteger(lastSet);
 | 
			
		||||
    stringWriter.writeChar(',');
 | 
			
		||||
    stringWriter.writeInteger(lastUpdateSource);
 | 
			
		||||
    stringWriter.writeChar(',');
 | 
			
		||||
    stringWriter.writeRaw(format.c_str());
 | 
			
		||||
    stringWriter.writeChar(',');
 | 
			
		||||
    writeToString(&stringWriter,data);
 | 
			
		||||
    writeToString(&stringWriter, data);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
template class GwBoatItem<double>;
 | 
			
		||||
| 
						 | 
				
			
			@ -229,8 +267,7 @@ void GwSatInfoList::update(GwSatInfo entry)
 | 
			
		|||
    sats.push_back(entry);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
GwBoatDataSatList::GwBoatDataSatList(String name, String formatInfo, unsigned long invalidTime , GwBoatItemMap *map) : 
 | 
			
		||||
        GwBoatItem<GwSatInfoList>(name, formatInfo, invalidTime, map) {}
 | 
			
		||||
GwBoatDataSatList::GwBoatDataSatList(String name, String formatInfo, unsigned long invalidTime, GwBoatItemMap *map) : GwBoatItem<GwSatInfoList>(name, formatInfo, invalidTime, map) {}
 | 
			
		||||
 | 
			
		||||
bool GwBoatDataSatList::update(GwSatInfo info, int source)
 | 
			
		||||
{
 | 
			
		||||
| 
						 | 
				
			
			@ -256,93 +293,119 @@ void GwBoatDataSatList::toJsonDoc(GwJsonDocument *doc, unsigned long minTime)
 | 
			
		|||
    GwBoatItem<GwSatInfoList>::toJsonDoc(doc, minTime);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
GwBoatData::GwBoatData(GwLog *logger){
 | 
			
		||||
    this->logger=logger;
 | 
			
		||||
GwBoatData::GwBoatData(GwLog *logger)
 | 
			
		||||
{
 | 
			
		||||
    this->logger = logger;
 | 
			
		||||
}
 | 
			
		||||
GwBoatData::~GwBoatData(){
 | 
			
		||||
GwBoatData::~GwBoatData()
 | 
			
		||||
{
 | 
			
		||||
    GwBoatItemBase::GwBoatItemMap::iterator it;
 | 
			
		||||
    for (it=values.begin() ; it != values.end();it++){
 | 
			
		||||
    for (it = values.begin(); it != values.end(); it++)
 | 
			
		||||
    {
 | 
			
		||||
        delete it->second;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
template<class T> GwBoatItem<T> *GwBoatData::getOrCreate(T initial, GwBoatItemNameProvider *provider)
 | 
			
		||||
template <class T>
 | 
			
		||||
GwBoatItem<T> *GwBoatData::getOrCreate(T initial, GwBoatItemNameProvider *provider)
 | 
			
		||||
{
 | 
			
		||||
    String name=provider->getBoatItemName();
 | 
			
		||||
    auto it=values.find(name);
 | 
			
		||||
    if (it != values.end()) {
 | 
			
		||||
        int expectedType=GwBoatItemTypes::getType(initial);
 | 
			
		||||
        if (expectedType != it->second->getCurrentType()){
 | 
			
		||||
            LOG_DEBUG(GwLog::DEBUG,"invalid type for boat item %s, expected %d, got %d",
 | 
			
		||||
                name.c_str(),expectedType,it->second->getCurrentType());
 | 
			
		||||
    String name = provider->getBoatItemName();
 | 
			
		||||
    auto it = values.find(name);
 | 
			
		||||
    if (it != values.end())
 | 
			
		||||
    {
 | 
			
		||||
        int expectedType = GwBoatItemTypes::getType(initial);
 | 
			
		||||
        if (expectedType != it->second->getCurrentType())
 | 
			
		||||
        {
 | 
			
		||||
            LOG_DEBUG(GwLog::DEBUG, "invalid type for boat item %s, expected %d, got %d",
 | 
			
		||||
                      name.c_str(), expectedType, it->second->getCurrentType());
 | 
			
		||||
            return NULL;
 | 
			
		||||
        }
 | 
			
		||||
        return (GwBoatItem<T>*)(it->second);
 | 
			
		||||
        return (GwBoatItem<T> *)(it->second);
 | 
			
		||||
    }
 | 
			
		||||
    GwBoatItem<T> *rt=new GwBoatItem<T>(name,
 | 
			
		||||
    GwBoatItem<T> *rt = new GwBoatItem<T>(name,
 | 
			
		||||
                                          provider->getBoatItemFormat(),
 | 
			
		||||
                                          provider->getInvalidTime(),
 | 
			
		||||
                                          &values);
 | 
			
		||||
    rt->update(initial);
 | 
			
		||||
    LOG_DEBUG(GwLog::LOG,"creating boatItem %s, type %d",
 | 
			
		||||
        name.c_str(),rt->getCurrentType());
 | 
			
		||||
    LOG_DEBUG(GwLog::LOG, "creating boatItem %s, type %d",
 | 
			
		||||
              name.c_str(), rt->getCurrentType());
 | 
			
		||||
    return rt;
 | 
			
		||||
}
 | 
			
		||||
template<class T> bool GwBoatData::update(const T value,int source,GwBoatItemNameProvider *provider){
 | 
			
		||||
    GwBoatItem<T> *item=getOrCreate(value,provider);
 | 
			
		||||
    if (! item) return false;
 | 
			
		||||
    return item->update(value,source);
 | 
			
		||||
template <class T>
 | 
			
		||||
bool GwBoatData::update(const T value, int source, GwBoatItemNameProvider *provider)
 | 
			
		||||
{
 | 
			
		||||
    GwBoatItem<T> *item = getOrCreate(value, provider);
 | 
			
		||||
    if (!item)
 | 
			
		||||
        return false;
 | 
			
		||||
    return item->update(value, source);
 | 
			
		||||
}
 | 
			
		||||
template bool GwBoatData::update<double>(double value,int source,GwBoatItemNameProvider *provider);
 | 
			
		||||
template<class T> T GwBoatData::getDataWithDefault(T defaultv, GwBoatItemNameProvider *provider){
 | 
			
		||||
    auto it=values.find(provider->getBoatItemName());
 | 
			
		||||
    if (it == values.end()) return defaultv;
 | 
			
		||||
    int expectedType=GwBoatItemTypes::getType(defaultv);
 | 
			
		||||
    if (expectedType != it->second->getCurrentType()) return defaultv;
 | 
			
		||||
template bool GwBoatData::update<double>(double value, int source, GwBoatItemNameProvider *provider);
 | 
			
		||||
template <class T>
 | 
			
		||||
T GwBoatData::getDataWithDefault(T defaultv, GwBoatItemNameProvider *provider)
 | 
			
		||||
{
 | 
			
		||||
    auto it = values.find(provider->getBoatItemName());
 | 
			
		||||
    if (it == values.end())
 | 
			
		||||
        return defaultv;
 | 
			
		||||
    int expectedType = GwBoatItemTypes::getType(defaultv);
 | 
			
		||||
    if (expectedType != it->second->getCurrentType())
 | 
			
		||||
        return defaultv;
 | 
			
		||||
    return ((GwBoatItem<T> *)(it->second))->getDataWithDefault(defaultv);
 | 
			
		||||
}
 | 
			
		||||
template double GwBoatData::getDataWithDefault<double>(double defaultv, GwBoatItemNameProvider *provider);
 | 
			
		||||
String GwBoatData::toJson() const {
 | 
			
		||||
    unsigned long minTime=millis();
 | 
			
		||||
String GwBoatData::toJson() const
 | 
			
		||||
{
 | 
			
		||||
    unsigned long minTime = millis();
 | 
			
		||||
    GwBoatItemBase::GwBoatItemMap::const_iterator it;
 | 
			
		||||
    size_t count=0;
 | 
			
		||||
    size_t elementSizes=0;
 | 
			
		||||
    for (it=values.begin() ; it != values.end();it++){
 | 
			
		||||
    size_t count = 0;
 | 
			
		||||
    size_t elementSizes = 0;
 | 
			
		||||
    for (it = values.begin(); it != values.end(); it++)
 | 
			
		||||
    {
 | 
			
		||||
        count++;
 | 
			
		||||
        elementSizes+=it->second->getJsonSize();
 | 
			
		||||
        elementSizes += it->second->getJsonSize();
 | 
			
		||||
    }
 | 
			
		||||
    int sz=JSON_OBJECT_SIZE(count)+elementSizes+10;
 | 
			
		||||
    LOG_DEBUG(GwLog::DEBUG,"size for boatData: %d",sz);
 | 
			
		||||
    int sz = JSON_OBJECT_SIZE(count) + elementSizes + 10;
 | 
			
		||||
    LOG_DEBUG(GwLog::DEBUG, "size for boatData: %d", sz);
 | 
			
		||||
    GwJsonDocument json(sz);
 | 
			
		||||
    for (it=values.begin() ; it != values.end();it++){
 | 
			
		||||
        it->second->toJsonDoc(&json,minTime);
 | 
			
		||||
    for (it = values.begin(); it != values.end(); it++)
 | 
			
		||||
    {
 | 
			
		||||
        it->second->toJsonDoc(&json, minTime);
 | 
			
		||||
    }
 | 
			
		||||
    String buf;
 | 
			
		||||
    serializeJson(json,buf);
 | 
			
		||||
    serializeJson(json, buf);
 | 
			
		||||
    return buf;
 | 
			
		||||
}
 | 
			
		||||
String GwBoatData::toString(){
 | 
			
		||||
String GwBoatData::toString()
 | 
			
		||||
{
 | 
			
		||||
    String rt;
 | 
			
		||||
    for (auto it=values.begin() ; it != values.end();it++){
 | 
			
		||||
        rt+=it->second->getDataString();
 | 
			
		||||
        rt+="\n";
 | 
			
		||||
    rt.reserve(values.size() * 80);
 | 
			
		||||
    for (auto it = values.begin(); it != values.end(); it++)
 | 
			
		||||
    {
 | 
			
		||||
        rt += it->second->getDataString();
 | 
			
		||||
        rt += "\n";
 | 
			
		||||
    }
 | 
			
		||||
    return rt;
 | 
			
		||||
}
 | 
			
		||||
bool GwBoatData::isValid(String name){
 | 
			
		||||
    auto it=values.find(name);
 | 
			
		||||
    if (it == values.end()) return false;
 | 
			
		||||
bool GwBoatData::isValid(String name)
 | 
			
		||||
{
 | 
			
		||||
    auto it = values.find(name);
 | 
			
		||||
    if (it == values.end())
 | 
			
		||||
        return false;
 | 
			
		||||
    return it->second->isValid();
 | 
			
		||||
}
 | 
			
		||||
GwBoatItemBase* GwBoatData::getBase(String name){
 | 
			
		||||
    auto it=values.find(name);
 | 
			
		||||
    if (it == values.end()) return NULL;
 | 
			
		||||
GwBoatItemBase *GwBoatData::getBase(String name)
 | 
			
		||||
{
 | 
			
		||||
    auto it = values.find(name);
 | 
			
		||||
    if (it == values.end())
 | 
			
		||||
        return NULL;
 | 
			
		||||
    return it->second;
 | 
			
		||||
}
 | 
			
		||||
double GwBoatData::getDoubleValue(String name,double defaultv){
 | 
			
		||||
    auto it=values.find(name);
 | 
			
		||||
    if (it == values.end()) return defaultv;
 | 
			
		||||
    if (! it->second->isValid()) return defaultv;
 | 
			
		||||
double GwBoatData::getDoubleValue(String name, double defaultv)
 | 
			
		||||
{
 | 
			
		||||
    auto it = values.find(name);
 | 
			
		||||
    if (it == values.end())
 | 
			
		||||
        return defaultv;
 | 
			
		||||
    if (!it->second->isValid())
 | 
			
		||||
        return defaultv;
 | 
			
		||||
    return it->second->getDoubleValue();
 | 
			
		||||
}
 | 
			
		||||
double formatCourse(double cv)
 | 
			
		||||
| 
						 | 
				
			
			@ -354,8 +417,9 @@ double formatCourse(double cv)
 | 
			
		|||
        rt += 360;
 | 
			
		||||
    return rt;
 | 
			
		||||
}
 | 
			
		||||
double formatDegToRad(double deg){
 | 
			
		||||
    return deg/180.0 * M_PI;
 | 
			
		||||
double formatDegToRad(double deg)
 | 
			
		||||
{
 | 
			
		||||
    return deg / 180.0 * M_PI;
 | 
			
		||||
}
 | 
			
		||||
double formatWind(double cv)
 | 
			
		||||
{
 | 
			
		||||
| 
						 | 
				
			
			@ -378,19 +442,23 @@ double mtr2nm(double m)
 | 
			
		|||
    return m / 1852.0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
bool convertToJson(const GwSatInfoList &si,JsonVariant &variant){
 | 
			
		||||
bool convertToJson(const GwSatInfoList &si, JsonVariant &variant)
 | 
			
		||||
{
 | 
			
		||||
    return variant.set(si.getNumSats());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#ifdef _UNDEF
 | 
			
		||||
#include <ArduinoJson/Json/TextFormatter.hpp>
 | 
			
		||||
 | 
			
		||||
class XWriter{
 | 
			
		||||
    public:
 | 
			
		||||
     void write(uint8_t c) {
 | 
			
		||||
class XWriter
 | 
			
		||||
{
 | 
			
		||||
public:
 | 
			
		||||
    void write(uint8_t c)
 | 
			
		||||
    {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
  void write(const uint8_t* s, size_t n) {
 | 
			
		||||
    void write(const uint8_t *s, size_t n)
 | 
			
		||||
    {
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
static XWriter xwriter;
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -14,6 +14,7 @@ class GwBoatItemBase{
 | 
			
		|||
            uint8_t *buffer =NULL;
 | 
			
		||||
            uint8_t *wp=NULL;
 | 
			
		||||
            size_t bufferSize=0;
 | 
			
		||||
            size_t baseOffset=0;
 | 
			
		||||
            void ensure(size_t size);
 | 
			
		||||
            public:
 | 
			
		||||
                StringWriter();
 | 
			
		||||
| 
						 | 
				
			
			@ -21,6 +22,8 @@ class GwBoatItemBase{
 | 
			
		|||
                size_t write(const uint8_t* s, size_t n);
 | 
			
		||||
                const char * c_str() const;
 | 
			
		||||
                int getSize() const;
 | 
			
		||||
                void setBase();
 | 
			
		||||
                bool baseFilled();
 | 
			
		||||
                void reset();
 | 
			
		||||
        };
 | 
			
		||||
        static const unsigned long INVALID_TIME=60000;
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -119,6 +119,6 @@ class TimeMonitor{
 | 
			
		|||
      current[index]=now;
 | 
			
		||||
      int64_t currentv=now-sv;
 | 
			
		||||
      if ((now-start) > max) max=now-start;
 | 
			
		||||
      times[index-1]->add(currentv);
 | 
			
		||||
      times[index]->add(currentv);
 | 
			
		||||
    }
 | 
			
		||||
};
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1205,10 +1205,10 @@ function parseBoatDataLine(line){
 | 
			
		|||
    let rt={};
 | 
			
		||||
    let parts=line.split(',');
 | 
			
		||||
    rt.name=parts[0];
 | 
			
		||||
    rt.valid=parts[1] === '1';
 | 
			
		||||
    rt.update=parseInt(parts[2]);
 | 
			
		||||
    rt.source=parseInt(parts[3]);
 | 
			
		||||
    rt.format=parts[4];
 | 
			
		||||
    rt.valid=parts[2] === '1';
 | 
			
		||||
    rt.update=parseInt(parts[3]);
 | 
			
		||||
    rt.source=parseInt(parts[4]);
 | 
			
		||||
    rt.format=parts[1];
 | 
			
		||||
    rt.value=parts[5];
 | 
			
		||||
    return rt;
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in New Issue