1
2
3
4
5
6 using System;
7 using System.Collections;
8
9 namespace System.Windows
10 {
11 public abstract class ContainerControl : Control
12 {
13 public ContainerControl(const string& windowClassName, WindowClassStyle windowClassStyle, WindowStyle style, ExtendedWindowStyle exStyle,
14 const Color& backgroundColor, const string& text, const Point& location, const Size& size, Dock dock, Anchors anchors) :
15 base(windowClassName, windowClassStyle, style, exStyle, backgroundColor, text, location, size, dock, anchors), children(this)
16 {
17 }
18 public ContainerControl(ControlCreateParams& createParams) : base(createParams), children(this)
19 {
20 }
21 public void AddChild(Control* child)
22 {
23 children.AddChild(child);
24 ControlEventArgs args(child);
25 OnControlAdded(args);
26 }
27 public UniquePtr<Control> RemoveChild(Control* child)
28 {
29 UniquePtr<Component> childComponent = children.RemoveChild(child);
30 ControlEventArgs args(child);
31 OnControlRemoved(args);
32 return UniquePtr<Control>(childComponent.Release() as Control*);
33 }
34 public void InsertChildBefore(Control* child, Control* before)
35 {
36 children.InsertBefore(child, before);
37 ControlEventArgs args(child);
38 OnControlAdded(args);
39 }
40 public void InsertChildAfter(Control* child, Control* after)
41 {
42 children.InsertAfter(child, after);
43 ControlEventArgs args(child);
44 OnControlAdded(args);
45 }
46 public nothrow const Container& Children() const
47 {
48 return children;
49 }
50 public override nothrow ContainerControl* GetContainerControl() const
51 {
52 return this;
53 }
54 internal override nothrow Control* GetFirstEnabledTabStopControl() const
55 {
56 Component* child = children.FirstChild();
57 while (child != null)
58 {
59 if (child is Control*)
60 {
61 Control* control = cast<Control*>(child);
62 Control* tabStopChild = control->GetFirstEnabledTabStopControl();
63 if (tabStopChild != null)
64 {
65 return tabStopChild;
66 }
67 }
68 child = child->NextSibling();
69 }
70 return null;
71 }
72 internal override nothrow Control* GetLastEnabledTabStopControl() const
73 {
74 Component* child = children.LastChild();
75 while (child != null)
76 {
77 if (child is Control*)
78 {
79 Control* control = cast<Control*>(child);
80 Control* tabStopChild = control->GetLastEnabledTabStopControl();
81 if (tabStopChild != null)
82 {
83 return tabStopChild;
84 }
85 }
86 child = child->PrevSibling();
87 }
88 return null;
89 }
90 protected override void OnSizeChanging(SizeChangingEventArgs& args)
91 {
92 base->OnSizeChanging(args);
93 int dx = args.newSize.w - args.oldSize.w;
94 int dy = args.newSize.h - args.oldSize.h;
95 MoveChildren(dx, dy);
96 }
97 protected override void OnChildSizeChanged(ControlEventArgs& args)
98 {
99 base->OnChildSizeChanged(args);
100 Control* parentControl = ParentControl();
101 if (parentControl != null)
102 {
103 parentControl->FireChildSizeChanged(args);
104 }
105 }
106 protected override void OnChildContentLocationChanged(ControlEventArgs& args)
107 {
108 base->OnChildContentLocationChanged(args);
109 Control* parentControl = ParentControl();
110 if (parentControl != null)
111 {
112 parentControl->OnChildContentLocationChanged(args);
113 }
114 }
115 protected override void OnChildContentChanged(ControlEventArgs& args)
116 {
117 base->OnChildContentChanged(args);
118 Control* parentControl = ParentControl();
119 if (parentControl != null)
120 {
121 parentControl->OnChildContentChanged(args);
122 }
123 }
124 protected override void OnChildContentSizeChanged(ControlEventArgs& args)
125 {
126 base->OnChildContentSizeChanged(args);
127 Control* parentControl = ParentControl();
128 if (parentControl != null)
129 {
130 parentControl->OnChildContentSizeChanged(args);
131 }
132 }
133 protected override void OnChildGotFocus(ControlEventArgs& args)
134 {
135 base->OnChildContentChanged(args);
136 Control* parentControl = ParentControl();
137 if (parentControl != null)
138 {
139 parentControl->OnChildContentChanged(args);
140 }
141 }
142 protected override void OnChildLostFocus(ControlEventArgs& args)
143 {
144 base->OnChildLostFocus(args);
145 Control* parentControl = ParentControl();
146 if (parentControl != null)
147 {
148 parentControl->OnChildContentChanged(args);
149 }
150 }
151 public override void PrintWindowTree(int level)
152 {
153 LogView* log = Application.GetLogView();
154 if (log != null)
155 {
156 log->WriteLine(string(' ', level) + "ContainerControl." + Text() + ".handle=" + ToHexString(cast<ulong>(Handle())) + " " + ParentText() + "[" + Rect(Point(), GetSize()).ToString() + "]");
157 }
158 Component* child = children.FirstChild();
159 while (child != null)
160 {
161 if (child is Control*)
162 {
163 Control* childControl = cast<Control*>(child);
164 childControl->PrintWindowTree(level + 1);
165 }
166 child = child->NextSibling();
167 }
168 }
169 protected override bool ProcessMessage(Message& message)
170 {
171 switch (message.msg)
172 {
173 case WM_SIZE:
174 {
175 Size newSize = message.LParamSize();
176 Size oldSize = GetSize();
177 if (newSize != oldSize)
178 {
179 Rect parentRect(Point(), newSize);
180 int dx = newSize.w - oldSize.w;
181 int dy = newSize.h - oldSize.h;
182 MoveChildren(dx, dy);
183 uint windowState = message.wparam;
184 SetSizeInternal(newSize, windowState);
185 DockChildren();
186 OnSizeChanged(windowState);
187 }
188 message.result = 0;
189 return true;
190 }
191 case WM_PAINT: case WM_MOVE: case WM_MOUSEMOVE: case WM_MOUSELEAVE: case WM_LBUTTONDOWN: case WM_LBUTTONUP: case WM_LBUTTONDBLCLK: case WM_RBUTTONDOWN: case WM_RBUTTONUP:
192 case WM_CHAR: case WM_KEYDOWN: case WM_KEYUP: case WM_SYSCOMMAND: case WM_HSCROLL: case WM_VSCROLL: case WM_MOUSEWHEEL:
193 case WM_SETFOCUS: case WM_KILLFOCUS: case WM_TIMER: case WM_COMMAND: case WM_SHOWWINDOW: case WM_CLIPBOARDUPDATE:
194 {
195 return base->ProcessMessage(message);
196 }
197 }
198 return false;
199 }
200 public void MoveChildren(int dx, int dy)
201 {
202 Component* child = children.FirstChild();
203 while (child != null)
204 {
205 if (child is Control*)
206 {
207 Control* childControl = cast<Control*>(child);
208 if (childControl->GetDock() == Dock.none)
209 {
210 childControl->MoveWindow(dx, dy);
211 }
212 }
213 child = child->NextSibling();
214 }
215 }
216 public void DockChildren()
217 {
218 Rect parentRect(Point(), GetSize());
219 DockChildren(parentRect);
220 }
221 public void DockChildren(Rect& parentRect)
222 {
223 List<Control*> filledControls;
224 List<ContainerControl*> containers;
225 Component* child = children.FirstChild();
226 while (child != null)
227 {
228 if (child is Control*)
229 {
230 Control* childControl = cast<Control*>(child);
231 switch (childControl->GetDock())
232 {
233 case Dock.none: break;
234 case Dock.fill: filledControls.Add(childControl); break;
235 default:
236 {
237 childControl->DockWindow(parentRect);
238 break;
239 }
240 }
241 if (childControl is ContainerControl*)
242 {
243 ContainerControl* containerChild = cast<ContainerControl*>(childControl);
244 containers.Add(containerChild);
245 }
246 }
247 child = child->NextSibling();
248 }
249 for (Control* filledControl : filledControls)
250 {
251 filledControl->DockWindow(parentRect);
252 }
253 for (ContainerControl* container : containers)
254 {
255 container->DockChildren();
256 }
257 }
258 internal override void PaintAll(PaintEventArgs& args, bool skipMenuBar)
259 {
260 try
261 {
262 base->PaintAll(args, skipMenuBar);
263 Control* topControl = TopControl();
264 Component* child = children.FirstChild();
265 while (child != null)
266 {
267 if (child is Control*)
268 {
269 Control* childControl = cast<Control*>(child);
270 if (childControl != topControl)
271 {
272 bool skip = false;
273 if (skipMenuBar)
274 {
275 if (childControl is MenuBar*)
276 {
277 skip = true;
278 }
279 else if (childControl is MenuBox*)
280 {
281 MenuBox* menuBox = cast<MenuBox*>(childControl);
282 if (!menuBox->PaintThisMenuBox())
283 {
284 skip = true;
285 }
286 }
287 }
288 if (!skip)
289 {
290 GraphicsState state = args.graphics.SaveChecked();
291 Point loc = childControl->Location();
292 args.graphics.SetClipChecked(Rect(childControl->Location(), childControl->GetSize()));
293 args.graphics.TranslateTransformChecked(loc.x, loc.y);
294 childControl->PaintAll(args, skipMenuBar);
295 args.graphics.RestoreChecked(state);
296 }
297 }
298 }
299 child = child->NextSibling();
300 }
301 if (topControl != null)
302 {
303 GraphicsState state = args.graphics.SaveChecked();
304 Point loc = topControl->Location();
305 args.graphics.SetClipChecked(Rect(topControl->Location(), topControl->GetSize()));
306 args.graphics.TranslateTransformChecked(loc.x, loc.y);
307 topControl->PaintAll(args, skipMenuBar);
308 args.graphics.RestoreChecked(state);
309 }
310 }
311 catch (const Exception& ex)
312 {
313 MessageBox.Show(ex.Message());
314 }
315 }
316 private Container children;
317 }
318 }