1+ #include < iostream>
2+
3+ namespace Problem
4+ {
5+ class Widget
6+ {
7+ public:
8+ virtual ~Widget () = default ;
9+ virtual std::string clickOn () const = 0;
10+ };
11+
12+ /* Concrete variations for Button */
13+ class Button : public Widget
14+ {
15+ public:
16+ virtual ~Button () = default ;
17+
18+ public:
19+ std::string clickOn () const override
20+ {
21+ return " Click on: Button\n " ;
22+ }
23+ };
24+
25+ class ButtonWindows : public Button
26+ {
27+ public:
28+ std::string clickOn () const override
29+ {
30+ return " [Linux]" + Button::clickOn ();
31+ }
32+ };
33+
34+ class ButtonLinux : public Button
35+ {
36+ public:
37+ std::string clickOn () const override
38+ {
39+ return " [Windows]" + Button::clickOn ();
40+ }
41+ };
42+
43+ /* Concrete variations for Label */
44+ class Label : public Widget
45+ {
46+ public:
47+ virtual ~Label () = default ;
48+
49+ public:
50+ std::string clickOn () const override
51+ {
52+ return " Click on: Label\n " ;
53+ }
54+ };
55+
56+ class LabelWindows : public Label
57+ {
58+ public:
59+ std::string clickOn () const override
60+ {
61+ return " [Windows]" + Label::clickOn ();
62+ }
63+ };
64+
65+ class LabelLinux : public Label
66+ {
67+ public:
68+ std::string clickOn () const override
69+ {
70+ return " [Linux]" + Label::clickOn ();
71+ }
72+ };
73+
74+ /* Concrete variations for others widgets like Text,CCombo or new platform macOS etc*/
75+ // [Problem 1] We have to write the Text/TextLinux ...
76+
77+ namespace Client
78+ {
79+ void clientCode (const Widget *widget)
80+ {
81+ if (widget != nullptr )
82+ std::cout << widget->clickOn ();
83+ }
84+ }
85+
86+ void run ()
87+ {
88+ // [Problem 2] : Use the Bridge if you need to be able to switch implementations at runtime. how to exmaple for this
89+ // still don't know
90+ Widget *button = new ButtonWindows ();
91+ Client::clientCode (button);
92+ delete button;
93+ }
94+ }
95+
96+ namespace BridgePattern
97+ {
98+ /* *
99+ * The Implementation defines the interface for all implementation classes. It
100+ * doesn't have to match the Abstraction's interface. In fact, the two
101+ * interfaces can be entirely different. Typically the Implementation interface
102+ * provides only primitive Widgets, while the Abstraction defines higher-
103+ * level Widgets based on those primitives.
104+ */
105+ class OsImplemetation
106+ {
107+ public:
108+ virtual std::string clickOnImplement () const = 0;
109+ virtual ~OsImplemetation () = default ;
110+ };
111+
112+ class WindowsImplemetation : public OsImplemetation
113+ {
114+ public:
115+ std::string clickOnImplement () const override
116+ {
117+ return " [Windows]" ;
118+ }
119+ };
120+
121+ class LinuxImplemetation : public OsImplemetation
122+ {
123+ public:
124+ std::string clickOnImplement () const override
125+ {
126+ return " [Linux]" ;
127+ }
128+ };
129+
130+ /* *
131+ * The Abstraction defines the interface for the "control" part of the two class
132+ * hierarchies. It maintains a reference to an object of the Implementation
133+ * hierarchy and delegates all of the real work to this object.
134+ */
135+ class WidgetAbstraction
136+ {
137+ protected:
138+ OsImplemetation *_implementation;
139+
140+ public:
141+ explicit WidgetAbstraction (OsImplemetation *implemetation) : _implementation{implemetation}
142+ {
143+ }
144+ virtual ~WidgetAbstraction () = default ;
145+
146+ virtual std::string clickOn () const = 0;
147+ };
148+
149+ /* *
150+ * We can extend the Abstraction without changing the Implementation classes.
151+ */
152+ class ButtonAbstraction : public WidgetAbstraction
153+ {
154+ public:
155+ explicit ButtonAbstraction (OsImplemetation *implemetation) : WidgetAbstraction{implemetation} {}
156+ std::string clickOn () const override
157+ {
158+ return this ->_implementation ->clickOnImplement () + " Click on: Button\n " ;
159+ }
160+ };
161+
162+ class LabelAbstraction : public WidgetAbstraction
163+ {
164+ public:
165+ explicit LabelAbstraction (OsImplemetation *implemetation) : WidgetAbstraction{implemetation} {}
166+ std::string clickOn () const override
167+ {
168+ return this ->_implementation ->clickOnImplement () + " Click on: Label\n " ;
169+ }
170+ };
171+
172+ namespace Client
173+ {
174+ void clientCode (const WidgetAbstraction *widget)
175+ {
176+ if (widget != nullptr )
177+ std::cout << widget->clickOn ();
178+ }
179+ }
180+
181+ void run ()
182+ {
183+ // TODO: check memory leak here
184+ OsImplemetation *os = new WindowsImplemetation ();
185+ WidgetAbstraction *widget = new ButtonAbstraction (os);
186+ Client::clientCode (widget);
187+
188+ os = new LinuxImplemetation ();
189+ widget = new LabelAbstraction (os);
190+ Client::clientCode (widget);
191+
192+ delete os;
193+ delete widget;
194+ }
195+ }
196+
197+ struct BridgeAutoruner
198+ {
199+ BridgeAutoruner ()
200+ {
201+ std::cout << " \n --- Bridge Pattern Example ---\n " ;
202+ Problem::run ();
203+ BridgePattern::run ();
204+ }
205+ };
206+
207+ static BridgeAutoruner instance;
0 commit comments