2
* Copyright (c) 2008, 2012, Oracle and/or its affiliates. All rights reserved.
4
* This program is free software; you can redistribute it and/or
5
* modify it under the terms of the GNU General Public License as
6
* published by the Free Software Foundation; version 2 of the
9
* This program is distributed in the hope that it will be useful,
10
* but WITHOUT ANY WARRANTY; without even the implied warranty of
11
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
* GNU General Public License for more details.
14
* You should have received a copy of the GNU General Public License
15
* along with this program; if not, write to the Free Software
16
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
23
using namespace Windows::Forms;
24
using namespace System::Drawing;
26
using namespace MySQL;
27
using namespace MySQL::Forms;
28
using namespace MySQL::Utilities;
29
using namespace MySQL::Controls;
31
using namespace Aga::Controls::Tree;
32
using namespace ScintillaNet;
34
DEFAULT_LOG_DOMAIN(DOMAIN_MFORMS_WRAPPER)
36
//----------------- ViewImpl ----------------------------------------------------------------------
38
ViewImpl::ViewImpl(::mforms::View *view)
44
//--------------------------------------------------------------------------------------------------
51
//--------------------------------------------------------------------------------------------------
54
* Determines, depending on the type of the given control, if the layout process should use the control's
55
* minimum or its preferred size.
56
* This is necessary because there is a discrepancy between what is considered the minimum size for layouting
57
* and the same size for Windows controls. The latter is usually just 0. Instead the preferred size comes close
58
* to what we need in the layouting process. Unfortunately, some controls just return their current size
59
* (even if they are empty) or the size they need to fit their full text (text box).
61
bool ViewImpl::use_min_width_for_layout(Control^ control)
63
TextBox^ text= dynamic_cast<TextBox^>(control);
64
bool needsMinWidth= (text != nullptr) && (text->Multiline);
67
System::Type^ type = control->GetType();
68
needsMinWidth= (type == TabControl::typeid) || (type == Panel::typeid) || (type == ComboBox::typeid)
69
|| (type == TreeViewAdv::typeid) || (type == ListBox::typeid) || (type == TextBox::typeid)
70
|| (type == SplitContainer::typeid) || (type == Scintilla::typeid)
72
// TODO: investigate if we can remove this and override GetPreferredSize in FlatTabControl instead.
73
|| (type == FlatTabControl::typeid);
79
//--------------------------------------------------------------------------------------------------
81
bool ViewImpl::use_min_height_for_layout(Control^ control)
83
TextBox^ text= dynamic_cast<TextBox^>(control);
84
bool needsMinHeight= (text != nullptr) && (text->Multiline);
87
System::Type^ type = control->GetType();
88
needsMinHeight= (type == TabControl::typeid) || (type == Panel::typeid) || (type == ListBox::typeid)
89
|| (type == TreeViewAdv::typeid) || (type == SplitContainer::typeid) || (type == Scintilla::typeid)
91
// TODO: investigate if we can remove this and override GetPreferredSize in FlatTabControl instead.
92
|| (type == FlatTabControl::typeid);
95
return needsMinHeight;
98
//--------------------------------------------------------------------------------------------------
101
* Removes the given mode from the auto resize settings of the given control.
103
void ViewImpl::remove_auto_resize(Control^ control, mforms::AutoResizeMode mode)
105
// Get backend object for the control, which allows to set individual auto resize modes.
106
mforms::View* view= ViewImpl::get_backend_control<mforms::View>(control);
109
case mforms::ResizeBoth:
110
view->set_resize_mode(mforms::ResizeNone);
112
case mforms::ResizeHorizontal:
113
if (view->get_resize_mode() == mforms::ResizeBoth)
114
view->set_resize_mode(mforms::ResizeVertical);
116
view->set_resize_mode(mforms::ResizeNone);
118
case mforms::ResizeVertical:
119
if (view->get_resize_mode() == mforms::ResizeBoth)
120
view->set_resize_mode(mforms::ResizeHorizontal);
122
view->set_resize_mode(mforms::ResizeNone);
127
//-------------------------------------------------------------------------------------------------
130
* Returns the current resize mode set for the associated back end object of control.
132
mforms::AutoResizeMode ViewImpl::get_auto_resize(Control^ control)
134
mforms::View* view= ViewImpl::get_backend_control<mforms::View>(control);
135
return view->get_resize_mode();
138
//-------------------------------------------------------------------------------------------------
141
* Determines if the given control can be resized in horizontal direction.
143
bool ViewImpl::can_auto_resize_horizontally(Control^ control)
145
mforms::View* view= ViewImpl::get_backend_control<mforms::View>(control);
146
mforms::AutoResizeMode mode= view->get_resize_mode();
148
return (mode == mforms::ResizeHorizontal) || (mode == mforms::ResizeBoth);
151
//-------------------------------------------------------------------------------------------------
154
* Determines if the given control can be resized in vertical direction.
156
bool ViewImpl::can_auto_resize_vertically(Control^ control)
158
mforms::View* view= ViewImpl::get_backend_control<mforms::View>(control);
159
mforms::AutoResizeMode mode= view->get_resize_mode();
161
return (mode == mforms::ResizeVertical) || (mode == mforms::ResizeBoth);
164
//-------------------------------------------------------------------------------------------------
167
* Enables resizing of the control in both directions.
169
void ViewImpl::set_full_auto_resize(Control^ control)
171
ViewImpl::get_backend_control<mforms::View>(control)->set_resize_mode(mforms::ResizeBoth);
174
//-------------------------------------------------------------------------------------------------
177
* Sets resize mode whatever the caller specified.
179
void ViewImpl::set_auto_resize(Control^ control, mforms::AutoResizeMode mode)
181
ViewImpl::get_backend_control<mforms::View>(control)->set_resize_mode(mode);
184
//-------------------------------------------------------------------------------------------------
186
bool ViewImpl::is_layout_dirty(Control^ control)
188
mforms::View* view= ViewImpl::get_backend_control<mforms::View>(control);
189
return view->is_layout_dirty();
192
//-------------------------------------------------------------------------------------------------
194
void ViewImpl::set_layout_dirty(Control^ control, bool value)
196
mforms::View* view= ViewImpl::get_backend_control<mforms::View>(control);
197
view->set_layout_dirty(value);
200
//-------------------------------------------------------------------------------------------------
202
void ViewImpl::destroy(::mforms::View *self)
204
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
208
//--------------------------------------------------------------------------------------------------
210
void ViewImpl::show(::mforms::View *self, bool show)
212
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
216
Control^ control= view->get_control<Control>();
217
control->Visible= show;
219
// Unfortunately, we cannot optimize handling here. Control::Visible not only returns the
220
// visibility of itself but its entire view hierarchy. So we cannot distinct between the two
221
// cases if the control itself is hidden or one of its parents. Setting Control::Visible
222
// does the right job, though.
223
//if (control->Visible != show)
224
if (control->IsHandleCreated && self->get_parent() != NULL)
225
self->get_parent()->set_layout_dirty(true);
229
//-------------------------------------------------------------------------------------------------
231
int ViewImpl::get_width(::mforms::View *self)
233
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
235
return view->get_control<Control>()->Width;
239
//-------------------------------------------------------------------------------------------------
241
int ViewImpl::get_height(::mforms::View *self)
243
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
245
return view->get_control<Control>()->Height;
249
//-------------------------------------------------------------------------------------------------
251
int ViewImpl::get_preferred_width(::mforms::View *self)
253
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
256
return view->get_control<Control>()->PreferredSize.Width;
261
//-------------------------------------------------------------------------------------------------
263
int ViewImpl::get_preferred_height(::mforms::View *self)
265
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
268
return view->get_control<Control>()->PreferredSize.Height;
273
//-------------------------------------------------------------------------------------------------
275
int ViewImpl::get_x(::mforms::View *self)
277
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
280
return view->get_control<Control>()->Left;
285
//-------------------------------------------------------------------------------------------------
287
int ViewImpl::get_y(::mforms::View *self)
289
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
292
return view->get_control<Control>()->Top;
297
//-------------------------------------------------------------------------------------------------
299
void ViewImpl::set_size(::mforms::View *self, int w, int h)
301
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
303
view->set_size(w, h);
306
//-------------------------------------------------------------------------------------------------
308
void ViewImpl::set_padding(::mforms::View *self, int left, int top, int right, int bottom)
310
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
313
self->set_layout_dirty(true);
314
view->set_padding(left, top, right, bottom);
318
//-------------------------------------------------------------------------------------------------
320
void ViewImpl::set_position(::mforms::View *self, int x, int y)
322
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
325
if (self->get_parent() != NULL)
326
self->get_parent()->set_layout_dirty(true);
327
view->set_position(x, y);
331
//-------------------------------------------------------------------------------------------------
333
void ViewImpl::client_to_screen(::mforms::View *self, int& x, int& y)
335
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
338
System::Drawing::Point location= System::Drawing::Point(x, y);
339
location= view->get_control<Control>()->PointToScreen(location);
345
//-------------------------------------------------------------------------------------------------
347
ViewImpl^ ViewImpl::get_parent()
349
mforms::View* view= get_backend_control<mforms::View>(get_control<Control>());
350
if (view != NULL && view->get_parent() != NULL)
351
return (ViewImpl^) ObjectImpl::FromUnmanaged(view->get_parent());
356
//-------------------------------------------------------------------------------------------------
358
void ViewImpl::relayout()
360
Control^ control= get_control<Control>();
361
if (control->InvokeRequired)
362
control->BeginInvoke(gcnew MethodInvoker(this, &ViewImpl::relayout));
364
control->PerformLayout();
367
//-------------------------------------------------------------------------------------------------
369
void ViewImpl::set_enabled(::mforms::View *self, bool flag)
371
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
373
view->get_control<Control>()->Enabled= flag;
376
//-------------------------------------------------------------------------------------------------
378
bool ViewImpl::is_enabled(::mforms::View *self)
380
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
382
return view->get_control<Control>()->Enabled;
386
//-------------------------------------------------------------------------------------------------
388
View *ViewImpl::find_subview(::mforms::View *self, std::string &name)
393
//-------------------------------------------------------------------------------------------------
395
void ViewImpl::set_name(::mforms::View *self, const std::string& text)
397
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
399
view->get_control<Control>()->Name = CppStringToNative(text);
402
//-------------------------------------------------------------------------------------------------
404
void ViewImpl::relayout(::mforms::View *self)
406
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
411
//-------------------------------------------------------------------------------------------------
413
void ViewImpl::set_needs_repaint(::mforms::View *self)
415
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
417
view->get_control<Control>()->Refresh();
420
//-------------------------------------------------------------------------------------------------
422
void ViewImpl::suspend_layout(::mforms::View *self, bool flag)
424
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
428
view->get_control<Control>()->SuspendLayout();
431
view->get_control<Control>()->ResumeLayout();
432
if (self->is_layout_dirty())
433
view->get_control<Control>()->PerformLayout();
438
//-------------------------------------------------------------------------------------------------
440
void ViewImpl::set_front_color(mforms::View *self, const std::string &color)
442
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
444
view->set_front_color(CppStringToNative(color));
447
//-------------------------------------------------------------------------------------------------
449
std::string ViewImpl::get_front_color(mforms::View *self)
451
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
453
return NativeToCppString(view->get_front_color());
457
//-------------------------------------------------------------------------------------------------
459
void ViewImpl::set_back_color(mforms::View *self, const std::string &color)
461
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
463
view->set_back_color(CppStringToNative(color));
466
//-------------------------------------------------------------------------------------------------
468
std::string ViewImpl::get_back_color(mforms::View *self)
470
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
472
return NativeToCppString(view->get_back_color());
476
//-------------------------------------------------------------------------------------------------
478
void ViewImpl::set_back_image(mforms::View *self, const std::string &path, mforms::ImageLayout layout)
480
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
482
view->set_back_image(CppStringToNative(path), layout);
486
//-------------------------------------------------------------------------------------------------
488
void ViewImpl::set_tooltip(::mforms::View *self, const std::string& text)
490
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
492
view->set_tooltip(text);
495
//-------------------------------------------------------------------------------------------------
497
void ViewImpl::set_font(::mforms::View *self, const std::string& fontDescription)
499
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
501
view->set_font(fontDescription);
504
//-------------------------------------------------------------------------------------------------
506
bool ViewImpl::is_shown(::mforms::View *self)
508
ViewImpl^ view= (ViewImpl^)ObjectImpl::FromUnmanaged(self);
510
return view->get_control<Control>()->Visible;
514
//-------------------------------------------------------------------------------------------------
516
void ViewImpl::set_size(int width, int height)
518
Control^ control= get_control<Control>();
519
Size newSize= control->Size;
521
newSize.Width= width;
523
newSize.Height= height;
525
control->MinimumSize = newSize; // TODO: wrong place for this, when we restore loaded settings we don't want to set a min size.
526
// Implement an own set_min_size function.
527
control->Size = newSize;
530
//-------------------------------------------------------------------------------------------------
532
void ViewImpl::set_padding(int left, int top, int right, int bottom)
534
Control^ control= get_control<Control>();
535
control->Padding = Windows::Forms::Padding(left, top, right, bottom);
538
//-------------------------------------------------------------------------------------------------
540
void ViewImpl::set_position(int x, int y)
542
get_control<Control>()->Location = Point(x, y);
545
//-------------------------------------------------------------------------------------------------
547
void ViewImpl::set_tooltip(const std::string& text)
549
if (tooltip == nullptr)
551
tooltip= gcnew ToolTip();
552
tooltip->AutoPopDelay = 10000; // 10 sec. show time
553
tooltip->InitialDelay = 500; // 500 ms before showing the tooltip if none was visible before.
554
tooltip->ReshowDelay = 250; // 250 ms before showing the tooltip if another one was active.
555
tooltip->ShowAlways = true; // Show tooltip even if the control is not active.
557
tooltip->SetToolTip(get_control<Control>(), CppStringToNative(text));
560
//-------------------------------------------------------------------------------------------------
562
void ViewImpl::set_font(const std::string& fontDescription)
568
base::parse_font_description(fontDescription, font, size, bold, italic);
570
FontStyle style = FontStyle::Regular;
572
style = (FontStyle) (style | FontStyle::Bold);
574
style = (FontStyle) (style | FontStyle::Italic);
578
get_control<Control>()->Font = ControlUtilities::GetFont(CppStringToNativeRaw(font),
579
(float) size, style);
581
catch (System::ArgumentException^ e)
583
// Argument exception pops up when the system cannot find the Regular font style (corrupt font).
584
log_error("ViewImpl::set_font failed. %s\n", e->Message);
588
//-------------------------------------------------------------------------------------------------
590
void ViewImpl::set_front_color(String ^color)
592
get_control<Control>()->ForeColor= System::Drawing::ColorTranslator::FromHtml(color);
595
//-------------------------------------------------------------------------------------------------
597
String^ ViewImpl::get_front_color()
599
return System::Drawing::ColorTranslator::ToHtml(get_control<Control>()->ForeColor);
602
//-------------------------------------------------------------------------------------------------
604
void ViewImpl::set_back_color(String ^color)
606
get_control<Control>()->BackColor= System::Drawing::ColorTranslator::FromHtml(color);
609
//-------------------------------------------------------------------------------------------------
611
String^ ViewImpl::get_back_color()
613
return System::Drawing::ColorTranslator::ToHtml(get_control<Control>()->BackColor);
616
//-------------------------------------------------------------------------------------------------
618
void ViewImpl::set_back_image(String ^path, mforms::ImageLayout layout)
620
Windows::Forms::ImageLayout native_layout;
623
case mforms::LayoutTile:
624
native_layout= Windows::Forms::ImageLayout::Tile;
626
case mforms::LayoutCenter:
627
native_layout= Windows::Forms::ImageLayout::Center;
629
case mforms::LayoutStretch:
630
native_layout= Windows::Forms::ImageLayout::Stretch;
632
case mforms::LayoutZoom:
633
native_layout= Windows::Forms::ImageLayout::Zoom;
636
native_layout= Windows::Forms::ImageLayout::None;
639
// An exception is raised if the image cannot be found.
640
Image^ image= Image::FromFile(path, true);
641
get_control<Control>()->BackgroundImage= image;
642
get_control<Control>()->BackgroundImageLayout= native_layout;
645
//-------------------------------------------------------------------------------------------------
648
* Resizes the given control according to its dock state. Sizes of the control which were not changed
649
* are also reset in the given Size structure to allow for proper child layouting.
651
void ViewImpl::resize_with_docking(Control^ control, System::Drawing::Size& size)
653
// If the control is docked somewhere resizing must be restricted not to destroy the docked
655
// Do not resize if the control has the fill dock style. In that case it must stay as it is.
656
if (control->Dock == DockStyle::Fill)
659
if (control->Dock == DockStyle::Left || control->Dock == DockStyle::Right)
660
size.Height= control->Size.Height;
662
if (control->Dock == DockStyle::Top || control->Dock == DockStyle::Bottom)
663
size.Width= control->Size.Width;
666
set_layout_dirty(control, true);
669
//-------------------------------------------------------------------------------------------------
672
* Removes auto resizing flags if a control is limited in resizing by docking.
674
void ViewImpl::adjust_auto_resize_from_docking(Control^ control)
676
if (control->Dock == DockStyle::Fill)
677
set_auto_resize(control, mforms::ResizeNone);
679
if (control->Dock == DockStyle::Left || control->Dock == DockStyle::Right)
680
remove_auto_resize(control, mforms::ResizeHorizontal);
682
if (control->Dock == DockStyle::Top || control->Dock == DockStyle::Bottom)
683
remove_auto_resize(control, mforms::ResizeVertical);
686
//-------------------------------------------------------------------------------------------------
688
void ViewImpl::flush_events(::mforms::View *)
690
Application::DoEvents();
693
//-------------------------------------------------------------------------------------------------