notdodo
notdodo

Reputation: 149

c++ inject function in class

I've this base class:

class Task {
private:
    bool enabled;
    void (*foo)();
public:
    virtual void init(int period) { enabled = true; }
    virtual void tick() = 0;

    void high(void (*f)()) { foo = f; }

    void callFoo() { foo(); }

    bool isEnabled() { return enabled; }
};

and a class which implements Task with this method:

LedTask::LedTask(int pin, Context* pContext) {
    this->pin = pin;
    this->pContext = pContext;
}

void LedTask::init(int period) {
    Task::init(period);
    this->led = new Led(pin);
}

void LedTask::tick() {
    Task::callFoo();

}

in main():

Task* t3 = new LedTask(LED_PIN, c);
t3->init(50);
t3->high([]{Serial.println("ok");});

This works but I'd like to know how to access private (and public) member of t3 instance; something like:

t3->high([]{ led->switchOn(); });

In short, I want to inject a function in a class and use its class members in it.

Upvotes: 1

Views: 2580

Answers (1)

πάντα ῥεῖ
πάντα ῥεῖ

Reputation: 1

As mentioned in my comment I suppose your LedTask class inherits from Task.

So you should drop the function pointer in the Task class in favor of a pure virtual function, that must be implemented in the inheriting classes:

class Task {
private:
    bool enabled;
protected: 
    virtual void foo() = 0; // <<<<<<<<<<<<<<<<<<<<<<<<<<
public:
    virtual void init(int period) { enabled = true; }
    virtual void tick() = 0;

    // void high(void (*f)()) { foo = f; } << not needed

    void callFoo() { foo(); }

    bool isEnabled() { return enabled; }
};

then in a second step in LedTask implement foo based on a std::function constructor parameter:

class LedTask : public Task {
public:
    LedTask(uint8_t pin, Context* pContext , std::function<void()> f) 
    : pin_(pin), pContext_(pContext), f_(f) {
    }
private:
    void foo() {
        f_();
    }
    uint8_t pin_;
    Context* pContext_;
    std::function<void()> f_;
};

Well, from your comments it sounds you'll need the Led object as a parameter for your injected function.

That member pointer for Led created in init() should be passed to the injected function.

You can either use something like

    std::function<void(Led&)> f_;

or

    void(*f_)(Led&);

Passing that parameter is done in the implementation as from above:

    void foo() {
        f_(*led);
    }

Upvotes: 1

Related Questions