Pubsubclient: setCallback in custom library error

Created on 7 Jul 2017  Â·  9Comments  Â·  Source: knolleary/pubsubclient

Hi,

I'm writing a custom library sourcing PubSubClient. Everything went well expect for integrating the callback function in my library.

I get the following errors from the Arduino IDE:

Error: no matching function for call to 'PubSubClient::setCallback("<"unresolved overloaded function type">")' client -> setCallback(callback);

In my xxx.h file I declared the following:

class Iotdevice {
...
void callback(char* topic, byte* payload, unsigned int length);
...
}

In my xxx.cpp I defined the following:

void Iotdevice::callback(char* topic, byte* payload, unsigned int length) {...}

I have tried a lot of variations, but I can't seem to solve it. Can anyone help me out?

Most helpful comment

Found this solution online.
https://hobbytronics.com.pk/arduino-custom-library-and-pubsubclient-call-back/
MQTTClient.setServer(MQTT_SERVER, 1883);
MQTTClient.setCallback([this] (char* topic, byte* payload, unsigned int length) { this->callback(topic, payload, length); });

All 9 comments

You can't use a class function for the callback. Define a global function and then call the class function from there.

Correct but wouldn't it be nice to if u could overload the method in a subclass.

@Pimmetje That would be nice to. Haven't tried that one.

I tried it. I made some small changes to the library and it worked for the simple tests i did. But it requires your to inherit from PubSubClient in order to overload the method of course.
I was working on this to make a base class that would handle wifi mqtt connecting and reconnecting without reprogramming it for every project. I also added a http update server just for fun but now i am getting off topic.
If u need a example let me know.

Hi,
What modifications had you made to PubSubClient to use the callback in another Class?
Thanks

Simon

Just a quick and dirty writeup (untested). If someone wants a proper diff let me know but it ill take me a little more time :D

Relevant part of the loop code: note the this->_callback lines:

                    if ((buffer[0]&0x06) == MQTTQOS1) {
                        msgId = (buffer[llen+3+tl]<<8)+buffer[llen+3+tl+1];
                        payload = buffer+llen+3+tl+2;
                        this->_callback(topic,payload,len-llen-3-tl-2);

                        buffer[0] = MQTTPUBACK;
                        buffer[1] = 2;
                        buffer[2] = (msgId >> 8);
                        buffer[3] = (msgId & 0xFF);
                        _client->write(buffer,4);
                        lastOutActivity = t;

                    } else {
                        payload = buffer+llen+3+tl;
                        this->_callback(topic,payload,len-llen-3-tl);
                    }

Added methods (h file)

private:
void _callback(char* topic, byte* payload, unsigned int len);
protected:
   virtual void onCallback(char* topic, byte* payload, unsigned int len);

Added methods (cpp file):

/**
 * This method should be overloaded. If the method is not overload the old callback will work
 * 
 * If the method is overloaded and the parent is called both onCallback and the
 * old style will get executed
 */
void PubSubClient::onCallback(char* topic, byte* payload, unsigned int len) {
    if (callback) {
        callback(topic, payload, len);
    }
}

void PubSubClient::_callback(char* topic, byte* payload, unsigned int len) {
    this->onCallback(topic, payload, len);
}

Everything works well !!!I found a very simple solution by declaring the callback of the following trend:
mqttClient.setCallback ([this] (char * topic, byte * payload, unsigned integer length) {this -> _ mqtt_callback (subject, payload, length);});
and works
Thank you for your help!
Simon

Le mercredi 18 octobre 2017 à 16:01:13 UTC+2, Pimmetje <[email protected]> a écrit :

Just a quick and dirty writeup (untested). If someone wants a proper diff let me know but it ill take me a little more time :D

Relevant part of the loop code: note the this->_callback lines:
if ((buffer[0]&0x06) == MQTTQOS1) {
msgId = (buffer[llen+3+tl]<<8)+buffer[llen+3+tl+1];
payload = buffer+llen+3+tl+2;
this->_callback(topic,payload,len-llen-3-tl-2);

                    buffer[0] = MQTTPUBACK;
                    buffer[1] = 2;
                    buffer[2] = (msgId >> 8);
                    buffer[3] = (msgId & 0xFF);
                    _client->write(buffer,4);
                    lastOutActivity = t;

                } else {
                    payload = buffer+llen+3+tl;
                    this->_callback(topic,payload,len-llen-3-tl);
                }

Added methods (h file)
private:
void _callback(char* topic, byte* payload, unsigned int len);
protected:
virtual void onCallback(char* topic, byte* payload, unsigned int len);

Added methods (cpp file):
/**

  • This method should be overloaded. If the method is not overload the old callback will work


    • If the method is overloaded and the parent is called both onCallback and the

  • old style will get executed
    /
    void PubSubClient::onCallback(char
    topic, byte* payload, unsigned int len) {
    if (callback) {
    callback(topic, payload, len);
    }
    }

void PubSubClient::_callback(char* topic, byte* payload, unsigned int len) {
this->onCallback(topic, payload, len);
}

—
You are receiving this because you commented.
Reply to this email directly, view it on GitHub, or mute the thread.

Found this solution online.
https://hobbytronics.com.pk/arduino-custom-library-and-pubsubclient-call-back/
MQTTClient.setServer(MQTT_SERVER, 1883);
MQTTClient.setCallback([this] (char* topic, byte* payload, unsigned int length) { this->callback(topic, payload, length); });

Hello , is this still open ? . Can anyone help me i tried solution that @yozmag typed but i keep getting error

/Users/arminsalcin/Documents/Arduino/libraries/Farmica/farma.cpp: In constructor 'Farma::Farma()':
/Users/arminsalcin/Documents/Arduino/libraries/Farmica/farma.cpp:19:120: error: no matching function for call to 'PubSubClient::setCallback(Farma::Farma()::<lambda(char*, byte*, unsigned int)>)'
 client.setCallback([this] (char* topic, byte* payload, unsigned int length) { this->callback(topic, payload, length); });
                                                                                                                        ^
In file included from /Users/arminsalcin/Documents/Arduino/libraries/Farmica/farma.h:15:0,
                 from /Users/arminsalcin/Documents/Arduino/libraries/Farmica/farma.cpp:1:
/Users/arminsalcin/Documents/Arduino/libraries/pubsubclient-2.5/src/PubSubClient.h:121:18: note: candidate: PubSubClient& PubSubClient::setCallback(void (*)(char*, uint8_t*, uint32_t))
    PubSubClient& setCallback(MQTT_CALLBACK_SIGNATURE);
                  ^

In cpp file

Farma::Farma(){
client.setCallback([this] (char* topic, byte* payload, unsigned int length) { this->callback(topic, payload, length); });

}


void Farma::callback(char *topic, byte *payload, unsigned int length)
{
//some code
}

in h file
void callback(char *topic, byte*payload, unsigned int length);

////////////////////
Fixedd !!!
As i used ESP32 i need in 'PubSubClient.h' to change :
#ifdef ESP8266
to
#if defined (ESP8266) || defined(ESP32)

Was this page helpful?
0 / 5 - 0 ratings