Last active
November 8, 2017 22:08
-
-
Save deanhu2/9cc7c92e6a03c004fa6e2ccd25fd5369 to your computer and use it in GitHub Desktop.
A simple example on abstracting a UI interface, and creating a MVVM register component that controls communication via events.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/****************************************************************************** | |
Online C++ Compiler. | |
Code, Compile, Run and Debug C++ program online. | |
Write your code in this editor and press "Run" button to compile and execute it. | |
*******************************************************************************/ | |
#include "stdafx.h" | |
#include <iostream> | |
#include <vector> | |
#include <utility> | |
#include <map> | |
#include <queue> | |
#include <memory> | |
using namespace std; | |
struct IComponent | |
{ | |
virtual ~IComponent() {}; | |
virtual void setWidth(int width) const = 0; | |
virtual void setHeight(int height) const = 0; | |
virtual void setX(int x) const = 0; | |
virtual void setY(int y) const = 0; | |
virtual int getX() const = 0; | |
virtual int getY() const = 0; | |
virtual int getWidth() const = 0; | |
virtual int getHeight() const = 0; | |
}; | |
struct BaseComponent : public IComponent | |
{ | |
virtual ~BaseComponent() {}; | |
BaseComponent() : m_x(0), m_y(0), m_width(100), m_height(100) {}; | |
BaseComponent(int x, int y, int width, int height) {}; | |
BaseComponent(const BaseComponent & copy) { std::cout << "copy" << std::endl; }; | |
BaseComponent(const BaseComponent && move) : m_x(0), m_y(0), m_width(100), m_height(100) { std::cout << "move " << std::endl; }; | |
virtual void setWidth(int width)const {}; | |
virtual void setHeight(int height) const {}; | |
virtual void setX(int x) const {}; | |
virtual void setY(int y) const {}; | |
virtual int getX() const { return m_x; }; | |
virtual int getY() const { return m_y; }; | |
virtual int getWidth() const { return m_width; }; | |
virtual int getHeight() const { return m_height; }; | |
virtual BaseComponent& operator=(BaseComponent&& other) { return *this; }; | |
private: | |
int m_width; | |
int m_height; | |
int m_x; | |
int m_y; | |
std::string m_Type; | |
}; | |
struct Window : public BaseComponent | |
{ | |
virtual ~Window() {}; | |
Window() : m_x(0), m_y(0), m_width(100), m_height(100) {}; | |
Window(int x, int y, int width, int height) {}; | |
virtual void setWidth(int width)const {}; | |
virtual void setHeight(int height) const {}; | |
virtual void setX(int x) const {}; | |
virtual void setY(int y) const {}; | |
virtual int getX() const { return m_x; }; | |
virtual int getY() const { return m_y; }; | |
virtual int getWidth() const { return m_width; }; | |
virtual int getHeight() const { return m_height; }; | |
private: | |
int m_width; | |
int m_height; | |
int m_x; | |
int m_y; | |
}; | |
enum UIEvent | |
{ | |
click = 0, | |
}; | |
struct RegisterComponent | |
{ | |
public: | |
RegisterComponent(std::unique_ptr<IComponent> component, UIEvent event) :m_Component(std::move(component)), m_Event(event) {}; | |
virtual ~RegisterComponent() {}; | |
RegisterComponent(const RegisterComponent& a) {}; | |
virtual IComponent& getComponent() { return *m_Component; }; | |
virtual UIEvent getEvent() { return m_Event; }; | |
private: | |
std::unique_ptr<IComponent> m_Component; | |
UIEvent m_Event; | |
}; | |
struct ComponentRegister | |
{ | |
public: | |
virtual ~ComponentRegister() {}; | |
ComponentRegister() :m_Index(0) {}; | |
virtual void registerComponentEvent(std::unique_ptr<IComponent> component, UIEvent event) | |
{ | |
RegisterComponent r(std::move(component), event); | |
auto ff = std::make_pair(m_Index, r); | |
m_Register.insert(ff); | |
m_Index++; | |
}; | |
virtual std::map<int, RegisterComponent>& getRegister() { return m_Register; }; | |
virtual bool searchEvent(UIEvent& m_Event) | |
{ | |
for (auto it = m_Register.begin(); it != m_Register.end(); ++it) | |
{ | |
auto f = it->first; | |
auto f2 = it->second; | |
auto f11 = f2.getEvent(); | |
switch (f11) | |
{ | |
case click: | |
{ | |
cout << "clicked"; | |
break; | |
} | |
default:break; | |
} | |
return true; | |
} | |
return false; | |
}; | |
protected: | |
private: | |
int m_Index; | |
std::map<int, RegisterComponent> m_Register; | |
}; | |
struct EventAggregator | |
{ | |
public: | |
virtual ~EventAggregator() {}; | |
EventAggregator() {}; | |
virtual void setRegister(std::unique_ptr<ComponentRegister> r) | |
{ | |
m_Register = std::move(r); | |
}; | |
virtual void addEvent(UIEvent event) | |
{ | |
m_Events.push(event); | |
}; | |
//may need mutex implementation for thread safety | |
virtual void Listen() { | |
while (!m_Events.empty()) | |
{ | |
auto l = m_Register.get(); | |
auto q_element = m_Events.front(); | |
if (l) | |
{ | |
l->searchEvent(q_element); | |
m_Events.pop(); | |
} | |
} | |
}; | |
protected: | |
private: | |
std::queue<UIEvent> m_Events; | |
std::unique_ptr<ComponentRegister> m_Register; | |
}; | |
int main() | |
{ | |
//create component register | |
std::unique_ptr<ComponentRegister> R = make_unique<ComponentRegister>(); | |
//create components | |
std::unique_ptr<Window> w = make_unique<Window>(); | |
//create event aggregator | |
EventAggregator A; | |
R.get()->registerComponentEvent(std::move(w), click); | |
A.setRegister(std::move(R)); | |
A.addEvent(click); | |
A.Listen(); | |
cout << "Press Enter to Continue"; | |
cin.ignore(); | |
//R.registerComponentEvent(std::move(w), click); | |
//R.registerComponent(w); | |
//R.registerComponent(w); | |
//cout << "X:" << w.getX() << " y:" << w.getY() << " Width:" << w.getWidth() << " Height:" << w.getHeight(); | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment