remove return type of slot callback 74/241474/1
authorMinJeong Kim <minjjj.kim@samsung.com>
Mon, 10 Feb 2020 10:40:39 +0000 (19:40 +0900)
committerSung-Jin Park <sj76.park@samsung.com>
Thu, 20 Aug 2020 09:43:12 +0000 (18:43 +0900)
Change-Id: If79805f1a4e88e61efe92574a3e5b0849ef738fd
Signed-off-by: MinJeong Kim <minjjj.kim@samsung.com>
src/bin/main.cpp [deleted file]
src/bin/sample1.cpp [new file with mode: 0644]
src/core/WObject.cpp
src/core/WObject.h
src/core/WObjectPrivate.h
src/core/WRefBase.h
src/core/WSignal.h

diff --git a/src/bin/main.cpp b/src/bin/main.cpp
deleted file mode 100644 (file)
index c0c004f..0000000
+++ /dev/null
@@ -1,58 +0,0 @@
-
-#include "../core/WObject.h"
-#include "../core/WSignal.h"
-#include <string>
-
-using namespace TizenDisplayServer;
-
-using SignalAType = WSignal<int, int>;
-using SignalBType = WSignal<double, int>;
-
-class MJ : public WObject
-{
-    public:
-    MJ() : WObject("MJ"){ std::cout << "construct MJ" << std::endl;}
-    MJ(std::string name) : WObject(name) {std::cout << "construct MJ" << name << std::endl;}
-    ~MJ(){ std::cout << "destruct MJ" << std::endl;}
-
-    struct SignalA : public SignalAType {
-        int emit(int val) { return SignalAType::emit(val); }
-    } signalA;
-
-    struct SignalB : public SignalBType {
-        double emit(int val) { return SignalBType::emit(val); }
-    } signalB;
-};
-
-class Holder : public WObject {
-    public:
-    Holder() : WObject("Holder") {std::cout << "construct Holder" << std::endl;}
-    Holder(std::string name) : WObject(name) {std::cout << "construct Holder" << std::endl;}
-    ~Holder() {std::cout << "destruct Holder" << std::endl;}
-
-    static int slotA(int a) { std::cout << "slotA invoked! a:" << a << std::endl; return 1; };
-    static double slotB(int a) { std::cout << "slotB invoked! a:" << a << std::endl; return 123.456; };
-    static int slotA2(int a) {std::cout << "slotA2 invoked! a:" << a << std::endl; return 2;}
-};
-
-int main (void)
-{
-    MJ mj("mj");
-    MJ mj2("mj2");
-    Holder holder("h1");
-    Holder holder2("h2");
-
-    std::cout << "<<<<<<<< slotA connect to signala >>>>>>>>" << std::endl;
-    mj.signalA.connect(&holder, Holder::slotA);
-    std::cout << "<<<<<<<< slotA2 connect to signala >>>>>>>>" << std::endl;
-    mj.signalA.connect(&holder, Holder::slotA2);
-    
-    std::cout << "<<<<<<<< slotB connect to signalB >>>>>>>>" << std::endl;
-    mj.signalB.connect(&holder, Holder::slotB);
-
-
-    int a  = mj.signalA.emit(1234);
-    double b = mj.signalB.emit(5678);
-
-    return 0;
-}
\ No newline at end of file
diff --git a/src/bin/sample1.cpp b/src/bin/sample1.cpp
new file mode 100644 (file)
index 0000000..acb5f61
--- /dev/null
@@ -0,0 +1,69 @@
+#include "../core/WObject.h"
+#include "../core/WSignal.h"
+#include "../core/WRefBase.h"
+#include <string>
+
+using namespace TizenDisplayServer;
+
+using SignalAType = WSignal<int>;
+using SignalBType = WSignal<double>;
+
+class Sender : public WObject
+{
+    public:
+    Sender() : WObject("Sender"){ std::cout << "construct Sender" << std::endl;}
+    Sender(std::string name) : WObject(name) {std::cout << "construct Sender " << name << std::endl;}
+    ~Sender(){ std::cout << "destruct Sender " << getName() << std::endl;}
+
+    struct SignalA : public SignalAType {
+        void emit(int val) { SignalAType::emit(val); }
+    } signalA;
+
+    struct SignalB : public SignalBType {
+        void emit(double val) { SignalBType::emit(val); }
+    } signalB;
+};
+
+class Receiver : public WObject, public WRefBase {
+    public:
+    Receiver() : WObject("Receiver"), WRefBase() { std::cout << "construct Receiver" << std::endl;}
+    Receiver(std::string name) : WObject(name), WRefBase() { std::cout << "construct Receiver " << name << std::endl;}
+    ~Receiver() { std::cout << "destruct Receiver(ref: " << getref() << ") " << getName() << std::endl; }
+
+    static void slotA(int a) { std::cout << "slotA invoked! a:" << a << std::endl; };
+    static void slotA2(int a) {std::cout << "slotA2 invoked! a:" << a << std::endl; }
+    static void slotB(double a) { std::cout << "slotB invoked! a:" << a << std::endl; };
+};
+
+int main (void)
+{
+    Sender *sender = new Sender("sender");
+    Sender *sender2 = new Sender("sender2");
+    Receiver *receiver = new Receiver("receiver1");
+    Receiver *receiver2 = new Receiver("receiver2");
+
+    sender->signalA.connect(receiver, Receiver::slotA);
+    sender->signalA.connect(receiver2, Receiver::slotA2);
+    sender->signalB.connect(receiver, Receiver::slotB);
+    sender->signalB.connect(receiver2, [](double val) {
+        std::cout << "Lambda slot invoked! val: " << val << std::endl;
+    });
+
+    sender->signalA.emit(1234);
+    sender->signalB.emit(45.67);
+
+    if (receiver2->getref() == 1)
+    {
+        receiver2->unref();
+        receiver2 = nullptr;
+    }
+
+    sender->signalB.emit(5678);
+    sender->signalA.emit(90.1);
+
+    delete sender;
+    delete sender2;
+    delete receiver;
+
+    return 0;
+}
\ No newline at end of file
index d46b329..53152db 100644 (file)
@@ -5,17 +5,46 @@ namespace TizenDisplayServer{
     WObjectPrivate::WObjectPrivate(WObject *p_ptr, std::string name) : p_ptr(p_ptr)
     {
         type_info.name = name;
-        std::cout << "construct WObjectPrivate" << std::endl;
     }
 
     WObjectPrivate::~WObjectPrivate()
     {
-        std::cout << "destruct WObjectPrivate" << std::endl;
+    }
+
+    void WObjectPrivate::attachDestroyObserver(WObjectObserverIface *ob)
+    {
+        observers.push_back(ob);
+    }
+
+    void WObjectPrivate::detachDestroyObserver(WObjectObserverIface *ob)
+    {
+        observers.remove(ob);
+    }
+
+    bool WObjectPrivate::setProperty(std::string key, WProperty property)
+    {
+    }
+
+    WProperty& WObjectPrivate::getProperty(std::string key)
+    {
+    }
+
+    void WObjectPrivate::destroyNotify(void)
+    {
+        for (WObjectObserverIface* ob : observers)
+        {
+            ob->destroyed(p_ptr);
+        }
+        observers.clear();
+    }
+
+    std::string WObjectPrivate::getName(void)
+    {
+        return type_info.name;
     }
 
     WObject::WObject(std::string name)
     {
-        std::cout << "construct WOBject " << name <<std::endl;
         std::unique_ptr<WObjectPrivate> ptr(new WObjectPrivate(this, name));
         d_ptr = std::move(ptr);
     }
@@ -23,4 +52,34 @@ namespace TizenDisplayServer{
     WObject::~WObject(){
         destroyNotify();
     }
+
+    void WObject::destroyNotify(void)
+    {
+        d_func()->destroyNotify();
+    }
+
+    void WObject::attachDestroyObserver(WObjectObserverIface *ob)
+    {
+        d_func()->attachDestroyObserver(ob);
+    }
+
+    void WObject::detachDestroyObserver(WObjectObserverIface *ob)
+    {
+        d_func()->detachDestroyObserver(ob);
+    }
+
+    bool WObject::setProperty(std::string key, WProperty property)
+    {
+
+    }
+
+    WProperty& WObject::getProperty(std::string key)
+    {
+
+    }
+
+    std::string WObject::getName(void)
+    {
+        return d_func()->getName();
+    }
 }
index 46e52f3..86a4211 100644 (file)
@@ -19,18 +19,19 @@ class WObject {
 
     inline WObjectPrivate* d_func() { return d_ptr.get(); }
     inline const WObjectPrivate* d_func() const { return d_ptr.get(); }
-    friend class WObjectPrivate;
 
     public:
-    WObject(std::string name = "default");
+    WObject(std::string name = "WObject");
     virtual ~WObject();
 
-    void attachObserver(WObjectObserverIface *ob){}
-    void detachObserver(WObjectObserverIface *ob){}
-    void destroyNotify(void){}
-    bool setProperty(std::string key, WProperty property){}
-    WProperty& getProperty(std::string key){}
+    void attachDestroyObserver(WObjectObserverIface *ob);
+    void detachDestroyObserver(WObjectObserverIface *ob);
+    void destroyNotify(void);
 
+    bool setProperty(std::string key, WProperty property);
+    WProperty& getProperty(std::string key);
+
+    std::string getName(void);
 };
 
 class WObjectObserverIface {
index a0ca476..8bd9a0d 100644 (file)
@@ -15,15 +15,15 @@ class WObjectObserverIface;
 
 class WObjectPrivate {
 
-    struct {
+    struct TypeInfo{
         std::string name;
-
-    }type_info;
+    };
 
     WObject *p_ptr;
 
     std::list<WObjectObserverIface*> observers;
     std::unordered_map<std::string, WProperty> properties;
+    TypeInfo type_info;
 
     public:
     WObjectPrivate() = delete;
@@ -32,10 +32,13 @@ class WObjectPrivate {
 
     inline const WObject *p_func() const{ return p_ptr;}
 
-    void attachObserver(WObjectObserverIface *ob);
-    void detachObserver(WObjectObserverIface *ob);
+    void attachDestroyObserver(WObjectObserverIface *ob);
+    void detachDestroyObserver(WObjectObserverIface *ob);
     bool setProperty(std::string key, WProperty property);
     WProperty& getProperty(std::string key);
+    void destroyNotify();
+
+    std::string getName(void);
 };
 }
 #else
index 970c91b..00007f8 100644 (file)
@@ -6,10 +6,10 @@ class WRefBase {
     int mCount;
 
     public:
-    WRefBase() : mCount(0) {};
-    virtual ~WRefBase();
+    WRefBase() : mCount(1) {}
+    virtual ~WRefBase() {}
 
-    void ref() {++mCount;}
+    void ref() { ++mCount; }
     void unref() {if (--mCount == 0) delete this;}
     int  getref() { return mCount; }
 };
index 741c0da..578620d 100644 (file)
@@ -15,52 +15,57 @@ namespace TizenDisplayServer{
         ~WSlotsObserver(){}
 
         virtual void destroyed(WObject *obj);
-        void addSlot(WObject *slot);
+        virtual void addSlot(WObject *slot);
     };
 
-    template <typename R, typename... Args>
+    template <typename... Args>
     class WSlotConnection : public WSlotsObserver{
         //TODO: make callback as callback iface
         //std::unique_ptr<WCallbackIface> callback;
-        R (*callback)(Args...);
-        template <typename _R, typename... _Args> friend class WSignal;
+        void (*callback)(Args...);
+        template <typename... _Args> friend class WSignal;
 
         public:
         WSlotConnection() {}
-        WSlotConnection(WObject *slot, R (*func) (Args...)) : callback(func) {
+        WSlotConnection(WObject *slot, void (*func) (Args...)) : callback(func) {
             //TODO: make callback as callback iface
             //std::unique_ptr<WCallbackIface> ptr(new WCallbackIface(func));
             //callback = std::move(ptr);
             addSlot(slot);
         }
-        virtual ~WSlotConnection() {}
+        virtual ~WSlotConnection()
+        {
+            for (auto &&slot : slots)
+                slot->detachDestroyObserver(this);
+            slots.clear();
+        }
 
-        void addSlot(WObject *slot)
+        void addSlot (WObject *slot) override
         {
             slots.push_back(slot);
+            slot->attachDestroyObserver(this);
         }
-        void destroyed(WObject *slot)
+        void destroyed(WObject *slot) override
         {
             slots.remove(slot);
             if (slots.empty())
-                delete this;
+            {
+                //TODO: detete from WSignal connections list with guarded pointer
+            }
         }
 
-        R invoke(Args... args)
+        void invoke(Args... args)
         {
-            if (!std::is_void<R>::value)
-            {
-                R ret = callback(args...);
-                return ret;
-            }
+            if (!slots.empty())
+                callback(args...);
         }
 
     };
 
-    template <typename R, typename... Args>
+    template <typename... Args>
     class WSignal {
-        std::list<std::unique_ptr<WSlotConnection<R, Args...>>> connections;
-        WSlotConnection<R, Args...> *findcon(R (*func)(Args...)) {
+        std::list<std::unique_ptr<WSlotConnection<Args...>>> connections;
+        WSlotConnection<Args...> *findcon(void (*func)(Args...)) {
             for (auto&& con : connections)
             {
               if (con->callback == func)
@@ -73,29 +78,27 @@ namespace TizenDisplayServer{
         WSignal() {}
         virtual ~WSignal() {}
 
-        WSignal<R, Args...>& operator()(void) { return *this; } // functor
+        WSignal<Args...>& operator()(void) { return *this; } // functor
 
-        void connect(WObject *slot, R (*func)(Args...))
+        void connect(WObject *slot, void (*func)(Args...))
         {
             if ((!slot) || (!func))
                 return;
             if (auto con = findcon(func))
+            {
                 con->addSlot(slot);
+            }
             else
-                connections.emplace_back(new WSlotConnection<R, Args...>(slot, func));
-        }
-
-        R emit(Args... args){
-            if (!std::is_void<R>::value)
             {
-                R ret;
-                for (auto &&con : connections)
-                {
-                    ret = con->invoke(args...);
-                }
-                return ret;
+                connections.emplace_back(new WSlotConnection<Args...>(slot, func));
             }
         }
+
+        void emit(Args... args)
+        {
+            for (auto &&con : connections)
+                con->invoke(args...);
+        }
     };
 }
 #else