1 //------------------------------------------------------------------------------
2 // emBorder.h
3 //
4 // Copyright (C) 2005-2010,2014-2016 Oliver Hamann.
5 //
6 // Homepage: http://eaglemode.sourceforge.net/
7 //
8 // This program is free software: you can redistribute it and/or modify it under
9 // the terms of the GNU General Public License version 3 as published by the
10 // Free Software Foundation.
11 //
12 // This program is distributed in the hope that it will be useful, but WITHOUT
13 // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14 // FOR A PARTICULAR PURPOSE. See the GNU General Public License version 3 for
15 // more details.
16 //
17 // You should have received a copy of the GNU General Public License version 3
18 // along with this program. If not, see <http://www.gnu.org/licenses/>.
19 //------------------------------------------------------------------------------
20
21 #ifndef emBorder_h
22 #define emBorder_h
23
24 #ifndef emVarModel_h
25 #include <emCore/emVarModel.h>
26 #endif
27
28 #ifndef emLook_h
29 #include <emCore/emLook.h>
30 #endif
31
32
33 //==============================================================================
34 //================================== emBorder ==================================
35 //==============================================================================
36
37 class emBorder : public emPanel {
38
39 public:
40
41 // This is the base class of all toolkit panels. A panel of this class
42 // can have a border, a label, a how-to text and an auxiliary area. And
43 // it has a content area. The label can consist of a caption, a
44 // description and an icon. The how-to text describes how to use the
45 // type of panel in general, and maybe something about its state. The
46 // auxiliary area is for showing a custom panel with additional things
47 // like a configuration or an extended help text. The label, the how-to
48 // text and the auxiliary area are shown in the border. Alternatively, a
49 // derived class can manage to move the label into the content area.
50
51 emBorder(
52 ParentArg parent, const emString & name,
53 const emString & caption=emString(),
54 const emString & description=emString(),
55 const emImage & icon=emImage()
56 );
57 // Constructor.
58 // Arguments:
59 // parent - Parent for this panel (emPanel or emView).
60 // name - The name for this panel.
61 // caption - The label's caption, or empty.
62 // description - The label's description, or empty.
63 // icon - The label's icon, or empty.
64
65 virtual ~emBorder();
66 // Destructor.
67
68 const emString & GetCaption() const;
69 void SetCaption(const emString & caption);
70 // The caption to be shown in the label.
71
72 const emString & GetDescription() const;
73 void SetDescription(const emString & description);
74 // The description to be shown in the label.
75
76 const emImage & GetIcon() const;
77 void SetIcon(const emImage & icon);
78 // The icon to be shown in the label.
79
80 void SetLabel(
81 const emString & caption=emString(),
82 const emString & description=emString(),
83 const emImage & icon=emImage()
84 );
85 // Set all three things which are making up the label.
86
87 emAlignment GetLabelAlignment() const;
88 void SetLabelAlignment(emAlignment labelAlignment);
89 // Alignment of the label as a whole within its available space.
90
91 emAlignment GetCaptionAlignment() const;
92 void SetCaptionAlignment(emAlignment captionAlignment);
93 // Horizontal alignment of lines within the caption text of the
94 // label. The top and bottom flags are ignored.
95
96 emAlignment GetDescriptionAlignment() const;
97 void SetDescriptionAlignment(emAlignment descriptionAlignment);
98 // Horizontal alignment of lines within the description text of
99 // the label. The top and bottom flags are ignored.
100
101 bool IsIconAboveCaption() const;
102 void SetIconAboveCaption(bool iconAboveCaption=true);
103 // Whether the icon is shown above the caption (true), or if it
104 // is shown to the left of the caption (false, the default).
105
106 double GetMaxIconAreaTallness() const;
107 void SetMaxIconAreaTallness(double maxIconAreaTallness);
108 // Maximum tallness (height/width ratio) of the area in the
109 // label preserved for the icon (if the label has an icon). The
110 // default is 1.0. If you have a group of elements (e.g.
111 // buttons) which show icons and captions, and if the icon
112 // images have different tallnesses, then it is a good idea to
113 // set this parameter to the minimum(!) tallness of all the icon
114 // images. Thereby, the icons and captions of all the elements
115 // will be aligned pretty equal.
116
117 enum OuterBorderType {
118 // Possibles types for the outer border line. This even
119 // specifies whether the background of the panel should be
120 // filled or not.
121 OBT_NONE,
122 // Do not have an outer border line, do not have a
123 // margin and do not fill the background.
124 OBT_FILLED,
125 // Like OBT_NONE, but fill the whole background with
126 // background color.
127 OBT_MARGIN,
128 // Like OBT_NONE, but have a small margin (for example,
129 // this is used by emLabel and emCheckBox). Larger
130 // margins should be solved through the parent panel,
131 // e.g. see emLinearLayout::SetSpace.
132 OBT_MARGIN_FILLED,
133 // Like OBT_MARGIN, but fill the whole background.
134 OBT_RECT,
135 // Have a rectangular outer border line and fill the
136 // rectangle with background color. Have a small margin.
137 OBT_ROUND_RECT,
138 // Like OBT_RECT but with round corners.
139 OBT_GROUP,
140 // Have a small special outer border for groups (used by
141 // group panels like emLinearGroup and so on).
142 OBT_INSTRUMENT,
143 // Like OBT_GROUP, but the border line is thicker (for
144 // example, this is used by emTextField).
145 OBT_INSTRUMENT_MORE_ROUND,
146 // Like OBT_INSTRUMENT, but with a larger corner radius
147 // (this is used by emButton).
148 OBT_POPUP_ROOT
149 // Have a special border for root panels of views which
150 // have the VF_POPUP_ZOOM flag set (should not be used
151 // for something else).
152 };
153
154 enum InnerBorderType {
155 // Possibles types for the inner border line.
156 IBT_NONE,
157 // Do not have an inner border line.
158 IBT_GROUP,
159 // Have a special round inner border line for groups.
160 IBT_INPUT_FIELD,
161 // Have a special round inner border and background for
162 // editable fields.
163 IBT_OUTPUT_FIELD,
164 // Have a special round inner border and background for
165 // non-editable fields.
166 IBT_CUSTOM_RECT
167 // Have a special rectangular inner border for custom
168 // stuff. Herewith, the content rectangle never has
169 // round corners.
170 };
171
172 OuterBorderType GetOuterBorderType() const;
173 InnerBorderType GetInnerBorderType() const;
174 void SetOuterBorderType(OuterBorderType obt);
175 void SetInnerBorderType(InnerBorderType ibt);
176 void SetBorderType(OuterBorderType obt, InnerBorderType ibt);
177 // Outer and inner border types. The default is OBT_NONE and
178 // IBT_NONE.
179
180 double GetBorderScaling() const;
181 void SetBorderScaling(double borderScaling);
182 // Scale factor for the size of the border. The default is 1.0.
183
184 const emLook & GetLook() const;
185 virtual void SetLook(const emLook & look, bool recursively=false);
186 // Look of this toolkit panel. At construction of a panel, the
187 // look is copied from the parent panel (if the parent is not
188 // emBorder, the grand parent is asked, and so on). When
189 // setting the look with the argument recursively=true, all
190 // descendant panels of class emBorder are even set through
191 // calling emLook::Apply for every child panel.
192
193 void HaveAux(const emString & panelName, double tallness);
194 // Make this border having a rectangular area for auxiliary
195 // stuff. It could be a user interface for configuring this
196 // panel, or an extended function, or some additional help or
197 // what ever you want. Either you could show the things through
198 // a child panel or through custom painting, but doing it with a
199 // child panel is easier. Whenever you create that panel. It is
200 // laid out automatically into the auxiliary area.
201 // Arguments:
202 // panelName - Name of the child panel to be laid out in the
203 // auxiliary area.
204 // tallness - Height/width ratio of the auxiliary area.
205
206 void RemoveAux();
207 // Inversion of HaveAux (does not delete the auxiliary panel).
208
209 bool HasAux() const;
210 // Whether this border has an area for auxiliary stuff.
211
212 const emString & GetAuxPanelName() const;
213 double GetAuxTallness() const;
214 // Properties of the auxiliary area set with HaveAux. Valid only
215 // if HasAux()==true.
216
217 emPanel * GetAuxPanel();
218 // Returns the auxiliary child panel, or NULL if not present.
219
220 void GetAuxRect(
221 double * pX, double * pY, double * pW, double * pH,
222 emColor * pCanvasColor=NULL
223 ) const;
224 // Get the coordinates and canvas color of the auxiliary area.
225 // Valid only if HasAux()==true.
226
227 virtual void GetSubstanceRect(double * pX, double * pY,
228 double * pW, double * pH,
229 double * pR) const;
230 // Overloaded from emPanel (read there).
231
232 virtual void GetContentRoundRect(
233 double * pX, double * pY, double * pW, double * pH, double * pR,
234 emColor * pCanvasColor=NULL
235 ) const;
236 // Get the coordinates and canvas color of the content area as a
237 // round rectangle (argument pR is for returning the radius of
238 // the corners).
239
240 virtual void GetContentRect(
241 double * pX, double * pY, double * pW, double * pH,
242 emColor * pCanvasColor=NULL
243 ) const;
244 // Get the coordinates and canvas color of the content area as a
245 // rectangle. If the inner border has round corners, the
246 // rectangle returned here is smaller than with
247 // GetContentRoundRect, so that it fits completely into the
248 // content area.
249
250 virtual void GetContentRectUnobscured(
251 double * pX, double * pY, double * pW, double * pH,
252 emColor * pCanvasColor=NULL
253 ) const;
254 // Get the coordinates and canvas color of the unobscured part
255 // of the content area. Some border types are painting an
256 // overlay like a shadow at the edges of the content area, after
257 // PaintContent is called. This does not work for child panels,
258 // because they are painted after the overlay. Therefore child
259 // panels should be laid out in the rectangle returned by
260 // GetContentRectUnobscured. It returns the inner part, which is
261 // not painted over.
262
263 protected:
264
265 virtual void Notice(NoticeFlags flags);
266 virtual bool IsOpaque() const;
267 virtual void Paint(const emPainter & painter, emColor canvasColor) const;
268 virtual void LayoutChildren();
269 // See emPanel. Hint: For painting the content area, please
270 // overload PaintContent instead of Paint, because with certain
271 // border types, a shadow is painted over the content area.
272
273 virtual bool HasHowTo() const;
274 virtual emString GetHowTo() const;
275 // This is about a text describing how to use this panel. If
276 // HasHowTo()==true, the text returned by GetHowTo() is shown
277 // very small in the center of the left edge of the border. When
278 // overloading GetHowTo(), please do not forget to call the
279 // original version and to include that text at the beginning.
280 // The default implementation of GetHowTo() returns a preface,
281 // and optionally a description of the disable state (if
282 // disabled) and optionally a description of the keyboard focus
283 // (if focusable). The default implementation of HasHowTo()
284 // return false, because the default text alone is not so
285 // helpful, and because the text would disturb some panel types.
286
287 virtual void PaintContent(
288 const emPainter & painter, double x, double y, double w,
289 double h, emColor canvasColor
290 ) const;
291 // This can be overloaded for painting the content area. The
292 // default implementation does nothing. The coordinates x,y,w,h
293 // are like from GetContentRect, but you could even use the
294 // coordinates returned by GetContentRoundRect.
295
296 virtual bool HasLabel() const;
297 // Whether this panel has a label. The default implementation
298 // checks whether at least one of caption, description and icon
299 // is not empty.
300
301 virtual double GetBestLabelTallness() const;
302 // Get the ideal tallness for the label area. The default
303 // implementation calculates this for the default implementation
304 // of PaintLabel.
305
306 virtual void PaintLabel(
307 const emPainter & painter, double x, double y, double w,
308 double h, emColor color, emColor canvasColor
309 ) const;
310 // Paint the label. The default implementation paints the
311 // caption, description and icon. This could be overloaded to
312 // paint something else for the label.
313
314 bool IsLabelInBorder() const;
315 void SetLabelInBorder(bool labelInBorder);
316 // Whether to show the label as part of the border. The default
317 // is true. If a derived class wants to have the label as part
318 // of the content, it should set false here and call PaintLabel
319 // itself.
320
321 struct TkResources {
322 TkResources();
323 ~TkResources();
324 emImage ImgButton;
325 emImage ImgButtonBorder;
326 emImage ImgButtonChecked;
327 emImage ImgButtonPressed;
328 emImage ImgCheckBox;
329 emImage ImgCheckBoxPressed;
330 emImage ImgCustomRectBorder;
331 emImage ImgDir;
332 emImage ImgDirUp;
333 emImage ImgGroupBorder;
334 emImage ImgGroupInnerBorder;
335 emImage ImgIOField;
336 emImage ImgPopupBorder;
337 emImage ImgRadioBox;
338 emImage ImgRadioBoxPressed;
339 emImage ImgSplitter;
340 emImage ImgSplitterPressed;
341 emImage ImgTunnel;
342 };
343 const TkResources & GetTkResources() const;
344 // Shared resources used by the toolkit panel implementations.
345 // This is more or less private stuff - do not use in custom
346 // classes.
347
348 // - - - - - - - - - - Depreciated methods - - - - - - - - - - - - - - -
349 // The following virtual non-const methods have been replaced by const
350 // methods (see above). The old versions still exist here with the
351 // "final" keyword added, so that old overridings will fail to compile.
352 // If you run into this, please adapt your overridings by adding "const".
353 public:
354 virtual void GetContentRoundRect(
355 double * pX, double * pY, double * pW, double * pH, double * pR,
356 emColor * pCanvasColor=NULL
357 ) final;
358 virtual void GetContentRect(
359 double * pX, double * pY, double * pW, double * pH,
360 emColor * pCanvasColor=NULL
361 ) final;
362 virtual void GetContentRectUnobscured(
363 double * pX, double * pY, double * pW, double * pH,
364 emColor * pCanvasColor=NULL
365 ) final;
366 protected:
367 virtual bool HasHowTo() final;
368 virtual emString GetHowTo() final;
369 virtual void PaintContent(
370 const emPainter & painter, double x, double y, double w,
371 double h, emColor canvasColor
372 ) final;
373 virtual bool HasLabel() final;
374 virtual double GetBestLabelTallness() final;
375 virtual void PaintLabel(
376 const emPainter & painter, double x, double y, double w,
377 double h, emColor color, emColor canvasColor
378 ) final;
379 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
380
381 private:
382
383 enum DoBorderFunc {
384 BORDER_FUNC_PAINT,
385 BORDER_FUNC_SUBSTANCE_ROUND_RECT,
386 BORDER_FUNC_CONTENT_ROUND_RECT,
387 BORDER_FUNC_CONTENT_RECT,
388 BORDER_FUNC_CONTENT_RECT_UNOBSCURED,
389 BORDER_FUNC_AUX_RECT
390 };
391 void DoBorder(
392 DoBorderFunc func, const emPainter * painter,
393 emColor canvasColor, double * pX, double * pY, double * pW,
394 double * pH, double * pR, emColor * pCanvasColor
395 ) const;
396
397 enum DoLabelFunc {
398 LABEL_FUNC_PAINT,
399 LABEL_FUNC_GET_BEST_TALLNESS
400 };
401 void DoLabel(
402 DoLabelFunc func, const emPainter * painter, double x, double y,
403 double w, double h, emColor color, emColor canvasColor,
404 double * pBestTallness
405 ) const;
406
407 struct AuxData {
408 emString PanelName;
409 double Tallness;
410 emCrossPtr<emPanel> PanelPointerCache;
411 };
412
413 emRef<emVarModel<TkResources> > TkResVarModel;
414 emString Caption;
415 emString Description;
416 emImage Icon;
417 AuxData * Aux;
418 emLook Look;
419 double MaxIconAreaTallness;
420 double BorderScaling;
421 emAlignment LabelAlignment;
422 emAlignment CaptionAlignment;
423 emAlignment DescriptionAlignment;
424 emByte OuterBorder;
425 emByte InnerBorder;
426 bool IconAboveCaption;
427 bool LabelInBorder;
428
429 static const char * HowToPreface;
430 static const char * HowToDisabled;
431 static const char * HowToFocus;
432 };
433
GetCaption()434 inline const emString & emBorder::GetCaption() const
435 {
436 return Caption;
437 }
438
GetDescription()439 inline const emString & emBorder::GetDescription() const
440 {
441 return Description;
442 }
443
GetIcon()444 inline const emImage & emBorder::GetIcon() const
445 {
446 return Icon;
447 }
448
GetLabelAlignment()449 inline emAlignment emBorder::GetLabelAlignment() const
450 {
451 return LabelAlignment;
452 }
453
GetCaptionAlignment()454 inline emAlignment emBorder::GetCaptionAlignment() const
455 {
456 return CaptionAlignment;
457 }
458
GetDescriptionAlignment()459 inline emAlignment emBorder::GetDescriptionAlignment() const
460 {
461 return DescriptionAlignment;
462 }
463
IsIconAboveCaption()464 inline bool emBorder::IsIconAboveCaption() const
465 {
466 return IconAboveCaption;
467 }
468
GetMaxIconAreaTallness()469 inline double emBorder::GetMaxIconAreaTallness() const
470 {
471 return MaxIconAreaTallness;
472 }
473
GetOuterBorderType()474 inline emBorder::OuterBorderType emBorder::GetOuterBorderType() const
475 {
476 return (OuterBorderType)OuterBorder;
477 }
478
GetInnerBorderType()479 inline emBorder::InnerBorderType emBorder::GetInnerBorderType() const
480 {
481 return (InnerBorderType)InnerBorder;
482 }
483
GetBorderScaling()484 inline double emBorder::GetBorderScaling() const
485 {
486 return BorderScaling;
487 }
488
GetLook()489 inline const emLook & emBorder::GetLook() const
490 {
491 return Look;
492 }
493
HasAux()494 inline bool emBorder::HasAux() const
495 {
496 return Aux!=NULL;
497 }
498
IsLabelInBorder()499 inline bool emBorder::IsLabelInBorder() const
500 {
501 return LabelInBorder;
502 }
503
GetTkResources()504 inline const emBorder::TkResources & emBorder::GetTkResources() const
505 {
506 return TkResVarModel->Var;
507 }
508
509
510 #endif
511