2016-04-18 10 views
-1

Ich habe diese KlasseC++ Lambda Callback - Wie erfasst man Variablen?

typedef void(*callback)(); 

class Button : public Control 
{ 
private: 
    callback onClickCallback; 

public: 
    void bind(callback func) 
    { 
     onClickCallback = func; 
    } 

    void onClick() 
    { 
     onClickCallback(); 
    } 
}; 

Button Control erbt die als Komponente in der Gui-Klasse zugeordnet ist. Die Gui-Klasse verfügt über eine Methode, die die onClick-Methode jeder Komponente in der Liste aufruft. Das OnClick Methode Rückruf ist Lambda-Ausdruck

Gui gui; 
gui.addControl<Button>(x, y, width, height).bind([] { 
    MessageBox(NULL, "OK", "OK", 0); 
    //How to capture gui 
    //Eg add another button on click: 
    //gui.addControl<Button>(x, y, width, height); 
}); 

ist die gui Klasse

class Gui 
{ 
private: 
    int index; 
    std::unordered_multimap<int, Control*> controls; 

public: 
    template <typename T, typename ...Args> 
    T& addControl(Args... args) 
    { 

     auto control = new T{ std::forward<Args>(args)... }; 
     std::pair<int, Control*> pair(index, control); 
     controls.insert(pair); 
     index++; 

     return *control; 
    } 

    void processMessages() 
    { 
     for (auto it = controls.begin(); it != controls.end(); ++it) 
     { 
      it->second->onClick(); 
     } 
    } 
}; 
+1

Sie kein Lambda mit Capture einen Funktionszeiger umwandeln kann. Sie müssen den Typ des Rückrufs in etwas ändern, in das er konvertiert werden kann. – Holt

+0

Völlig unklar, was Sie erfassen müssen. Ist Ihre Frage zur generellen Capture-Syntax oder ist Ihnen ein bestimmter Fall unklar? Wenn es das erstere ist, müssen Sie sich auf die Dokumentation beziehen, wenn letzterer, klareren Code post. – SergeyA

+2

@Holt, nicht erfassende Lambdas können in Funktionszeiger umgewandelt werden. – SergeyA

Antwort

0

ich es tatsächlich getan hat, ich weiß nicht, ob dies die richtige Lösung ist, aber es scheint zu funktionieren.

Die Button-Klasse wurde aktualisiert.

class Button : public Control 
{ 
private: 
    std::function<void()> onClickCallback; 

public: 
    //Override 
    void bind(std::function<void()> func) 
    { 
     onClickCallback = func; 
    } 

    //Override 
    void onClick() 
    { 
     onClickCallback(); 
    } 
}; 

Es funktioniert jetzt! auch zusätzliche Unterstützung für verschiedene Veranstaltungen wie zB mouse_click, on_focus_gained etc ...

gui.addControl<Button>(hWnd, "Button", 3, 26, 70, 23).bind("mouse_click", [&] { 
    gui.getControl<Button>(0).setText("Clicked"); 
}); 
Verwandte Themen