Small doc tweaks
[wxWidgets.git] / include / wx / richtext / richtextbuffer.h
1 /////////////////////////////////////////////////////////////////////////////
2 // Name: wx/richtext/richtextbuffer.h
3 // Purpose: Buffer for wxRichTextCtrl
4 // Author: Julian Smart
5 // Modified by:
6 // Created: 2005-09-30
7 // RCS-ID: $Id$
8 // Copyright: (c) Julian Smart
9 // Licence: wxWindows licence
10 /////////////////////////////////////////////////////////////////////////////
11
12 #ifndef _WX_RICHTEXTBUFFER_H_
13 #define _WX_RICHTEXTBUFFER_H_
14
15 /*
16
17 Data structures
18 ===============
19
20 Data is represented by a hierarchy of objects, all derived from
21 wxRichTextObject.
22
23 The top of the hierarchy is the buffer, a kind of wxRichTextParagraphLayoutBox.
24 These boxes will allow flexible placement of text boxes on a page, but
25 for now there is a single box representing the document, and this box is
26 a wxRichTextParagraphLayoutBox which contains further wxRichTextParagraph
27 objects, each of which can include text and images.
28
29 Each object maintains a range (start and end position) measured
30 from the start of the main parent box.
31 A paragraph object knows its range, and a text fragment knows its range
32 too. So, a character or image in a page has a position relative to the
33 start of the document, and a character in an embedded text box has
34 a position relative to that text box. For now, we will not be dealing with
35 embedded objects but it's something to bear in mind for later.
36
37 Note that internally, a range (5,5) represents a range of one character.
38 In the public wx[Rich]TextCtrl API, this would be passed to e.g. SetSelection
39 as (5,6). A paragraph with one character might have an internal range of (0, 1)
40 since the end of the paragraph takes up one position.
41
42 Layout
43 ======
44
45 When Layout is called on an object, it is given a size which the object
46 must limit itself to, or one or more flexible directions (vertical
47 or horizontal). So for example a centered paragraph is given the page
48 width to play with (minus any margins), but can extend indefinitely
49 in the vertical direction. The implementation of Layout can then
50 cache the calculated size and position within the parent.
51
52 */
53
54 /*!
55 * Includes
56 */
57
58 #include "wx/defs.h"
59
60 #if wxUSE_RICHTEXT
61
62 #include "wx/list.h"
63 #include "wx/textctrl.h"
64 #include "wx/bitmap.h"
65 #include "wx/image.h"
66 #include "wx/cmdproc.h"
67 #include "wx/txtstrm.h"
68 #include "wx/variant.h"
69
70 #if wxUSE_DATAOBJ
71 #include "wx/dataobj.h"
72 #endif
73
74 // Compatibility
75 //#define wxRichTextAttr wxTextAttr
76 #define wxTextAttrEx wxTextAttr
77
78 // Setting wxRICHTEXT_USE_OWN_CARET to 1 implements a
79 // caret reliably without using wxClientDC in case there
80 // are platform-specific problems with the generic caret.
81 #if defined(__WXGTK__) || defined(__WXMAC__)
82 #define wxRICHTEXT_USE_OWN_CARET 1
83 #else
84 #define wxRICHTEXT_USE_OWN_CARET 0
85 #endif
86
87 // Switch off for binary compatibility, on for faster drawing
88 // Note: this seems to be buggy (overzealous use of extents) so
89 // don't use for now
90 #define wxRICHTEXT_USE_OPTIMIZED_LINE_DRAWING 0
91
92 // The following two symbols determine whether an output implementation
93 // is present. To switch the relevant one on, set wxRICHTEXT_USE_XMLDOCUMENT_OUTPUT in
94 // richtextxml.cpp. By default, the faster direct output implementation is used.
95
96 // Include the wxXmlDocument implementation for output
97 #define wxRICHTEXT_HAVE_XMLDOCUMENT_OUTPUT 1
98
99 // Include the faster, direct implementation for output
100 #define wxRICHTEXT_HAVE_DIRECT_OUTPUT 1
101
102 /*
103 * Special characters
104 */
105
106 extern WXDLLIMPEXP_RICHTEXT const wxChar wxRichTextLineBreakChar;
107
108 /*!
109 * File types in wxRichText context.
110 */
111 enum wxRichTextFileType
112 {
113 wxRICHTEXT_TYPE_ANY = 0,
114 wxRICHTEXT_TYPE_TEXT,
115 wxRICHTEXT_TYPE_XML,
116 wxRICHTEXT_TYPE_HTML,
117 wxRICHTEXT_TYPE_RTF,
118 wxRICHTEXT_TYPE_PDF
119 };
120
121 /*
122 * Forward declarations
123 */
124
125 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextCtrl;
126 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextObject;
127 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextImage;
128 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextCacheObject;
129 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextObjectList;
130 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextLine;
131 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextParagraph;
132 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextFileHandler;
133 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextStyleSheet;
134 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextListStyleDefinition;
135 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextEvent;
136 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextRenderer;
137 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextBuffer;
138 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextXMLHandler;
139 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextParagraphLayoutBox;
140 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextImageBlock;
141 class WXDLLIMPEXP_FWD_XML wxXmlNode;
142 class wxRichTextFloatCollector;
143
144 /*!
145 * Flags determining the available space, passed to Layout
146 */
147
148 #define wxRICHTEXT_FIXED_WIDTH 0x01
149 #define wxRICHTEXT_FIXED_HEIGHT 0x02
150 #define wxRICHTEXT_VARIABLE_WIDTH 0x04
151 #define wxRICHTEXT_VARIABLE_HEIGHT 0x08
152
153 // Only lay out the part of the buffer that lies within
154 // the rect passed to Layout.
155 #define wxRICHTEXT_LAYOUT_SPECIFIED_RECT 0x10
156
157 /*
158 * Flags to pass to Draw
159 */
160
161 // Ignore paragraph cache optimization, e.g. for printing purposes
162 // where one line may be drawn higher (on the next page) compared
163 // with the previous line
164 #define wxRICHTEXT_DRAW_IGNORE_CACHE 0x01
165 #define wxRICHTEXT_DRAW_SELECTED 0x02
166 #define wxRICHTEXT_DRAW_PRINT 0x04
167 #define wxRICHTEXT_DRAW_GUIDELINES 0x08
168
169 /*
170 * Flags returned from hit-testing, or passed to hit-test function.
171 */
172 enum wxRichTextHitTestFlags
173 {
174 // The point was not on this object
175 wxRICHTEXT_HITTEST_NONE = 0x01,
176
177 // The point was before the position returned from HitTest
178 wxRICHTEXT_HITTEST_BEFORE = 0x02,
179
180 // The point was after the position returned from HitTest
181 wxRICHTEXT_HITTEST_AFTER = 0x04,
182
183 // The point was on the position returned from HitTest
184 wxRICHTEXT_HITTEST_ON = 0x08,
185
186 // The point was on space outside content
187 wxRICHTEXT_HITTEST_OUTSIDE = 0x10,
188
189 // Only do hit-testing at the current level (don't traverse into top-level objects)
190 wxRICHTEXT_HITTEST_NO_NESTED_OBJECTS = 0x20
191 };
192
193 /*!
194 * Flags for GetRangeSize
195 */
196
197 #define wxRICHTEXT_FORMATTED 0x01
198 #define wxRICHTEXT_UNFORMATTED 0x02
199 #define wxRICHTEXT_CACHE_SIZE 0x04
200 #define wxRICHTEXT_HEIGHT_ONLY 0x08
201
202 /*!
203 * Flags for SetStyle/SetListStyle
204 */
205
206 #define wxRICHTEXT_SETSTYLE_NONE 0x00
207
208 // Specifies that this operation should be undoable
209 #define wxRICHTEXT_SETSTYLE_WITH_UNDO 0x01
210
211 // Specifies that the style should not be applied if the
212 // combined style at this point is already the style in question.
213 #define wxRICHTEXT_SETSTYLE_OPTIMIZE 0x02
214
215 // Specifies that the style should only be applied to paragraphs,
216 // and not the content. This allows content styling to be
217 // preserved independently from that of e.g. a named paragraph style.
218 #define wxRICHTEXT_SETSTYLE_PARAGRAPHS_ONLY 0x04
219
220 // Specifies that the style should only be applied to characters,
221 // and not the paragraph. This allows content styling to be
222 // preserved independently from that of e.g. a named paragraph style.
223 #define wxRICHTEXT_SETSTYLE_CHARACTERS_ONLY 0x08
224
225 // For SetListStyle only: specifies starting from the given number, otherwise
226 // deduces number from existing attributes
227 #define wxRICHTEXT_SETSTYLE_RENUMBER 0x10
228
229 // For SetListStyle only: specifies the list level for all paragraphs, otherwise
230 // the current indentation will be used
231 #define wxRICHTEXT_SETSTYLE_SPECIFY_LEVEL 0x20
232
233 // Resets the existing style before applying the new style
234 #define wxRICHTEXT_SETSTYLE_RESET 0x40
235
236 // Removes the given style instead of applying it
237 #define wxRICHTEXT_SETSTYLE_REMOVE 0x80
238
239 /*!
240 * Flags for object insertion
241 */
242
243 #define wxRICHTEXT_INSERT_NONE 0x00
244 #define wxRICHTEXT_INSERT_WITH_PREVIOUS_PARAGRAPH_STYLE 0x01
245 #define wxRICHTEXT_INSERT_INTERACTIVE 0x02
246
247 // A special flag telling the buffer to keep the first paragraph style
248 // as-is, when deleting a paragraph marker. In future we might pass a
249 // flag to InsertFragment and DeleteRange to indicate the appropriate mode.
250 #define wxTEXT_ATTR_KEEP_FIRST_PARA_STYLE 0x10000000
251
252 /*!
253 * Default superscript/subscript font multiplication factor
254 */
255
256 #define wxSCRIPT_MUL_FACTOR 1.5
257
258 typedef unsigned short wxTextAttrDimensionFlags;
259
260 // Miscellaneous text box flags
261 enum wxTextBoxAttrFlags
262 {
263 wxTEXT_BOX_ATTR_FLOAT = 0x00000001,
264 wxTEXT_BOX_ATTR_CLEAR = 0x00000002,
265 wxTEXT_BOX_ATTR_COLLAPSE_BORDERS = 0x00000004,
266 wxTEXT_BOX_ATTR_VERTICAL_ALIGNMENT = 0x00000004
267 };
268
269 // Whether a value is present, used in dimension flags
270 enum wxTextAttrValueFlags
271 {
272 wxTEXT_ATTR_VALUE_VALID = 0x1000,
273 wxTEXT_ATTR_VALUE_VALID_MASK = 0x1000
274 };
275
276 // Units - included in the dimension value
277 enum wxTextAttrUnits
278 {
279 wxTEXT_ATTR_UNITS_TENTHS_MM = 0x0001,
280 wxTEXT_ATTR_UNITS_PIXELS = 0x0002,
281 wxTEXT_ATTR_UNITS_PERCENTAGE = 0x0004,
282 wxTEXT_ATTR_UNITS_POINTS = 0x0008,
283
284 wxTEXT_ATTR_UNITS_MASK = 0x000F
285 };
286
287 // Position - included in the dimension flags
288 enum wxTextBoxAttrPosition
289 {
290 wxTEXT_BOX_ATTR_POSITION_STATIC = 0x0000, // Default is static, i.e. as per normal layout
291 wxTEXT_BOX_ATTR_POSITION_RELATIVE = 0x0010, // Relative to the relevant edge
292 wxTEXT_BOX_ATTR_POSITION_ABSOLUTE = 0x0020,
293
294 wxTEXT_BOX_ATTR_POSITION_MASK = 0x00F0
295 };
296
297 /**
298 @class wxTextAttrDimension
299
300 A class representing a rich text dimension, including units and position.
301
302 @library{wxrichtext}
303 @category{richtext}
304
305 @see wxRichTextAttr, wxRichTextCtrl, wxTextAttrDimensions
306 */
307
308 class WXDLLIMPEXP_RICHTEXT wxTextAttrDimension
309 {
310 public:
311 /**
312 Default constructor.
313 */
314 wxTextAttrDimension() { Reset(); }
315 /**
316 Constructor taking value and units flag.
317 */
318 wxTextAttrDimension(int value, wxTextAttrUnits units = wxTEXT_ATTR_UNITS_TENTHS_MM) { m_value = value; m_flags = units|wxTEXT_ATTR_VALUE_VALID; }
319
320 /**
321 Resets the dimension value and flags.
322 */
323 void Reset() { m_value = 0; m_flags = 0; }
324
325 /**
326 Partial equality test.
327 */
328 bool EqPartial(const wxTextAttrDimension& dim) const;
329
330 /** Apply the dimension, but not those identical to @a compareWith if present.
331 */
332 bool Apply(const wxTextAttrDimension& dim, const wxTextAttrDimension* compareWith = NULL);
333
334 /** Collects the attributes that are common to a range of content, building up a note of
335 which attributes are absent in some objects and which clash in some objects.
336 */
337 void CollectCommonAttributes(const wxTextAttrDimension& attr, wxTextAttrDimension& clashingAttr, wxTextAttrDimension& absentAttr);
338
339 /**
340 Equality operator.
341 */
342 bool operator==(const wxTextAttrDimension& dim) const { return m_value == dim.m_value && m_flags == dim.m_flags; }
343
344 /**
345 Returns the integer value of the dimension.
346 */
347 int GetValue() const { return m_value; }
348
349 /**
350 Returns the floating-pointing value of the dimension in mm.
351
352 */
353 float GetValueMM() const { return float(m_value) / 10.0; }
354
355 /**
356 Sets the value of the dimension in mm.
357 */
358 void SetValueMM(float value) { m_value = (int) ((value * 10.0) + 0.5); m_flags |= wxTEXT_ATTR_VALUE_VALID; }
359
360 /**
361 Sets the integer value of the dimension.
362 */
363 void SetValue(int value) { m_value = value; m_flags |= wxTEXT_ATTR_VALUE_VALID; }
364
365 /**
366 Sets the integer value of the dimension, passing dimension flags.
367 */
368 void SetValue(int value, wxTextAttrDimensionFlags flags) { SetValue(value); m_flags = flags; }
369
370 /**
371 Sets the integer value and units.
372 */
373 void SetValue(int value, wxTextAttrUnits units) { m_value = value; m_flags = units | wxTEXT_ATTR_VALUE_VALID; }
374
375 /**
376 Sets the dimension.
377 */
378 void SetValue(const wxTextAttrDimension& dim) { (*this) = dim; }
379
380 /**
381 Gets the units of the dimension.
382 */
383 wxTextAttrUnits GetUnits() const { return (wxTextAttrUnits) (m_flags & wxTEXT_ATTR_UNITS_MASK); }
384
385 /**
386 Sets the units of the dimension.
387 */
388 void SetUnits(wxTextAttrUnits units) { m_flags &= ~wxTEXT_ATTR_UNITS_MASK; m_flags |= units; }
389
390 /**
391 Gets the position flags.
392 */
393 wxTextBoxAttrPosition GetPosition() const { return (wxTextBoxAttrPosition) (m_flags & wxTEXT_BOX_ATTR_POSITION_MASK); }
394
395 /**
396 Sets the position flags.
397 */
398 void SetPosition(wxTextBoxAttrPosition pos) { m_flags &= ~wxTEXT_BOX_ATTR_POSITION_MASK; m_flags |= pos; }
399
400 /**
401 Returns @true if the dimension is valid.
402 */
403 bool IsValid() const { return (m_flags & wxTEXT_ATTR_VALUE_VALID) != 0; }
404
405 /**
406 Sets the valid flag.
407 */
408 void SetValid(bool b) { m_flags &= ~wxTEXT_ATTR_VALUE_VALID_MASK; m_flags |= (b ? wxTEXT_ATTR_VALUE_VALID : 0); }
409
410 /**
411 Gets the dimension flags.
412 */
413 wxTextAttrDimensionFlags GetFlags() const { return m_flags; }
414
415 /**
416 Sets the dimension flags.
417 */
418 void SetFlags(wxTextAttrDimensionFlags flags) { m_flags = flags; }
419
420 int m_value;
421 wxTextAttrDimensionFlags m_flags;
422 };
423
424 /**
425 @class wxTextAttrDimensions
426 A class for left, right, top and bottom dimensions.
427
428 @library{wxrichtext}
429 @category{richtext}
430
431 @see wxRichTextAttr, wxRichTextCtrl, wxTextAttrDimension
432 */
433
434 class WXDLLIMPEXP_RICHTEXT wxTextAttrDimensions
435 {
436 public:
437 /**
438 Default constructor.
439 */
440 wxTextAttrDimensions() {}
441
442 /**
443 Resets the value and flags for all dimensions.
444 */
445 void Reset() { m_left.Reset(); m_top.Reset(); m_right.Reset(); m_bottom.Reset(); }
446
447 /**
448 Equality operator.
449 */
450 bool operator==(const wxTextAttrDimensions& dims) const { return m_left == dims.m_left && m_top == dims.m_top && m_right == dims.m_right && m_bottom == dims.m_bottom; }
451
452 /**
453 Partial equality test.
454
455 */
456 bool EqPartial(const wxTextAttrDimensions& dims) const;
457
458 /**
459 Apply border to 'this', but not if the same as @a compareWith.
460
461 */
462 bool Apply(const wxTextAttrDimensions& dims, const wxTextAttrDimensions* compareWith = NULL);
463
464 /**
465 Collects the attributes that are common to a range of content, building up a note of
466 which attributes are absent in some objects and which clash in some objects.
467
468 */
469 void CollectCommonAttributes(const wxTextAttrDimensions& attr, wxTextAttrDimensions& clashingAttr, wxTextAttrDimensions& absentAttr);
470
471 /**
472 Remove specified attributes from this object.
473 */
474 bool RemoveStyle(const wxTextAttrDimensions& attr);
475
476 /**
477 Gets the left dimension.
478 */
479 const wxTextAttrDimension& GetLeft() const { return m_left; }
480 wxTextAttrDimension& GetLeft() { return m_left; }
481
482 /**
483 Gets the right dimension.
484
485 */
486 const wxTextAttrDimension& GetRight() const { return m_right; }
487 wxTextAttrDimension& GetRight() { return m_right; }
488
489 /**
490 Gets the top dimension.
491
492 */
493 const wxTextAttrDimension& GetTop() const { return m_top; }
494 wxTextAttrDimension& GetTop() { return m_top; }
495
496 /**
497 Gets the bottom dimension.
498
499 */
500 const wxTextAttrDimension& GetBottom() const { return m_bottom; }
501 wxTextAttrDimension& GetBottom() { return m_bottom; }
502
503 wxTextAttrDimension m_left;
504 wxTextAttrDimension m_top;
505 wxTextAttrDimension m_right;
506 wxTextAttrDimension m_bottom;
507 };
508
509 /**
510 @class wxTextAttrSize
511 A class for representing width and height.
512
513 @library{wxrichtext}
514 @category{richtext}
515
516 @see wxRichTextAttr, wxRichTextCtrl, wxTextAttrDimension
517 */
518
519 class WXDLLIMPEXP_RICHTEXT wxTextAttrSize
520 {
521 public:
522 /**
523 Default constructor.
524 */
525 wxTextAttrSize() {}
526
527 /**
528 Resets the width and height dimensions.
529 */
530 void Reset() { m_width.Reset(); m_height.Reset(); }
531
532 /**
533 Equality operator.
534 */
535 bool operator==(const wxTextAttrSize& size) const { return m_width == size.m_width && m_height == size.m_height ; }
536
537 /**
538 Partial equality test.
539 */
540 bool EqPartial(const wxTextAttrSize& dims) const;
541
542 /**
543 Apply border to this object, but not if the same as @a compareWith.
544 */
545 bool Apply(const wxTextAttrSize& dims, const wxTextAttrSize* compareWith = NULL);
546
547 /**
548 Collects the attributes that are common to a range of content, building up a note of
549 which attributes are absent in some objects and which clash in some objects.
550 */
551 void CollectCommonAttributes(const wxTextAttrSize& attr, wxTextAttrSize& clashingAttr, wxTextAttrSize& absentAttr);
552
553 /**
554 Removes the specified attributes from this object.
555 */
556 bool RemoveStyle(const wxTextAttrSize& attr);
557
558 /**
559 Returns the width.
560 */
561 wxTextAttrDimension& GetWidth() { return m_width; }
562 const wxTextAttrDimension& GetWidth() const { return m_width; }
563
564 /**
565 Sets the width.
566 */
567 void SetWidth(int value, wxTextAttrDimensionFlags flags) { m_width.SetValue(value, flags); }
568 /**
569 Sets the width.
570 */
571 void SetWidth(int value, wxTextAttrUnits units) { m_width.SetValue(value, units); }
572 /**
573 Sets the width.
574 */
575 void SetWidth(const wxTextAttrDimension& dim) { m_width.SetValue(dim); }
576
577 /**
578 Gets the height.
579 */
580 wxTextAttrDimension& GetHeight() { return m_height; }
581 const wxTextAttrDimension& GetHeight() const { return m_height; }
582
583 /**
584 Sets the height.
585 */
586 void SetHeight(int value, wxTextAttrDimensionFlags flags) { m_height.SetValue(value, flags); }
587 /**
588 Sets the height.
589 */
590 void SetHeight(int value, wxTextAttrUnits units) { m_height.SetValue(value, units); }
591 /**
592 Sets the height.
593 */
594 void SetHeight(const wxTextAttrDimension& dim) { m_height.SetValue(dim); }
595
596 wxTextAttrDimension m_width;
597 wxTextAttrDimension m_height;
598 };
599
600 /**
601 @class wxTextAttrDimensionConverter
602 A class to make it easier to convert dimensions.
603
604 @library{wxrichtext}
605 @category{richtext}
606
607 @see wxRichTextAttr, wxRichTextCtrl, wxTextAttrDimension
608 */
609
610 class WXDLLIMPEXP_RICHTEXT wxTextAttrDimensionConverter
611 {
612 public:
613 /**
614 Constructor.
615 */
616 wxTextAttrDimensionConverter(wxDC& dc, double scale = 1.0, const wxSize& parentSize = wxDefaultSize);
617 /**
618 Constructor.
619 */
620 wxTextAttrDimensionConverter(int ppi, double scale = 1.0, const wxSize& parentSize = wxDefaultSize);
621
622 /**
623 Gets the pixel size for the given dimension.
624 */
625 int GetPixels(const wxTextAttrDimension& dim, int direction = wxHORIZONTAL) const;
626 /**
627 Gets the mm size for the given dimension.
628 */
629 int GetTenthsMM(const wxTextAttrDimension& dim) const;
630
631 /**
632 Converts tenths of a mm to pixels.
633 */
634 int ConvertTenthsMMToPixels(int units) const;
635 /**
636 Converts pixels to tenths of a mm.
637 */
638 int ConvertPixelsToTenthsMM(int pixels) const;
639
640 int m_ppi;
641 double m_scale;
642 wxSize m_parentSize;
643 };
644
645 // Border styles
646 enum wxTextAttrBorderStyle
647 {
648 wxTEXT_BOX_ATTR_BORDER_NONE = 0,
649 wxTEXT_BOX_ATTR_BORDER_SOLID = 1,
650 wxTEXT_BOX_ATTR_BORDER_DOTTED = 2,
651 wxTEXT_BOX_ATTR_BORDER_DASHED = 3,
652 wxTEXT_BOX_ATTR_BORDER_DOUBLE = 4,
653 wxTEXT_BOX_ATTR_BORDER_GROOVE = 5,
654 wxTEXT_BOX_ATTR_BORDER_RIDGE = 6,
655 wxTEXT_BOX_ATTR_BORDER_INSET = 7,
656 wxTEXT_BOX_ATTR_BORDER_OUTSET = 8
657 };
658
659 // Border style presence flags
660 enum wxTextAttrBorderFlags
661 {
662 wxTEXT_BOX_ATTR_BORDER_STYLE = 0x0001,
663 wxTEXT_BOX_ATTR_BORDER_COLOUR = 0x0002
664 };
665
666 // Border width symbols for qualitative widths
667 enum wxTextAttrBorderWidth
668 {
669 wxTEXT_BOX_ATTR_BORDER_THIN = -1,
670 wxTEXT_BOX_ATTR_BORDER_MEDIUM = -2,
671 wxTEXT_BOX_ATTR_BORDER_THICK = -3
672 };
673
674 // Float styles
675 enum wxTextBoxAttrFloatStyle
676 {
677 wxTEXT_BOX_ATTR_FLOAT_NONE = 0,
678 wxTEXT_BOX_ATTR_FLOAT_LEFT = 1,
679 wxTEXT_BOX_ATTR_FLOAT_RIGHT = 2
680 };
681
682 // Clear styles
683 enum wxTextBoxAttrClearStyle
684 {
685 wxTEXT_BOX_ATTR_CLEAR_NONE = 0,
686 wxTEXT_BOX_ATTR_CLEAR_LEFT = 1,
687 wxTEXT_BOX_ATTR_CLEAR_RIGHT = 2,
688 wxTEXT_BOX_ATTR_CLEAR_BOTH = 3
689 };
690
691 // Collapse mode styles. TODO: can they be switched on per side?
692 enum wxTextBoxAttrCollapseMode
693 {
694 wxTEXT_BOX_ATTR_COLLAPSE_NONE = 0,
695 wxTEXT_BOX_ATTR_COLLAPSE_FULL = 1
696 };
697
698 // Vertical alignment values
699 enum wxTextBoxAttrVerticalAlignment
700 {
701 wxTEXT_BOX_ATTR_VERTICAL_ALIGNMENT_NONE = 0,
702 wxTEXT_BOX_ATTR_VERTICAL_ALIGNMENT_TOP = 1,
703 wxTEXT_BOX_ATTR_VERTICAL_ALIGNMENT_CENTRE = 2,
704 wxTEXT_BOX_ATTR_VERTICAL_ALIGNMENT_BOTTOM = 3
705 };
706
707 /**
708 @class wxTextAttrBorder
709 A class representing a rich text object border.
710
711 @library{wxrichtext}
712 @category{richtext}
713
714 @see wxRichTextAttr, wxRichTextCtrl, wxRichTextAttrBorders
715 */
716
717 class WXDLLIMPEXP_RICHTEXT wxTextAttrBorder
718 {
719 public:
720 /**
721 Default constructor.
722 */
723 wxTextAttrBorder() { Reset(); }
724
725 /**
726 Equality operator.
727 */
728 bool operator==(const wxTextAttrBorder& border) const
729 {
730 return m_flags == border.m_flags && m_borderStyle == border.m_borderStyle &&
731 m_borderColour == border.m_borderColour && m_borderWidth == border.m_borderWidth;
732 }
733
734 /**
735 Resets the border style, colour, width and flags.
736 */
737 void Reset() { m_borderStyle = 0; m_borderColour = 0; m_flags = 0; m_borderWidth.Reset(); }
738
739 /**
740 Partial equality test.
741 */
742 bool EqPartial(const wxTextAttrBorder& border) const;
743
744 /**
745 Applies the border to this object, but not if the same as @a compareWith.
746
747 */
748 bool Apply(const wxTextAttrBorder& border, const wxTextAttrBorder* compareWith = NULL);
749
750 /**
751 Removes the specified attributes from this object.
752 */
753 bool RemoveStyle(const wxTextAttrBorder& attr);
754
755 /**
756 Collects the attributes that are common to a range of content, building up a note of
757 which attributes are absent in some objects and which clash in some objects.
758 */
759 void CollectCommonAttributes(const wxTextAttrBorder& attr, wxTextAttrBorder& clashingAttr, wxTextAttrBorder& absentAttr);
760
761 /**
762 Sets the border style.
763 */
764 void SetStyle(int style) { m_borderStyle = style; m_flags |= wxTEXT_BOX_ATTR_BORDER_STYLE; }
765
766 /**
767 Gets the border style.
768
769 */
770 int GetStyle() const { return m_borderStyle; }
771
772 /**
773 Sets the border colour.
774 */
775 void SetColour(unsigned long colour) { m_borderColour = colour; m_flags |= wxTEXT_BOX_ATTR_BORDER_COLOUR; }
776
777 /**
778 Sets the border colour.
779 */
780 void SetColour(const wxColour& colour) { m_borderColour = colour.GetRGB(); m_flags |= wxTEXT_BOX_ATTR_BORDER_COLOUR; }
781
782 /**
783 Gets the colour as a long.
784 */
785 unsigned long GetColourLong() const { return m_borderColour; }
786
787 /**
788 Gets the colour.
789 */
790 wxColour GetColour() const { return wxColour(m_borderColour); }
791
792 /**
793 Gets the border width.
794 */
795 wxTextAttrDimension& GetWidth() { return m_borderWidth; }
796 const wxTextAttrDimension& GetWidth() const { return m_borderWidth; }
797
798 /**
799 Sets the border width.
800 */
801 void SetWidth(const wxTextAttrDimension& width) { m_borderWidth = width; }
802 /**
803 Sets the border width.
804 */
805 void SetWidth(int value, wxTextAttrUnits units = wxTEXT_ATTR_UNITS_TENTHS_MM) { SetWidth(wxTextAttrDimension(value, units)); }
806
807 /**
808 True if the border has a valid style.
809 */
810 bool HasStyle() const { return (m_flags & wxTEXT_BOX_ATTR_BORDER_STYLE) != 0; }
811
812 /**
813 True if the border has a valid colour.
814 */
815 bool HasColour() const { return (m_flags & wxTEXT_BOX_ATTR_BORDER_COLOUR) != 0; }
816
817 /**
818 True if the border has a valid width.
819 */
820 bool HasWidth() const { return m_borderWidth.IsValid(); }
821
822 /**
823 True if the border is valid.
824 */
825 bool IsValid() const { return HasWidth(); }
826
827 /**
828 Set the valid flag for this border.
829 */
830 void MakeValid() { m_borderWidth.SetValid(true); }
831
832 /**
833 Returns the border flags.
834 */
835 int GetFlags() const { return m_flags; }
836
837 /**
838 Sets the border flags.
839 */
840 void SetFlags(int flags) { m_flags = flags; }
841
842 /**
843 Adds a border flag.
844 */
845 void AddFlag(int flag) { m_flags |= flag; }
846
847 /**
848 Removes a border flag.
849 */
850 void RemoveFlag(int flag) { m_flags &= ~flag; }
851
852 int m_borderStyle;
853 unsigned long m_borderColour;
854 wxTextAttrDimension m_borderWidth;
855 int m_flags;
856 };
857
858 /**
859 @class wxTextAttrBorders
860 A class representing a rich text object's borders.
861
862 @library{wxrichtext}
863 @category{richtext}
864
865 @see wxRichTextAttr, wxRichTextCtrl, wxRichTextAttrBorder
866 */
867
868 class WXDLLIMPEXP_RICHTEXT wxTextAttrBorders
869 {
870 public:
871 /**
872 Default constructor.
873 */
874 wxTextAttrBorders() { }
875
876 /**
877 Equality operator.
878 */
879 bool operator==(const wxTextAttrBorders& borders) const
880 {
881 return m_left == borders.m_left && m_right == borders.m_right &&
882 m_top == borders.m_top && m_bottom == borders.m_bottom;
883 }
884
885 /**
886 Sets the style of all borders.
887 */
888 void SetStyle(int style);
889
890 /**
891 Sets colour of all borders.
892 */
893 void SetColour(unsigned long colour);
894
895 /**
896 Sets the colour for all borders.
897 */
898 void SetColour(const wxColour& colour);
899
900 /**
901 Sets the width of all borders.
902 */
903 void SetWidth(const wxTextAttrDimension& width);
904
905 /**
906 Sets the width of all borders.
907 */
908 void SetWidth(int value, wxTextAttrUnits units = wxTEXT_ATTR_UNITS_TENTHS_MM) { SetWidth(wxTextAttrDimension(value, units)); }
909
910 /**
911 Resets all borders.
912 */
913 void Reset() { m_left.Reset(); m_right.Reset(); m_top.Reset(); m_bottom.Reset(); }
914
915 /**
916 Partial equality test.
917 */
918 bool EqPartial(const wxTextAttrBorders& borders) const;
919
920 /**
921 Applies border to this object, but not if the same as @a compareWith.
922 */
923 bool Apply(const wxTextAttrBorders& borders, const wxTextAttrBorders* compareWith = NULL);
924
925 /**
926 Removes the specified attributes from this object.
927 */
928 bool RemoveStyle(const wxTextAttrBorders& attr);
929
930 /**
931 Collects the attributes that are common to a range of content, building up a note of
932 which attributes are absent in some objects and which clash in some objects.
933 */
934 void CollectCommonAttributes(const wxTextAttrBorders& attr, wxTextAttrBorders& clashingAttr, wxTextAttrBorders& absentAttr);
935
936 /**
937 Returns @true if all borders are valid.
938 */
939 bool IsValid() const { return m_left.IsValid() || m_right.IsValid() || m_top.IsValid() || m_bottom.IsValid(); }
940
941 /**
942 Returns the left border.
943 */
944 const wxTextAttrBorder& GetLeft() const { return m_left; }
945 wxTextAttrBorder& GetLeft() { return m_left; }
946
947 /**
948 Returns the right border.
949 */
950 const wxTextAttrBorder& GetRight() const { return m_right; }
951 wxTextAttrBorder& GetRight() { return m_right; }
952
953 /**
954 Returns the top border.
955 */
956 const wxTextAttrBorder& GetTop() const { return m_top; }
957 wxTextAttrBorder& GetTop() { return m_top; }
958
959 /**
960 Returns the bottom border.
961 */
962 const wxTextAttrBorder& GetBottom() const { return m_bottom; }
963 wxTextAttrBorder& GetBottom() { return m_bottom; }
964
965 wxTextAttrBorder m_left, m_right, m_top, m_bottom;
966
967 };
968
969 /**
970 @class wxTextBoxAttr
971 A class representing the box attributes of a rich text object.
972
973 @library{wxrichtext}
974 @category{richtext}
975
976 @see wxRichTextAttr, wxRichTextCtrl
977 */
978
979 class WXDLLIMPEXP_RICHTEXT wxTextBoxAttr
980 {
981 public:
982 /**
983 Default constructor.
984 */
985 wxTextBoxAttr() { Init(); }
986
987 /**
988 Copy constructor.
989 */
990 wxTextBoxAttr(const wxTextBoxAttr& attr) { Init(); (*this) = attr; }
991
992 /**
993 Initialises this object.
994 */
995 void Init() { Reset(); }
996
997 /**
998 Resets this object.
999 */
1000 void Reset();
1001
1002 // Copy. Unnecessary since we let it do a binary copy
1003 //void Copy(const wxTextBoxAttr& attr);
1004
1005 // Assignment
1006 //void operator= (const wxTextBoxAttr& attr);
1007
1008 /**
1009 Equality test.
1010 */
1011 bool operator== (const wxTextBoxAttr& attr) const;
1012
1013 /**
1014 Partial equality test, ignoring unset attributes.
1015
1016 */
1017 bool EqPartial(const wxTextBoxAttr& attr) const;
1018
1019 /**
1020 Merges the given attributes. If @a compareWith is non-NULL, then it will be used
1021 to mask out those attributes that are the same in style and @a compareWith, for
1022 situations where we don't want to explicitly set inherited attributes.
1023 */
1024 bool Apply(const wxTextBoxAttr& style, const wxTextBoxAttr* compareWith = NULL);
1025
1026 /**
1027 Collects the attributes that are common to a range of content, building up a note of
1028 which attributes are absent in some objects and which clash in some objects.
1029 */
1030 void CollectCommonAttributes(const wxTextBoxAttr& attr, wxTextBoxAttr& clashingAttr, wxTextBoxAttr& absentAttr);
1031
1032 /**
1033 Removes the specified attributes from this object.
1034 */
1035 bool RemoveStyle(const wxTextBoxAttr& attr);
1036
1037 /**
1038 Sets the flags.
1039 */
1040 void SetFlags(int flags) { m_flags = flags; }
1041
1042 /**
1043 Returns the flags.
1044 */
1045 int GetFlags() const { return m_flags; }
1046
1047 /**
1048 Is this flag present?
1049 */
1050 bool HasFlag(wxTextBoxAttrFlags flag) const { return (m_flags & flag) != 0; }
1051
1052 /**
1053 Removes this flag.
1054 */
1055 void RemoveFlag(wxTextBoxAttrFlags flag) { m_flags &= ~flag; }
1056
1057 /**
1058 Adds this flag.
1059 */
1060 void AddFlag(wxTextBoxAttrFlags flag) { m_flags |= flag; }
1061
1062 /**
1063 Returns @true if no attributes are set.
1064 */
1065 bool IsDefault() const;
1066
1067 /**
1068 Returns the float mode.
1069 */
1070 wxTextBoxAttrFloatStyle GetFloatMode() const { return m_floatMode; }
1071
1072 /**
1073 Sets the float mode.
1074 */
1075 void SetFloatMode(wxTextBoxAttrFloatStyle mode) { m_floatMode = mode; m_flags |= wxTEXT_BOX_ATTR_FLOAT; }
1076
1077 /**
1078 Returns @true if float mode is active.
1079 */
1080 bool HasFloatMode() const { return HasFlag(wxTEXT_BOX_ATTR_FLOAT); }
1081
1082 /**
1083 Returns @true if this object is floating?
1084 */
1085 bool IsFloating() const { return HasFloatMode() && GetFloatMode() != wxTEXT_BOX_ATTR_FLOAT_NONE; }
1086
1087 /**
1088 Returns the clear mode - whether to wrap text after object. Currently unimplemented.
1089 */
1090 wxTextBoxAttrClearStyle GetClearMode() const { return m_clearMode; }
1091
1092 /**
1093 Set the clear mode. Currently unimplemented.
1094 */
1095 void SetClearMode(wxTextBoxAttrClearStyle mode) { m_clearMode = mode; m_flags |= wxTEXT_BOX_ATTR_CLEAR; }
1096
1097 /**
1098 Returns @true if we have a clear flag.
1099 */
1100 bool HasClearMode() const { return HasFlag(wxTEXT_BOX_ATTR_CLEAR); }
1101
1102 /**
1103 Returns the collapse mode - whether to collapse borders. Currently unimplemented.
1104 */
1105 wxTextBoxAttrCollapseMode GetCollapseBorders() const { return m_collapseMode; }
1106
1107 /**
1108 Sets the collapse mode - whether to collapse borders. Currently unimplemented.
1109 */
1110 void SetCollapseBorders(wxTextBoxAttrCollapseMode collapse) { m_collapseMode = collapse; m_flags |= wxTEXT_BOX_ATTR_COLLAPSE_BORDERS; }
1111
1112 /**
1113 Returns @true if the collapse borders flag is present.
1114 */
1115 bool HasCollapseBorders() const { return HasFlag(wxTEXT_BOX_ATTR_COLLAPSE_BORDERS); }
1116
1117 /**
1118 Returns the vertical alignment.
1119 */
1120 wxTextBoxAttrVerticalAlignment GetVerticalAlignment() const { return m_verticalAlignment; }
1121
1122 /**
1123 Sets the vertical alignment.
1124 */
1125 void SetVerticalAlignment(wxTextBoxAttrVerticalAlignment verticalAlignment) { m_verticalAlignment = verticalAlignment; m_flags |= wxTEXT_BOX_ATTR_VERTICAL_ALIGNMENT; }
1126
1127 /**
1128 Returns @true if a vertical alignment flag is present.
1129 */
1130 bool HasVerticalAlignment() const { return HasFlag(wxTEXT_BOX_ATTR_VERTICAL_ALIGNMENT); }
1131
1132 /**
1133 Returns the margin values.
1134 */
1135 wxTextAttrDimensions& GetMargins() { return m_margins; }
1136 const wxTextAttrDimensions& GetMargins() const { return m_margins; }
1137
1138 /**
1139 Returns the left margin.
1140 */
1141 wxTextAttrDimension& GetLeftMargin() { return m_margins.m_left; }
1142 const wxTextAttrDimension& GetLeftMargin() const { return m_margins.m_left; }
1143
1144 /**
1145 Returns the right margin.
1146 */
1147 wxTextAttrDimension& GetRightMargin() { return m_margins.m_right; }
1148 const wxTextAttrDimension& GetRightMargin() const { return m_margins.m_right; }
1149
1150 /**
1151 Returns the top margin.
1152 */
1153 wxTextAttrDimension& GetTopMargin() { return m_margins.m_top; }
1154 const wxTextAttrDimension& GetTopMargin() const { return m_margins.m_top; }
1155
1156 /**
1157 Returns the bottom margin.
1158 */
1159 wxTextAttrDimension& GetBottomMargin() { return m_margins.m_bottom; }
1160 const wxTextAttrDimension& GetBottomMargin() const { return m_margins.m_bottom; }
1161
1162 /**
1163 Returns the position.
1164 */
1165 wxTextAttrDimensions& GetPosition() { return m_position; }
1166 const wxTextAttrDimensions& GetPosition() const { return m_position; }
1167
1168 /**
1169 Returns the left position.
1170 */
1171 wxTextAttrDimension& GetLeft() { return m_position.m_left; }
1172 const wxTextAttrDimension& GetLeft() const { return m_position.m_left; }
1173
1174 /**
1175 Returns the right position.
1176 */
1177 wxTextAttrDimension& GetRight() { return m_position.m_right; }
1178 const wxTextAttrDimension& GetRight() const { return m_position.m_right; }
1179
1180 /**
1181 Returns the top position.
1182 */
1183 wxTextAttrDimension& GetTop() { return m_position.m_top; }
1184 const wxTextAttrDimension& GetTop() const { return m_position.m_top; }
1185
1186 /**
1187 Returns the bottom position.
1188 */
1189 wxTextAttrDimension& GetBottom() { return m_position.m_bottom; }
1190 const wxTextAttrDimension& GetBottom() const { return m_position.m_bottom; }
1191
1192 /**
1193 Returns the padding values.
1194 */
1195 wxTextAttrDimensions& GetPadding() { return m_padding; }
1196 const wxTextAttrDimensions& GetPadding() const { return m_padding; }
1197
1198 /**
1199 Returns the left padding value.
1200 */
1201 wxTextAttrDimension& GetLeftPadding() { return m_padding.m_left; }
1202 const wxTextAttrDimension& GetLeftPadding() const { return m_padding.m_left; }
1203
1204 /**
1205 Returns the right padding value.
1206 */
1207 wxTextAttrDimension& GetRightPadding() { return m_padding.m_right; }
1208 const wxTextAttrDimension& GetRightPadding() const { return m_padding.m_right; }
1209
1210 /**
1211 Returns the top padding value.
1212 */
1213 wxTextAttrDimension& GetTopPadding() { return m_padding.m_top; }
1214 const wxTextAttrDimension& GetTopPadding() const { return m_padding.m_top; }
1215
1216 /**
1217 Returns the bottom padding value.
1218 */
1219 wxTextAttrDimension& GetBottomPadding() { return m_padding.m_bottom; }
1220 const wxTextAttrDimension& GetBottomPadding() const { return m_padding.m_bottom; }
1221
1222 /**
1223 Returns the borders.
1224 */
1225 wxTextAttrBorders& GetBorder() { return m_border; }
1226 const wxTextAttrBorders& GetBorder() const { return m_border; }
1227
1228 /**
1229 Returns the left border.
1230 */
1231 wxTextAttrBorder& GetLeftBorder() { return m_border.m_left; }
1232 const wxTextAttrBorder& GetLeftBorder() const { return m_border.m_left; }
1233
1234 /**
1235 Returns the top border.
1236 */
1237 wxTextAttrBorder& GetTopBorder() { return m_border.m_top; }
1238 const wxTextAttrBorder& GetTopBorder() const { return m_border.m_top; }
1239
1240 /**
1241 Returns the right border.
1242 */
1243 wxTextAttrBorder& GetRightBorder() { return m_border.m_right; }
1244 const wxTextAttrBorder& GetRightBorder() const { return m_border.m_right; }
1245
1246 /**
1247 Returns the bottom border.
1248 */
1249 wxTextAttrBorder& GetBottomBorder() { return m_border.m_bottom; }
1250 const wxTextAttrBorder& GetBottomBorder() const { return m_border.m_bottom; }
1251
1252 /**
1253 Returns the outline.
1254 */
1255 wxTextAttrBorders& GetOutline() { return m_outline; }
1256 const wxTextAttrBorders& GetOutline() const { return m_outline; }
1257
1258 /**
1259 Returns the left outline.
1260 */
1261 wxTextAttrBorder& GetLeftOutline() { return m_outline.m_left; }
1262 const wxTextAttrBorder& GetLeftOutline() const { return m_outline.m_left; }
1263
1264 /**
1265 Returns the top outline.
1266 */
1267 wxTextAttrBorder& GetTopOutline() { return m_outline.m_top; }
1268 const wxTextAttrBorder& GetTopOutline() const { return m_outline.m_top; }
1269
1270 /**
1271 Returns the right outline.
1272 */
1273 wxTextAttrBorder& GetRightOutline() { return m_outline.m_right; }
1274 const wxTextAttrBorder& GetRightOutline() const { return m_outline.m_right; }
1275
1276 /**
1277 Returns the bottom outline.
1278 */
1279 wxTextAttrBorder& GetBottomOutline() { return m_outline.m_bottom; }
1280 const wxTextAttrBorder& GetBottomOutline() const { return m_outline.m_bottom; }
1281
1282 /**
1283 Returns the object size.
1284 */
1285 wxTextAttrSize& GetSize() { return m_size; }
1286 const wxTextAttrSize& GetSize() const { return m_size; }
1287
1288 /**
1289 Sets the object size.
1290 */
1291 void SetSize(const wxTextAttrSize& sz) { m_size = sz; }
1292
1293 /**
1294 Returns the object width.
1295 */
1296 wxTextAttrDimension& GetWidth() { return m_size.m_width; }
1297 const wxTextAttrDimension& GetWidth() const { return m_size.m_width; }
1298
1299 /**
1300 Returns the object height.
1301 */
1302 wxTextAttrDimension& GetHeight() { return m_size.m_height; }
1303 const wxTextAttrDimension& GetHeight() const { return m_size.m_height; }
1304
1305 public:
1306
1307 int m_flags;
1308
1309 wxTextAttrDimensions m_margins;
1310 wxTextAttrDimensions m_padding;
1311 wxTextAttrDimensions m_position;
1312
1313 wxTextAttrSize m_size;
1314
1315 wxTextAttrBorders m_border;
1316 wxTextAttrBorders m_outline;
1317
1318 wxTextBoxAttrFloatStyle m_floatMode;
1319 wxTextBoxAttrClearStyle m_clearMode;
1320 wxTextBoxAttrCollapseMode m_collapseMode;
1321 wxTextBoxAttrVerticalAlignment m_verticalAlignment;
1322 };
1323
1324 /**
1325 @class wxRichTextAttr
1326 A class representing enhanced attributes for rich text objects.
1327 This adds a wxTextBoxAttr member to the basic wxTextAttr class.
1328
1329 @library{wxrichtext}
1330 @category{richtext}
1331
1332 @see wxRichTextAttr, wxTextBoxAttr, wxRichTextCtrl
1333 */
1334
1335 class WXDLLIMPEXP_RICHTEXT wxRichTextAttr: public wxTextAttr
1336 {
1337 public:
1338 /**
1339 Constructor taking a wxTextAttr.
1340 */
1341 wxRichTextAttr(const wxTextAttr& attr) { wxTextAttr::Copy(attr); }
1342
1343 /**
1344 Copy constructor.
1345 */
1346 wxRichTextAttr(const wxRichTextAttr& attr): wxTextAttr() { Copy(attr); }
1347
1348 /**
1349 Default constructor.
1350 */
1351 wxRichTextAttr() {}
1352
1353 /**
1354 Copy function.
1355 */
1356 void Copy(const wxRichTextAttr& attr);
1357
1358 /**
1359 Assignment operator.
1360 */
1361 void operator=(const wxRichTextAttr& attr) { Copy(attr); }
1362
1363 /**
1364 Assignment operator.
1365 */
1366 void operator=(const wxTextAttr& attr) { wxTextAttr::Copy(attr); }
1367
1368 /**
1369 Equality test.
1370 */
1371 bool operator==(const wxRichTextAttr& attr) const;
1372
1373 /**
1374 Partial equality test taking comparison object into account.
1375 */
1376 bool EqPartial(const wxRichTextAttr& attr) const;
1377
1378 /**
1379 Merges the given attributes. If @a compareWith
1380 is non-NULL, then it will be used to mask out those attributes that are the same in style
1381 and @a compareWith, for situations where we don't want to explicitly set inherited attributes.
1382 */
1383 bool Apply(const wxRichTextAttr& style, const wxRichTextAttr* compareWith = NULL);
1384
1385 /**
1386 Collects the attributes that are common to a range of content, building up a note of
1387 which attributes are absent in some objects and which clash in some objects.
1388 */
1389 void CollectCommonAttributes(const wxRichTextAttr& attr, wxRichTextAttr& clashingAttr, wxRichTextAttr& absentAttr);
1390
1391 /**
1392 Removes the specified attributes from this object.
1393 */
1394 bool RemoveStyle(const wxRichTextAttr& attr);
1395
1396 /**
1397 Returns the text box attributes.
1398 */
1399 wxTextBoxAttr& GetTextBoxAttr() { return m_textBoxAttr; }
1400 const wxTextBoxAttr& GetTextBoxAttr() const { return m_textBoxAttr; }
1401
1402 /**
1403 Set the text box attributes.
1404 */
1405 void SetTextBoxAttr(const wxTextBoxAttr& attr) { m_textBoxAttr = attr; }
1406
1407 wxTextBoxAttr m_textBoxAttr;
1408 };
1409
1410 WX_DECLARE_USER_EXPORTED_OBJARRAY(wxVariant, wxRichTextVariantArray, WXDLLIMPEXP_RICHTEXT);
1411
1412 // ----------------------------------------------------------------------------
1413 // wxRichTextProperties - A simple property class using wxVariants
1414 // ----------------------------------------------------------------------------
1415
1416 class WXDLLIMPEXP_RICHTEXT wxRichTextProperties: public wxObject
1417 {
1418 DECLARE_DYNAMIC_CLASS(wxRichTextProperties)
1419 public:
1420 wxRichTextProperties() {}
1421 wxRichTextProperties(const wxRichTextProperties& props): wxObject() { Copy(props); }
1422
1423 void operator=(const wxRichTextProperties& props) { Copy(props); }
1424 bool operator==(const wxRichTextProperties& props) const;
1425 void Copy(const wxRichTextProperties& props) { m_properties = props.m_properties; }
1426 const wxVariant& operator[](size_t idx) const { return m_properties[idx]; }
1427 wxVariant& operator[](size_t idx) { return m_properties[idx]; }
1428 void Clear() { m_properties.Clear(); }
1429
1430 const wxRichTextVariantArray& GetProperties() const { return m_properties; }
1431 wxRichTextVariantArray& GetProperties() { return m_properties; }
1432 void SetProperties(const wxRichTextVariantArray& props) { m_properties = props; }
1433
1434 wxArrayString GetPropertyNames() const;
1435
1436 size_t GetCount() const { return m_properties.GetCount(); }
1437
1438 int HasProperty(const wxString& name) const { return Find(name) != -1; }
1439
1440 int Find(const wxString& name) const;
1441 const wxVariant& GetProperty(const wxString& name) const;
1442 wxVariant* FindOrCreateProperty(const wxString& name);
1443
1444 wxString GetPropertyString(const wxString& name) const;
1445 long GetPropertyLong(const wxString& name) const;
1446 bool GetPropertyBool(const wxString& name) const;
1447 double GetPropertyDouble(const wxString& name) const;
1448
1449 void SetProperty(const wxVariant& variant);
1450 void SetProperty(const wxString& name, const wxVariant& variant);
1451 void SetProperty(const wxString& name, const wxString& value);
1452 void SetProperty(const wxString& name, long value);
1453 void SetProperty(const wxString& name, double value);
1454 void SetProperty(const wxString& name, bool value);
1455
1456 protected:
1457 wxRichTextVariantArray m_properties;
1458 };
1459
1460
1461 /*!
1462 * wxRichTextFontTable
1463 * Manages quick access to a pool of fonts for rendering rich text
1464 */
1465
1466 class WXDLLIMPEXP_RICHTEXT wxRichTextFontTable: public wxObject
1467 {
1468 public:
1469 wxRichTextFontTable();
1470
1471 wxRichTextFontTable(const wxRichTextFontTable& table);
1472 virtual ~wxRichTextFontTable();
1473
1474 bool IsOk() const { return m_refData != NULL; }
1475
1476 wxFont FindFont(const wxRichTextAttr& fontSpec);
1477 void Clear();
1478
1479 void operator= (const wxRichTextFontTable& table);
1480 bool operator == (const wxRichTextFontTable& table) const;
1481 bool operator != (const wxRichTextFontTable& table) const { return !(*this == table); }
1482
1483 protected:
1484
1485 DECLARE_DYNAMIC_CLASS(wxRichTextFontTable)
1486 };
1487
1488 /*!
1489 * wxRichTextRange class declaration
1490 * This stores beginning and end positions for a range of data.
1491 * TODO: consider renaming wxTextRange and using for all text controls.
1492 */
1493
1494 class WXDLLIMPEXP_RICHTEXT wxRichTextRange
1495 {
1496 public:
1497 // Constructors
1498
1499 wxRichTextRange() { m_start = 0; m_end = 0; }
1500 wxRichTextRange(long start, long end) { m_start = start; m_end = end; }
1501 wxRichTextRange(const wxRichTextRange& range) { m_start = range.m_start; m_end = range.m_end; }
1502 ~wxRichTextRange() {}
1503
1504 void operator =(const wxRichTextRange& range) { m_start = range.m_start; m_end = range.m_end; }
1505 bool operator ==(const wxRichTextRange& range) const { return (m_start == range.m_start && m_end == range.m_end); }
1506 bool operator !=(const wxRichTextRange& range) const { return (m_start != range.m_start || m_end != range.m_end); }
1507 wxRichTextRange operator -(const wxRichTextRange& range) const { return wxRichTextRange(m_start - range.m_start, m_end - range.m_end); }
1508 wxRichTextRange operator +(const wxRichTextRange& range) const { return wxRichTextRange(m_start + range.m_start, m_end + range.m_end); }
1509
1510 void SetRange(long start, long end) { m_start = start; m_end = end; }
1511
1512 void SetStart(long start) { m_start = start; }
1513 long GetStart() const { return m_start; }
1514
1515 void SetEnd(long end) { m_end = end; }
1516 long GetEnd() const { return m_end; }
1517
1518 /// Returns true if this range is completely outside 'range'
1519 bool IsOutside(const wxRichTextRange& range) const { return range.m_start > m_end || range.m_end < m_start; }
1520
1521 /// Returns true if this range is completely within 'range'
1522 bool IsWithin(const wxRichTextRange& range) const { return m_start >= range.m_start && m_end <= range.m_end; }
1523
1524 /// Returns true if the given position is within this range. Allow
1525 /// for the possibility of an empty range - assume the position
1526 /// is within this empty range. NO, I think we should not match with an empty range.
1527 // bool Contains(long pos) const { return pos >= m_start && (pos <= m_end || GetLength() == 0); }
1528 bool Contains(long pos) const { return pos >= m_start && pos <= m_end ; }
1529
1530 /// Limit this range to be within 'range'
1531 bool LimitTo(const wxRichTextRange& range) ;
1532
1533 /// Gets the length of the range
1534 long GetLength() const { return m_end - m_start + 1; }
1535
1536 /// Swaps the start and end
1537 void Swap() { long tmp = m_start; m_start = m_end; m_end = tmp; }
1538
1539 /// Convert to internal form: (n, n) is the range of a single character.
1540 wxRichTextRange ToInternal() const { return wxRichTextRange(m_start, m_end-1); }
1541
1542 /// Convert from internal to public API form: (n, n+1) is the range of a single character.
1543 wxRichTextRange FromInternal() const { return wxRichTextRange(m_start, m_end+1); }
1544
1545 protected:
1546 long m_start;
1547 long m_end;
1548 };
1549
1550 WX_DECLARE_USER_EXPORTED_OBJARRAY(wxRichTextRange, wxRichTextRangeArray, WXDLLIMPEXP_RICHTEXT);
1551
1552 #define wxRICHTEXT_ALL wxRichTextRange(-2, -2)
1553 #define wxRICHTEXT_NONE wxRichTextRange(-1, -1)
1554
1555 // ----------------------------------------------------------------------------
1556 // wxRichTextSelection: stores selection information
1557 // ----------------------------------------------------------------------------
1558
1559 #define wxRICHTEXT_NO_SELECTION wxRichTextRange(-2, -2)
1560
1561 class WXDLLIMPEXP_RICHTEXT wxRichTextSelection
1562 {
1563 public:
1564 wxRichTextSelection(const wxRichTextSelection& sel) { Copy(sel); }
1565 wxRichTextSelection(const wxRichTextRange& range, wxRichTextParagraphLayoutBox* container) { m_ranges.Add(range); m_container = container; }
1566 wxRichTextSelection() { Reset(); }
1567
1568 /// Reset the selection
1569 void Reset() { m_ranges.Clear(); m_container = NULL; }
1570
1571 /// Set the selection
1572 void Set(const wxRichTextRange& range, wxRichTextParagraphLayoutBox* container)
1573 { m_ranges.Clear(); m_ranges.Add(range); m_container = container; }
1574
1575 /// Add a selection
1576 void Add(const wxRichTextRange& range)
1577 { m_ranges.Add(range); }
1578
1579 /// Set the selections
1580 void Set(const wxRichTextRangeArray& ranges, wxRichTextParagraphLayoutBox* container)
1581 { m_ranges = ranges; m_container = container; }
1582
1583 /// Copy
1584 void Copy(const wxRichTextSelection& sel)
1585 { m_ranges = sel.m_ranges; m_container = sel.m_container; }
1586
1587 /// Assignment
1588 void operator=(const wxRichTextSelection& sel) { Copy(sel); }
1589
1590 /// Equality test
1591 bool operator==(const wxRichTextSelection& sel) const;
1592
1593 /// Index operator
1594 wxRichTextRange operator[](size_t i) const { return GetRange(i); }
1595
1596 /// Get the selection ranges
1597 wxRichTextRangeArray& GetRanges() { return m_ranges; }
1598 const wxRichTextRangeArray& GetRanges() const { return m_ranges; }
1599
1600 /// Set the selection ranges
1601 void SetRanges(const wxRichTextRangeArray& ranges) { m_ranges = ranges; }
1602
1603 /// Get the number of ranges in the selection
1604 size_t GetCount() const { return m_ranges.GetCount(); }
1605
1606 /// Get the given range
1607 wxRichTextRange GetRange(size_t i) const { return m_ranges[i]; }
1608
1609 /// Get the first range if there is one, otherwise wxRICHTEXT_NO_SELECTION.
1610 wxRichTextRange GetRange() const { return (m_ranges.GetCount() > 0) ? (m_ranges[0]) : wxRICHTEXT_NO_SELECTION; }
1611
1612 /// Set a single range.
1613 void SetRange(const wxRichTextRange& range) { m_ranges.Clear(); m_ranges.Add(range); }
1614
1615 /// Get the container for which the selection is valid
1616 wxRichTextParagraphLayoutBox* GetContainer() const { return m_container; }
1617
1618 /// Set the container for which the selection is valid
1619 void SetContainer(wxRichTextParagraphLayoutBox* container) { m_container = container; }
1620
1621 /// Is the selection valid?
1622 bool IsValid() const { return m_ranges.GetCount() > 0 && GetContainer(); }
1623
1624 /// Get the selection appropriate to the specified object, if any; returns an empty array if none
1625 /// at the level of the object's container.
1626 wxRichTextRangeArray GetSelectionForObject(wxRichTextObject* obj) const;
1627
1628 /// Is the given position within the selection?
1629 bool WithinSelection(long pos, wxRichTextObject* obj) const;
1630
1631 /// Is the given position within the selection?
1632 bool WithinSelection(long pos) const { return WithinSelection(pos, m_ranges); }
1633
1634 /// Is the given position within the selection range?
1635 static bool WithinSelection(long pos, const wxRichTextRangeArray& ranges);
1636
1637 /// Is the given range within the selection range?
1638 static bool WithinSelection(const wxRichTextRange& range, const wxRichTextRangeArray& ranges);
1639
1640 wxRichTextRangeArray m_ranges;
1641 wxRichTextParagraphLayoutBox* m_container;
1642 };
1643
1644 /*!
1645 * wxRichTextObject class declaration
1646 * This is the base for drawable objects.
1647 */
1648
1649 class WXDLLIMPEXP_RICHTEXT wxRichTextObject: public wxObject
1650 {
1651 DECLARE_CLASS(wxRichTextObject)
1652 public:
1653 // Constructors
1654
1655 wxRichTextObject(wxRichTextObject* parent = NULL);
1656 virtual ~wxRichTextObject();
1657
1658 // Overrideables
1659
1660 /// Draw the item, within the given range. Some objects may ignore the range (for
1661 /// example paragraphs) while others must obey it (lines, to implement wrapping)
1662 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style) = 0;
1663
1664 /// Lay the item out at the specified position with the given size constraint.
1665 /// Layout must set the cached size.
1666 virtual bool Layout(wxDC& dc, const wxRect& rect, int style) = 0;
1667
1668 /// Hit-testing: returns a flag indicating hit test details, plus
1669 /// information about position. contextObj is returned to specify what object
1670 /// position is relevant to, since otherwise there's an ambiguity.
1671 /// obj may not a child of contextObj, since we may be referring to the container itself
1672 /// if we have no hit on a child - for example if we click outside an object.
1673 virtual int HitTest(wxDC& dc, const wxPoint& pt, long& textPosition, wxRichTextObject** obj, wxRichTextObject** contextObj, int flags = 0);
1674
1675 /// Finds the absolute position and row height for the given character position
1676 virtual bool FindPosition(wxDC& WXUNUSED(dc), long WXUNUSED(index), wxPoint& WXUNUSED(pt), int* WXUNUSED(height), bool WXUNUSED(forceLineStart)) { return false; }
1677
1678 /// Get the best size, i.e. the ideal starting size for this object irrespective
1679 /// of available space. For a short text string, it will be the size that exactly encloses
1680 /// the text. For a longer string, it might use the parent width for example.
1681 virtual wxSize GetBestSize() const { return m_size; }
1682
1683 /**
1684 Gets the object size for the given range. Returns false if the range
1685 is invalid for this object.
1686 */
1687
1688 virtual bool GetRangeSize(const wxRichTextRange& range, wxSize& size, int& descent, wxDC& dc, int flags, wxPoint position = wxPoint(0,0), wxArrayInt* partialExtents = NULL) const = 0;
1689
1690 /// Do a split, returning an object containing the second part, and setting
1691 /// the first part in 'this'.
1692 virtual wxRichTextObject* DoSplit(long WXUNUSED(pos)) { return NULL; }
1693
1694 /// Calculate range. By default, guess that the object is 1 unit long.
1695 virtual void CalculateRange(long start, long& end) { end = start ; m_range.SetRange(start, end); }
1696
1697 /// Delete range
1698 virtual bool DeleteRange(const wxRichTextRange& WXUNUSED(range)) { return false; }
1699
1700 /// Returns true if the object is empty
1701 virtual bool IsEmpty() const { return false; }
1702
1703 /// Whether this object floatable
1704 virtual bool IsFloatable() const { return false; }
1705
1706 /// Whether this object is currently floating
1707 virtual bool IsFloating() const { return GetAttributes().GetTextBoxAttr().IsFloating(); }
1708
1709 /// Whether this object is a place holding one
1710 // virtual bool IsPlaceHolding() const { return false; }
1711
1712 /// The floating direction
1713 virtual int GetFloatDirection() const { return GetAttributes().GetTextBoxAttr().GetFloatMode(); }
1714
1715 /// Get any text in this object for the given range
1716 virtual wxString GetTextForRange(const wxRichTextRange& WXUNUSED(range)) const { return wxEmptyString; }
1717
1718 /// Returns true if this object can merge itself with the given one.
1719 virtual bool CanMerge(wxRichTextObject* WXUNUSED(object)) const { return false; }
1720
1721 /// Returns true if this object merged itself with the given one.
1722 /// The calling code will then delete the given object.
1723 virtual bool Merge(wxRichTextObject* WXUNUSED(object)) { return false; }
1724
1725 /// Dump to output stream for debugging
1726 virtual void Dump(wxTextOutputStream& stream);
1727
1728 /// Can we edit properties via a GUI?
1729 virtual bool CanEditProperties() const { return false; }
1730
1731 /// Edit properties via a GUI
1732 virtual bool EditProperties(wxWindow* WXUNUSED(parent), wxRichTextBuffer* WXUNUSED(buffer)) { return false; }
1733
1734 /// Return the label to be used for the properties context menu item.
1735 virtual wxString GetPropertiesMenuLabel() const { return wxEmptyString; }
1736
1737 /// Returns true if objects of this class can accept the focus, i.e. a call to SetFocusObject
1738 /// is possible. For example, containers supporting text, such as a text box object, can accept the focus,
1739 /// but a table can't (set the focus to individual cells instead).
1740 virtual bool AcceptsFocus() const { return false; }
1741
1742 #if wxUSE_XML
1743 /// Import this object from XML
1744 virtual bool ImportFromXML(wxRichTextBuffer* buffer, wxXmlNode* node, wxRichTextXMLHandler* handler, bool* recurse);
1745 #endif
1746
1747 #if wxRICHTEXT_HAVE_DIRECT_OUTPUT
1748 /// Export this object directly to the given stream.
1749 virtual bool ExportXML(wxOutputStream& stream, int indent, wxRichTextXMLHandler* handler);
1750 #endif
1751
1752 #if wxRICHTEXT_HAVE_XMLDOCUMENT_OUTPUT
1753 /// Export this object to the given parent node, usually creating at least one child node.
1754 virtual bool ExportXML(wxXmlNode* parent, wxRichTextXMLHandler* handler);
1755 #endif
1756
1757 /// Does this object take note of paragraph attributes? Text and image objects don't.
1758 virtual bool UsesParagraphAttributes() const { return true; }
1759
1760 /// What is the XML node name of this object?
1761 virtual wxString GetXMLNodeName() const { return wxT("unknown"); }
1762
1763 /// Invalidate the buffer. With no argument, invalidates whole buffer.
1764 virtual void Invalidate(const wxRichTextRange& invalidRange = wxRICHTEXT_ALL);
1765
1766 /// Can this object handle the selections of its children? FOr example, a table.
1767 virtual bool HandlesChildSelections() const { return false; }
1768
1769 /// Returns a selection object specifying the selections between start and end character positions.
1770 /// For example, a table would deduce what cells (of range length 1) are selected when dragging across the table.
1771 virtual wxRichTextSelection GetSelection(long WXUNUSED(start), long WXUNUSED(end)) const { return wxRichTextSelection(); }
1772
1773 // Accessors
1774
1775 /// Get/set the cached object size as calculated by Layout.
1776 virtual wxSize GetCachedSize() const { return m_size; }
1777 virtual void SetCachedSize(const wxSize& sz) { m_size = sz; }
1778
1779 /// Get/set the maximum object size as calculated by Layout. This allows
1780 /// us to fit an object to its contents or allocate extra space if required.
1781 virtual wxSize GetMaxSize() const { return m_maxSize; }
1782 virtual void SetMaxSize(const wxSize& sz) { m_maxSize = sz; }
1783
1784 /// Get/set the minimum object size as calculated by Layout. This allows
1785 /// us to constrain an object to its absolute minimum size if necessary.
1786 virtual wxSize GetMinSize() const { return m_minSize; }
1787 virtual void SetMinSize(const wxSize& sz) { m_minSize = sz; }
1788
1789 /// Get the 'natural' size for an object. For an image, it would be the
1790 /// image size.
1791 virtual wxTextAttrSize GetNaturalSize() const { return wxTextAttrSize(); }
1792
1793 /// Get/set the object position
1794 virtual wxPoint GetPosition() const { return m_pos; }
1795 virtual void SetPosition(const wxPoint& pos) { m_pos = pos; }
1796
1797 /// Get the absolute object position, by traversing up the child/parent hierarchy
1798 /// TODO: may not be needed, if all object positions are in fact relative to the
1799 /// top of the coordinate space.
1800 virtual wxPoint GetAbsolutePosition() const;
1801
1802 /// Get the rectangle enclosing the object
1803 virtual wxRect GetRect() const { return wxRect(GetPosition(), GetCachedSize()); }
1804
1805 /// Set the range
1806 void SetRange(const wxRichTextRange& range) { m_range = range; }
1807
1808 /// Get the range
1809 const wxRichTextRange& GetRange() const { return m_range; }
1810 wxRichTextRange& GetRange() { return m_range; }
1811
1812 /// Set the 'own' range, for a top-level object with its own position space
1813 void SetOwnRange(const wxRichTextRange& range) { m_ownRange = range; }
1814
1815 /// Get own range (valid if top-level)
1816 const wxRichTextRange& GetOwnRange() const { return m_ownRange; }
1817 wxRichTextRange& GetOwnRange() { return m_ownRange; }
1818
1819 /// Get own range only if a top-level object
1820 wxRichTextRange GetOwnRangeIfTopLevel() const { return IsTopLevel() ? m_ownRange : m_range; }
1821
1822 /// Is this composite?
1823 virtual bool IsComposite() const { return false; }
1824
1825 /// Get/set the parent.
1826 virtual wxRichTextObject* GetParent() const { return m_parent; }
1827 virtual void SetParent(wxRichTextObject* parent) { m_parent = parent; }
1828
1829 /// Get/set the top-level container of this object.
1830 /// May return itself if it's a container; use GetParentContainer to return
1831 /// a different container.
1832 virtual wxRichTextParagraphLayoutBox* GetContainer() const;
1833
1834 /// Get/set the top-level container of this object.
1835 /// Returns a different container than itself, unless there's no parent, in which case it will return NULL.
1836 virtual wxRichTextParagraphLayoutBox* GetParentContainer() const { return GetParent() ? GetParent()->GetContainer() : GetContainer(); }
1837
1838 /// Set the margin around the object, in pixels
1839 virtual void SetMargins(int margin);
1840 virtual void SetMargins(int leftMargin, int rightMargin, int topMargin, int bottomMargin);
1841 virtual int GetLeftMargin() const;
1842 virtual int GetRightMargin() const;
1843 virtual int GetTopMargin() const;
1844 virtual int GetBottomMargin() const;
1845
1846 /// Calculate the available content space in the given rectangle, given the
1847 /// margins, border and padding specified in the object's attributes.
1848 virtual wxRect GetAvailableContentArea(wxDC& dc, const wxRect& outerRect) const;
1849
1850 /// Lays out the object first with a given amount of space, and then if no width was specified in attr,
1851 /// lays out the object again using the minimum size
1852 virtual bool LayoutToBestSize(wxDC& dc, wxRichTextBuffer* buffer,
1853 const wxRichTextAttr& parentAttr, const wxRichTextAttr& attr, const wxRect& availableParentSpace, int style);
1854
1855 /// Set/get attributes object
1856 void SetAttributes(const wxRichTextAttr& attr) { m_attributes = attr; }
1857 const wxRichTextAttr& GetAttributes() const { return m_attributes; }
1858 wxRichTextAttr& GetAttributes() { return m_attributes; }
1859
1860 /// Set/get properties
1861 wxRichTextProperties& GetProperties() { return m_properties; }
1862 const wxRichTextProperties& GetProperties() const { return m_properties; }
1863 void SetProperties(const wxRichTextProperties& props) { m_properties = props; }
1864
1865 /// Set/get stored descent
1866 void SetDescent(int descent) { m_descent = descent; }
1867 int GetDescent() const { return m_descent; }
1868
1869 /// Gets the containing buffer
1870 wxRichTextBuffer* GetBuffer() const;
1871
1872 /// Sets the identifying name for this object, as a property.
1873 void SetName(const wxString& name) { m_properties.SetProperty(wxT("name"), name); }
1874
1875 /// Gets the identifying name for this object.
1876 wxString GetName() const { return m_properties.GetPropertyString(wxT("name")); }
1877
1878 /// Is this object top-level, i.e. with its own paragraphs, such as a text box?
1879 virtual bool IsTopLevel() const { return false; }
1880
1881 /// Returns @true if the object will be shown, @false otherwise.
1882 bool IsShown() const { return m_show; }
1883
1884 // Operations
1885
1886 /// Call to show or hide this object. This function does not cause the content to be
1887 /// laid out or redrawn.
1888 virtual void Show(bool show) { m_show = show; }
1889
1890 /// Clone the object
1891 virtual wxRichTextObject* Clone() const { return NULL; }
1892
1893 /// Copy
1894 void Copy(const wxRichTextObject& obj);
1895
1896 /// Reference-counting allows us to use the same object in multiple
1897 /// lists (not yet used)
1898 void Reference() { m_refCount ++; }
1899 void Dereference();
1900
1901 /// Move the object recursively, by adding the offset from old to new
1902 virtual void Move(const wxPoint& pt);
1903
1904 /// Convert units in tenths of a millimetre to device units
1905 int ConvertTenthsMMToPixels(wxDC& dc, int units) const;
1906 static int ConvertTenthsMMToPixels(int ppi, int units, double scale = 1.0);
1907
1908 /// Convert units in pixels to tenths of a millimetre
1909 int ConvertPixelsToTenthsMM(wxDC& dc, int pixels) const;
1910 static int ConvertPixelsToTenthsMM(int ppi, int pixels, double scale = 1.0);
1911
1912 /// Draw the borders and background for the given rectangle and attributes.
1913 /// Width and height are taken to be the outer margin size, not the content.
1914 static bool DrawBoxAttributes(wxDC& dc, wxRichTextBuffer* buffer, const wxRichTextAttr& attr, const wxRect& boxRect, int flags = 0);
1915
1916 /// Draw a border
1917 static bool DrawBorder(wxDC& dc, wxRichTextBuffer* buffer, const wxTextAttrBorders& attr, const wxRect& rect, int flags = 0);
1918
1919 /// Get the various rectangles of the box model in pixels. You can either specify contentRect (inner)
1920 /// or marginRect (outer), and the other must be the default rectangle (no width or height).
1921 /// Note that the outline doesn't affect the position of the rectangle, it's drawn in whatever space
1922 /// is available.
1923 static bool GetBoxRects(wxDC& dc, wxRichTextBuffer* buffer, const wxRichTextAttr& attr, wxRect& marginRect, wxRect& borderRect, wxRect& contentRect, wxRect& paddingRect, wxRect& outlineRect);
1924
1925 /// Get the total margin for the object in pixels, taking into account margin, padding and border size
1926 static bool GetTotalMargin(wxDC& dc, wxRichTextBuffer* buffer, const wxRichTextAttr& attr, int& leftMargin, int& rightMargin,
1927 int& topMargin, int& bottomMargin);
1928
1929 /// Returns the rectangle which the child has available to it given restrictions specified in the
1930 /// child attribute, e.g. 50% width of the parent, 400 pixels, x position 20% of the parent, etc.
1931 static wxRect AdjustAvailableSpace(wxDC& dc, wxRichTextBuffer* buffer, const wxRichTextAttr& parentAttr, const wxRichTextAttr& childAttr, const wxRect& availableParentSpace);
1932
1933 protected:
1934 wxSize m_size;
1935 wxSize m_maxSize;
1936 wxSize m_minSize;
1937 wxPoint m_pos;
1938 int m_descent; // Descent for this object (if any)
1939 int m_refCount;
1940 bool m_show;
1941 wxRichTextObject* m_parent;
1942
1943 /// The range of this object (start position to end position)
1944 wxRichTextRange m_range;
1945
1946 /// The internal range of this object, if it's a top-level object with its own range space
1947 wxRichTextRange m_ownRange;
1948
1949 /// Attributes
1950 wxRichTextAttr m_attributes;
1951
1952 /// Properties
1953 wxRichTextProperties m_properties;
1954 };
1955
1956 WX_DECLARE_LIST_WITH_DECL( wxRichTextObject, wxRichTextObjectList, class WXDLLIMPEXP_RICHTEXT );
1957
1958 /*!
1959 * wxRichTextCompositeObject class declaration
1960 * Objects of this class can contain other objects.
1961 */
1962
1963 class WXDLLIMPEXP_RICHTEXT wxRichTextCompositeObject: public wxRichTextObject
1964 {
1965 DECLARE_CLASS(wxRichTextCompositeObject)
1966 public:
1967 // Constructors
1968
1969 wxRichTextCompositeObject(wxRichTextObject* parent = NULL);
1970 virtual ~wxRichTextCompositeObject();
1971
1972 // Overrideables
1973
1974 /// Hit-testing: returns a flag indicating hit test details, plus
1975 /// information about position
1976 virtual int HitTest(wxDC& dc, const wxPoint& pt, long& textPosition, wxRichTextObject** obj, wxRichTextObject** contextObj, int flags = 0);
1977
1978 /// Finds the absolute position and row height for the given character position
1979 virtual bool FindPosition(wxDC& dc, long index, wxPoint& pt, int* height, bool forceLineStart);
1980
1981 /// Calculate range
1982 virtual void CalculateRange(long start, long& end);
1983
1984 /// Delete range
1985 virtual bool DeleteRange(const wxRichTextRange& range);
1986
1987 /// Get any text in this object for the given range
1988 virtual wxString GetTextForRange(const wxRichTextRange& range) const;
1989
1990 /// Gets the object size for the given range. Returns false if the range
1991 /// is invalid for this object.
1992 virtual bool GetRangeSize(const wxRichTextRange& range, wxSize& size, int& descent, wxDC& dc, int flags, wxPoint position = wxPoint(0,0), wxArrayInt* partialExtents = NULL) const;
1993
1994 /// Dump to output stream for debugging
1995 virtual void Dump(wxTextOutputStream& stream);
1996
1997 /// Invalidate the buffer. With no argument, invalidates whole buffer.
1998 virtual void Invalidate(const wxRichTextRange& invalidRange = wxRICHTEXT_ALL);
1999
2000 // Accessors
2001
2002 /// Get the children
2003 wxRichTextObjectList& GetChildren() { return m_children; }
2004 const wxRichTextObjectList& GetChildren() const { return m_children; }
2005
2006 /// Get the child count
2007 size_t GetChildCount() const ;
2008
2009 /// Get the nth child
2010 wxRichTextObject* GetChild(size_t n) const ;
2011
2012 /// Is this composite?
2013 virtual bool IsComposite() const { return true; }
2014
2015 /// Returns true if the buffer is empty
2016 virtual bool IsEmpty() const { return GetChildCount() == 0; }
2017
2018 /// Get the child object at the given character position
2019 virtual wxRichTextObject* GetChildAtPosition(long pos) const;
2020
2021 // Operations
2022
2023 /// Copy
2024 void Copy(const wxRichTextCompositeObject& obj);
2025
2026 /// Assignment
2027 void operator= (const wxRichTextCompositeObject& obj) { Copy(obj); }
2028
2029 /// Append a child, returning the position
2030 size_t AppendChild(wxRichTextObject* child) ;
2031
2032 /// Insert the child in front of the given object, or at the beginning
2033 bool InsertChild(wxRichTextObject* child, wxRichTextObject* inFrontOf) ;
2034
2035 /// Delete the child
2036 bool RemoveChild(wxRichTextObject* child, bool deleteChild = false) ;
2037
2038 /// Delete all children
2039 bool DeleteChildren() ;
2040
2041 /// Recursively merge all pieces that can be merged.
2042 bool Defragment(const wxRichTextRange& range = wxRICHTEXT_ALL);
2043
2044 /// Move the object recursively, by adding the offset from old to new
2045 virtual void Move(const wxPoint& pt);
2046
2047 protected:
2048 wxRichTextObjectList m_children;
2049 };
2050
2051 /*!
2052 * wxRichTextParagraphBox class declaration
2053 * This box knows how to lay out paragraphs.
2054 */
2055
2056 class WXDLLIMPEXP_RICHTEXT wxRichTextParagraphLayoutBox: public wxRichTextCompositeObject
2057 {
2058 DECLARE_DYNAMIC_CLASS(wxRichTextParagraphLayoutBox)
2059 public:
2060 // Constructors
2061
2062 wxRichTextParagraphLayoutBox(wxRichTextObject* parent = NULL);
2063 wxRichTextParagraphLayoutBox(const wxRichTextParagraphLayoutBox& obj): wxRichTextCompositeObject() { Init(); Copy(obj); }
2064 ~wxRichTextParagraphLayoutBox();
2065
2066 // Overrideables
2067
2068 /// Hit-testing: returns a flag indicating hit test details, plus
2069 /// information about position
2070 virtual int HitTest(wxDC& dc, const wxPoint& pt, long& textPosition, wxRichTextObject** obj, wxRichTextObject** contextObj, int flags = 0);
2071
2072 /// Draw the item
2073 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
2074
2075 /// Lay the item out
2076 virtual bool Layout(wxDC& dc, const wxRect& rect, int style);
2077
2078 /// Gets the object size for the given range. Returns false if the range
2079 /// is invalid for this object.
2080 virtual bool GetRangeSize(const wxRichTextRange& range, wxSize& size, int& descent, wxDC& dc, int flags, wxPoint position = wxPoint(0,0), wxArrayInt* partialExtents = NULL) const;
2081
2082 /// Delete range
2083 virtual bool DeleteRange(const wxRichTextRange& range);
2084
2085 /// Get any text in this object for the given range
2086 virtual wxString GetTextForRange(const wxRichTextRange& range) const;
2087
2088 #if wxUSE_XML
2089 /// Import this object from XML
2090 virtual bool ImportFromXML(wxRichTextBuffer* buffer, wxXmlNode* node, wxRichTextXMLHandler* handler, bool* recurse);
2091 #endif
2092
2093 #if wxRICHTEXT_HAVE_DIRECT_OUTPUT
2094 /// Export this object directly to the given stream.
2095 virtual bool ExportXML(wxOutputStream& stream, int indent, wxRichTextXMLHandler* handler);
2096 #endif
2097
2098 #if wxRICHTEXT_HAVE_XMLDOCUMENT_OUTPUT
2099 /// Export this object to the given parent node, usually creating at least one child node.
2100 virtual bool ExportXML(wxXmlNode* parent, wxRichTextXMLHandler* handler);
2101 #endif
2102
2103 /// What is the XML node name of this object?
2104 virtual wxString GetXMLNodeName() const { return wxT("paragraphlayout"); }
2105
2106 /// Returns true if objects of this class can accept the focus, i.e. a call to SetFocusObject
2107 /// is possible. For example, containers supporting text, such as a text box object, can accept the focus,
2108 /// but a table can't (set the focus to individual cells instead).
2109 virtual bool AcceptsFocus() const { return true; }
2110
2111 // Accessors
2112
2113 /// Associate a control with the buffer, for operations that for example require refreshing the window.
2114 void SetRichTextCtrl(wxRichTextCtrl* ctrl) { m_ctrl = ctrl; }
2115
2116 /// Get the associated control.
2117 wxRichTextCtrl* GetRichTextCtrl() const { return m_ctrl; }
2118
2119 /// Get/set whether the last paragraph is partial or complete
2120 void SetPartialParagraph(bool partialPara) { m_partialParagraph = partialPara; }
2121 bool GetPartialParagraph() const { return m_partialParagraph; }
2122
2123 /// Returns the style sheet associated with the overall buffer.
2124 virtual wxRichTextStyleSheet* GetStyleSheet() const;
2125
2126 /// Is this object top-level, i.e. with its own paragraphs, such as a text box?
2127 virtual bool IsTopLevel() const { return true; }
2128
2129 // Operations
2130
2131 /// Submit command to insert paragraphs
2132 bool InsertParagraphsWithUndo(long pos, const wxRichTextParagraphLayoutBox& paragraphs, wxRichTextCtrl* ctrl, wxRichTextBuffer* buffer, int flags = 0);
2133
2134 /// Submit command to insert the given text
2135 bool InsertTextWithUndo(long pos, const wxString& text, wxRichTextCtrl* ctrl, wxRichTextBuffer* buffer, int flags = 0);
2136
2137 /// Submit command to insert the given text
2138 bool InsertNewlineWithUndo(long pos, wxRichTextCtrl* ctrl, wxRichTextBuffer* buffer, int flags = 0);
2139
2140 /// Submit command to insert the given image
2141 bool InsertImageWithUndo(long pos, const wxRichTextImageBlock& imageBlock,
2142 wxRichTextCtrl* ctrl, wxRichTextBuffer* buffer, int flags,
2143 const wxRichTextAttr& textAttr);
2144
2145 /// Get the style that is appropriate for a new paragraph at this position.
2146 /// If the previous paragraph has a paragraph style name, look up the next-paragraph
2147 /// style.
2148 wxRichTextAttr GetStyleForNewParagraph(wxRichTextBuffer* buffer, long pos, bool caretPosition = false, bool lookUpNewParaStyle=false) const;
2149
2150 /// Insert an object.
2151 wxRichTextObject* InsertObjectWithUndo(long pos, wxRichTextObject *object, wxRichTextCtrl* ctrl, wxRichTextBuffer* buffer, int flags = 0);
2152
2153 /// Submit command to delete this range
2154 bool DeleteRangeWithUndo(const wxRichTextRange& range, wxRichTextCtrl* ctrl, wxRichTextBuffer* buffer);
2155
2156 /// Draw the floats of this buffer
2157 void DrawFloats(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
2158
2159 /// Move an anchored object to another paragraph
2160 void MoveAnchoredObjectToParagraph(wxRichTextParagraph* from, wxRichTextParagraph* to, wxRichTextObject* obj);
2161
2162 /// Initialize the object.
2163 void Init();
2164
2165 /// Clear all children
2166 virtual void Clear();
2167
2168 /// Clear and initialize with one blank paragraph
2169 virtual void Reset();
2170
2171 /// Convenience function to add a paragraph of text
2172 virtual wxRichTextRange AddParagraph(const wxString& text, wxRichTextAttr* paraStyle = NULL);
2173
2174 /// Convenience function to add an image
2175 virtual wxRichTextRange AddImage(const wxImage& image, wxRichTextAttr* paraStyle = NULL);
2176
2177 /// Adds multiple paragraphs, based on newlines.
2178 virtual wxRichTextRange AddParagraphs(const wxString& text, wxRichTextAttr* paraStyle = NULL);
2179
2180 /// Get the line at the given position. If caretPosition is true, the position is
2181 /// a caret position, which is normally a smaller number.
2182 virtual wxRichTextLine* GetLineAtPosition(long pos, bool caretPosition = false) const;
2183
2184 /// Get the line at the given y pixel position, or the last line.
2185 virtual wxRichTextLine* GetLineAtYPosition(int y) const;
2186
2187 /// Get the paragraph at the given character or caret position
2188 virtual wxRichTextParagraph* GetParagraphAtPosition(long pos, bool caretPosition = false) const;
2189
2190 /// Get the line size at the given position
2191 virtual wxSize GetLineSizeAtPosition(long pos, bool caretPosition = false) const;
2192
2193 /// Given a position, get the number of the visible line (potentially many to a paragraph),
2194 /// starting from zero at the start of the buffer. We also have to pass a bool (startOfLine)
2195 /// that indicates whether the caret is being shown at the end of the previous line or at the start
2196 /// of the next, since the caret can be shown at 2 visible positions for the same underlying
2197 /// position.
2198 virtual long GetVisibleLineNumber(long pos, bool caretPosition = false, bool startOfLine = false) const;
2199
2200 /// Given a line number, get the corresponding wxRichTextLine object.
2201 virtual wxRichTextLine* GetLineForVisibleLineNumber(long lineNumber) const;
2202
2203 /// Get the leaf object in a paragraph at this position.
2204 /// Given a position, get the corresponding wxRichTextLine object.
2205 virtual wxRichTextObject* GetLeafObjectAtPosition(long position) const;
2206
2207 /// Get the paragraph by number
2208 virtual wxRichTextParagraph* GetParagraphAtLine(long paragraphNumber) const;
2209
2210 /// Get the paragraph for a given line
2211 virtual wxRichTextParagraph* GetParagraphForLine(wxRichTextLine* line) const;
2212
2213 /// Get the length of the paragraph
2214 virtual int GetParagraphLength(long paragraphNumber) const;
2215
2216 /// Get the number of paragraphs
2217 virtual int GetParagraphCount() const { return static_cast<int>(GetChildCount()); }
2218
2219 /// Get the number of visible lines
2220 virtual int GetLineCount() const;
2221
2222 /// Get the text of the paragraph
2223 virtual wxString GetParagraphText(long paragraphNumber) const;
2224
2225 /// Convert zero-based line column and paragraph number to a position.
2226 virtual long XYToPosition(long x, long y) const;
2227
2228 /// Convert zero-based position to line column and paragraph number
2229 virtual bool PositionToXY(long pos, long* x, long* y) const;
2230
2231 /// Set text attributes: character and/or paragraph styles.
2232 virtual bool SetStyle(const wxRichTextRange& range, const wxRichTextAttr& style, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO);
2233
2234 /// Set the attributes for the given object only, for example the box attributes for a text box.
2235 virtual void SetStyle(wxRichTextObject *obj, const wxRichTextAttr& textAttr, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO);
2236
2237 /// Get the combined text attributes for this position.
2238 virtual bool GetStyle(long position, wxRichTextAttr& style);
2239
2240 /// Get the content (uncombined) attributes for this position.
2241 virtual bool GetUncombinedStyle(long position, wxRichTextAttr& style);
2242
2243 /// Implementation helper for GetStyle. If combineStyles is true, combine base, paragraph and
2244 /// context attributes.
2245 virtual bool DoGetStyle(long position, wxRichTextAttr& style, bool combineStyles = true);
2246
2247 /// Get the combined style for a range - if any attribute is different within the range,
2248 /// that attribute is not present within the flags
2249 virtual bool GetStyleForRange(const wxRichTextRange& range, wxRichTextAttr& style);
2250
2251 /// Combines 'style' with 'currentStyle' for the purpose of summarising the attributes of a range of
2252 /// content.
2253 bool CollectStyle(wxRichTextAttr& currentStyle, const wxRichTextAttr& style, wxRichTextAttr& clashingAttr, wxRichTextAttr& absentAttr);
2254
2255 /// Set list style
2256 virtual bool SetListStyle(const wxRichTextRange& range, wxRichTextListStyleDefinition* def, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO, int startFrom = 1, int specifiedLevel = -1);
2257 virtual bool SetListStyle(const wxRichTextRange& range, const wxString& defName, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO, int startFrom = 1, int specifiedLevel = -1);
2258
2259 /// Clear list for given range
2260 virtual bool ClearListStyle(const wxRichTextRange& range, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO);
2261
2262 /// Number/renumber any list elements in the given range.
2263 /// def/defName can be NULL/empty to indicate that the existing list style should be used.
2264 virtual bool NumberList(const wxRichTextRange& range, wxRichTextListStyleDefinition* def = NULL, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO, int startFrom = 1, int specifiedLevel = -1);
2265 virtual bool NumberList(const wxRichTextRange& range, const wxString& defName, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO, int startFrom = 1, int specifiedLevel = -1);
2266
2267 /// Promote the list items within the given range. promoteBy can be a positive or negative number, e.g. 1 or -1
2268 /// def/defName can be NULL/empty to indicate that the existing list style should be used.
2269 virtual bool PromoteList(int promoteBy, const wxRichTextRange& range, wxRichTextListStyleDefinition* def = NULL, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO, int specifiedLevel = -1);
2270 virtual bool PromoteList(int promoteBy, const wxRichTextRange& range, const wxString& defName, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO, int specifiedLevel = -1);
2271
2272 /// Helper for NumberList and PromoteList, that does renumbering and promotion simultaneously
2273 /// def/defName can be NULL/empty to indicate that the existing list style should be used.
2274 virtual bool DoNumberList(const wxRichTextRange& range, const wxRichTextRange& promotionRange, int promoteBy, wxRichTextListStyleDefinition* def, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO, int startFrom = 1, int specifiedLevel = -1);
2275
2276 /// Fills in the attributes for numbering a paragraph after previousParagraph.
2277 virtual bool FindNextParagraphNumber(wxRichTextParagraph* previousParagraph, wxRichTextAttr& attr) const;
2278
2279 /// Test if this whole range has character attributes of the specified kind. If any
2280 /// of the attributes are different within the range, the test fails. You
2281 /// can use this to implement, for example, bold button updating. style must have
2282 /// flags indicating which attributes are of interest.
2283 virtual bool HasCharacterAttributes(const wxRichTextRange& range, const wxRichTextAttr& style) const;
2284
2285 /// Test if this whole range has paragraph attributes of the specified kind. If any
2286 /// of the attributes are different within the range, the test fails. You
2287 /// can use this to implement, for example, centering button updating. style must have
2288 /// flags indicating which attributes are of interest.
2289 virtual bool HasParagraphAttributes(const wxRichTextRange& range, const wxRichTextAttr& style) const;
2290
2291 /// Clone
2292 virtual wxRichTextObject* Clone() const { return new wxRichTextParagraphLayoutBox(*this); }
2293
2294 /// Insert fragment into this box at the given position. If partialParagraph is true,
2295 /// it is assumed that the last (or only) paragraph is just a piece of data with no paragraph
2296 /// marker.
2297 virtual bool InsertFragment(long position, wxRichTextParagraphLayoutBox& fragment);
2298
2299 /// Make a copy of the fragment corresponding to the given range, putting it in 'fragment'.
2300 virtual bool CopyFragment(const wxRichTextRange& range, wxRichTextParagraphLayoutBox& fragment);
2301
2302 /// Apply the style sheet to the buffer, for example if the styles have changed.
2303 virtual bool ApplyStyleSheet(wxRichTextStyleSheet* styleSheet);
2304
2305 /// Copy
2306 void Copy(const wxRichTextParagraphLayoutBox& obj);
2307
2308 /// Assignment
2309 void operator= (const wxRichTextParagraphLayoutBox& obj) { Copy(obj); }
2310
2311 /// Calculate ranges
2312 virtual void UpdateRanges();
2313
2314 /// Get all the text
2315 virtual wxString GetText() const;
2316
2317 /// Set default style for new content. Setting it to a default attribute
2318 /// makes new content take on the 'basic' style.
2319 virtual bool SetDefaultStyle(const wxRichTextAttr& style);
2320
2321 /// Get default style
2322 virtual const wxRichTextAttr& GetDefaultStyle() const { return m_defaultAttributes; }
2323
2324 /// Set basic (overall) style
2325 virtual void SetBasicStyle(const wxRichTextAttr& style) { m_attributes = style; }
2326
2327 /// Get basic (overall) style
2328 virtual const wxRichTextAttr& GetBasicStyle() const { return m_attributes; }
2329
2330 /// Invalidate the buffer. With no argument, invalidates whole buffer.
2331 virtual void Invalidate(const wxRichTextRange& invalidRange = wxRICHTEXT_ALL);
2332
2333 /// Do the (in)validation for this object only
2334 virtual void DoInvalidate(const wxRichTextRange& invalidRange);
2335
2336 /// Do the (in)validation both up and down the hierarchy
2337 virtual void InvalidateHierarchy(const wxRichTextRange& invalidRange = wxRICHTEXT_ALL);
2338
2339 /// Gather information about floating objects. If untilObj is non-NULL,
2340 /// will stop getting information if the current object is this, since we
2341 /// will collect the rest later.
2342 virtual bool UpdateFloatingObjects(const wxRect& availableRect, wxRichTextObject* untilObj = NULL);
2343
2344 /// Get invalid range, rounding to entire paragraphs if argument is true.
2345 wxRichTextRange GetInvalidRange(bool wholeParagraphs = false) const;
2346
2347 /// Does this object need layout?
2348 bool IsDirty() const { return m_invalidRange != wxRICHTEXT_NONE; }
2349
2350 /// Get the wxRichTextFloatCollector of this object
2351 wxRichTextFloatCollector* GetFloatCollector() { return m_floatCollector; }
2352
2353 /// Get the number of floating objects at this level
2354 int GetFloatingObjectCount() const;
2355
2356 /// Get a list of floating objects
2357 bool GetFloatingObjects(wxRichTextObjectList& objects) const;
2358
2359 protected:
2360 wxRichTextCtrl* m_ctrl;
2361 wxRichTextAttr m_defaultAttributes;
2362
2363 /// The invalidated range that will need full layout
2364 wxRichTextRange m_invalidRange;
2365
2366 // Is the last paragraph partial or complete?
2367 bool m_partialParagraph;
2368
2369 // The floating layout state
2370 wxRichTextFloatCollector* m_floatCollector;
2371 };
2372
2373 /**
2374 @class wxRichTextBox
2375
2376 wxRichTextBox is a floating or inline text box, containing paragraphs.
2377 */
2378
2379 class WXDLLIMPEXP_RICHTEXT wxRichTextBox: public wxRichTextParagraphLayoutBox
2380 {
2381 DECLARE_DYNAMIC_CLASS(wxRichTextBox)
2382 public:
2383 // Constructors
2384
2385 /**
2386 Default constructor; optionally pass the parent object.
2387 */
2388
2389 wxRichTextBox(wxRichTextObject* parent = NULL);
2390
2391 /**
2392 Copy constructor.
2393 */
2394
2395 wxRichTextBox(const wxRichTextBox& obj): wxRichTextParagraphLayoutBox() { Copy(obj); }
2396
2397 // Overrideables
2398
2399 /**
2400 Draws the item.
2401 */
2402
2403 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
2404
2405 /**
2406 Returns the XML node name of this object.
2407 */
2408
2409 virtual wxString GetXMLNodeName() const { return wxT("textbox"); }
2410
2411 /// Can we edit properties via a GUI?
2412 virtual bool CanEditProperties() const { return true; }
2413
2414 /// Edit properties via a GUI
2415 virtual bool EditProperties(wxWindow* parent, wxRichTextBuffer* buffer);
2416
2417 /// Return the label to be used for the properties context menu item.
2418 virtual wxString GetPropertiesMenuLabel() const { return _("&Box"); }
2419
2420 // Accessors
2421
2422 // Operations
2423
2424 /**
2425 Makes a clone of this object.
2426 */
2427 virtual wxRichTextObject* Clone() const { return new wxRichTextBox(*this); }
2428
2429 /**
2430 Copies this object.
2431 */
2432 void Copy(const wxRichTextBox& obj);
2433
2434 protected:
2435 };
2436
2437 /*!
2438 * wxRichTextLine class declaration
2439 * This object represents a line in a paragraph, and stores
2440 * offsets from the start of the paragraph representing the
2441 * start and end positions of the line.
2442 */
2443
2444 class WXDLLIMPEXP_RICHTEXT wxRichTextLine
2445 {
2446 public:
2447 // Constructors
2448
2449 wxRichTextLine(wxRichTextParagraph* parent);
2450 wxRichTextLine(const wxRichTextLine& obj) { Init( NULL); Copy(obj); }
2451 virtual ~wxRichTextLine() {}
2452
2453 // Overrideables
2454
2455 // Accessors
2456
2457 /// Set the range
2458 void SetRange(const wxRichTextRange& range) { m_range = range; }
2459 void SetRange(long from, long to) { m_range = wxRichTextRange(from, to); }
2460
2461 /// Get the parent paragraph
2462 wxRichTextParagraph* GetParent() { return m_parent; }
2463
2464 /// Get the range
2465 const wxRichTextRange& GetRange() const { return m_range; }
2466 wxRichTextRange& GetRange() { return m_range; }
2467
2468 /// Get the absolute range
2469 wxRichTextRange GetAbsoluteRange() const;
2470
2471 /// Get/set the line size as calculated by Layout.
2472 virtual wxSize GetSize() const { return m_size; }
2473 virtual void SetSize(const wxSize& sz) { m_size = sz; }
2474
2475 /// Get/set the object position relative to the parent
2476 virtual wxPoint GetPosition() const { return m_pos; }
2477 virtual void SetPosition(const wxPoint& pos) { m_pos = pos; }
2478
2479 /// Get the absolute object position
2480 virtual wxPoint GetAbsolutePosition() const;
2481
2482 /// Get the rectangle enclosing the line
2483 virtual wxRect GetRect() const { return wxRect(GetAbsolutePosition(), GetSize()); }
2484
2485 /// Set/get stored descent
2486 void SetDescent(int descent) { m_descent = descent; }
2487 int GetDescent() const { return m_descent; }
2488
2489 #if wxRICHTEXT_USE_OPTIMIZED_LINE_DRAWING
2490 wxArrayInt& GetObjectSizes() { return m_objectSizes; }
2491 const wxArrayInt& GetObjectSizes() const { return m_objectSizes; }
2492 #endif
2493
2494 // Operations
2495
2496 /// Initialisation
2497 void Init(wxRichTextParagraph* parent);
2498
2499 /// Copy
2500 void Copy(const wxRichTextLine& obj);
2501
2502 /// Clone
2503 virtual wxRichTextLine* Clone() const { return new wxRichTextLine(*this); }
2504
2505 protected:
2506
2507 /// The range of the line (start position to end position)
2508 /// This is relative to the parent paragraph.
2509 wxRichTextRange m_range;
2510
2511 /// Size and position measured relative to top of paragraph
2512 wxPoint m_pos;
2513 wxSize m_size;
2514
2515 /// Maximum descent for this line (location of text baseline)
2516 int m_descent;
2517
2518 // The parent object
2519 wxRichTextParagraph* m_parent;
2520
2521 #if wxRICHTEXT_USE_OPTIMIZED_LINE_DRAWING
2522 wxArrayInt m_objectSizes;
2523 #endif
2524 };
2525
2526 WX_DECLARE_LIST_WITH_DECL( wxRichTextLine, wxRichTextLineList , class WXDLLIMPEXP_RICHTEXT );
2527
2528 /*!
2529 * wxRichTextParagraph class declaration
2530 * This object represents a single paragraph (or in a straight text editor, a line).
2531 */
2532
2533 class WXDLLIMPEXP_RICHTEXT wxRichTextParagraph: public wxRichTextCompositeObject
2534 {
2535 DECLARE_DYNAMIC_CLASS(wxRichTextParagraph)
2536 public:
2537 // Constructors
2538
2539 wxRichTextParagraph(wxRichTextObject* parent = NULL, wxRichTextAttr* style = NULL);
2540 wxRichTextParagraph(const wxString& text, wxRichTextObject* parent = NULL, wxRichTextAttr* paraStyle = NULL, wxRichTextAttr* charStyle = NULL);
2541 virtual ~wxRichTextParagraph();
2542 wxRichTextParagraph(const wxRichTextParagraph& obj): wxRichTextCompositeObject() { Copy(obj); }
2543
2544 // Overrideables
2545
2546 /// Draw the item
2547 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
2548
2549 /// Lay the item out
2550 virtual bool Layout(wxDC& dc, const wxRect& rect, int style);
2551
2552 /// Gets the object size for the given range. Returns false if the range
2553 /// is invalid for this object.
2554 virtual bool GetRangeSize(const wxRichTextRange& range, wxSize& size, int& descent, wxDC& dc, int flags, wxPoint position = wxPoint(0,0), wxArrayInt* partialExtents = NULL) const;
2555
2556 /// Finds the absolute position and row height for the given character position
2557 virtual bool FindPosition(wxDC& dc, long index, wxPoint& pt, int* height, bool forceLineStart);
2558
2559 /// Hit-testing: returns a flag indicating hit test details, plus
2560 /// information about position and the object that was found.
2561 virtual int HitTest(wxDC& dc, const wxPoint& pt, long& textPosition, wxRichTextObject** obj, wxRichTextObject** contextObj, int flags = 0);
2562
2563 /// Calculate range
2564 virtual void CalculateRange(long start, long& end);
2565
2566 /// What is the XML node name of this object?
2567 virtual wxString GetXMLNodeName() const { return wxT("paragraph"); }
2568
2569 // Accessors
2570
2571 /// Get the cached lines
2572 wxRichTextLineList& GetLines() { return m_cachedLines; }
2573
2574 // Operations
2575
2576 /// Copy
2577 void Copy(const wxRichTextParagraph& obj);
2578
2579 /// Clone
2580 virtual wxRichTextObject* Clone() const { return new wxRichTextParagraph(*this); }
2581
2582 /// Clear the cached lines
2583 void ClearLines();
2584
2585 // Implementation
2586
2587 /// Apply paragraph styles such as centering to the wrapped lines
2588 virtual void ApplyParagraphStyle(wxRichTextLine* line, const wxRichTextAttr& attr, const wxRect& rect, wxDC& dc);
2589
2590 /// Insert text at the given position
2591 virtual bool InsertText(long pos, const wxString& text);
2592
2593 /// Split an object at this position if necessary, and return
2594 /// the previous object, or NULL if inserting at beginning.
2595 virtual wxRichTextObject* SplitAt(long pos, wxRichTextObject** previousObject = NULL);
2596
2597 /// Move content to a list from this point
2598 virtual void MoveToList(wxRichTextObject* obj, wxList& list);
2599
2600 /// Add content back from list
2601 virtual void MoveFromList(wxList& list);
2602
2603 /// Get the plain text searching from the start or end of the range.
2604 /// The resulting string may be shorter than the range given.
2605 bool GetContiguousPlainText(wxString& text, const wxRichTextRange& range, bool fromStart = true);
2606
2607 /// Find a suitable wrap position. wrapPosition is the last position in the line to the left
2608 /// of the split.
2609 bool FindWrapPosition(const wxRichTextRange& range, wxDC& dc, int availableSpace, long& wrapPosition, wxArrayInt* partialExtents);
2610
2611 /// Find the object at the given position
2612 wxRichTextObject* FindObjectAtPosition(long position);
2613
2614 /// Get the bullet text for this paragraph.
2615 wxString GetBulletText();
2616
2617 /// Allocate or reuse a line object
2618 wxRichTextLine* AllocateLine(int pos);
2619
2620 /// Clear remaining unused line objects, if any
2621 bool ClearUnusedLines(int lineCount);
2622
2623 /// Get combined attributes of the base style, paragraph style and character style. We use this to dynamically
2624 /// retrieve the actual style.
2625 wxRichTextAttr GetCombinedAttributes(const wxRichTextAttr& contentStyle, bool includingBoxAttr = false) const;
2626
2627 /// Get combined attributes of the base style and paragraph style.
2628 wxRichTextAttr GetCombinedAttributes(bool includingBoxAttr = false) const;
2629
2630 /// Get the first position from pos that has a line break character.
2631 long GetFirstLineBreakPosition(long pos);
2632
2633 /// Create default tabstop array
2634 static void InitDefaultTabs();
2635
2636 /// Clear default tabstop array
2637 static void ClearDefaultTabs();
2638
2639 /// Get default tabstop array
2640 static const wxArrayInt& GetDefaultTabs() { return sm_defaultTabs; }
2641
2642 /// Layout the floats object
2643 void LayoutFloat(wxDC& dc, const wxRect& rect, int style, wxRichTextFloatCollector* floatCollector);
2644
2645 protected:
2646 /// The lines that make up the wrapped paragraph
2647 wxRichTextLineList m_cachedLines;
2648
2649 /// Default tabstops
2650 static wxArrayInt sm_defaultTabs;
2651
2652 friend class wxRichTextFloatCollector;
2653 };
2654
2655 /*!
2656 * wxRichTextPlainText class declaration
2657 * This object represents a single piece of text.
2658 */
2659
2660 class WXDLLIMPEXP_RICHTEXT wxRichTextPlainText: public wxRichTextObject
2661 {
2662 DECLARE_DYNAMIC_CLASS(wxRichTextPlainText)
2663 public:
2664 // Constructors
2665
2666 wxRichTextPlainText(const wxString& text = wxEmptyString, wxRichTextObject* parent = NULL, wxRichTextAttr* style = NULL);
2667 wxRichTextPlainText(const wxRichTextPlainText& obj): wxRichTextObject() { Copy(obj); }
2668
2669 // Overrideables
2670
2671 /// Draw the item
2672 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
2673
2674 /// Lay the item out
2675 virtual bool Layout(wxDC& dc, const wxRect& rect, int style);
2676
2677 /// Gets the object size for the given range. Returns false if the range
2678 /// is invalid for this object.
2679 virtual bool GetRangeSize(const wxRichTextRange& range, wxSize& size, int& descent, wxDC& dc, int flags, wxPoint position = wxPoint(0,0), wxArrayInt* partialExtents = NULL) const;
2680
2681 /// Get any text in this object for the given range
2682 virtual wxString GetTextForRange(const wxRichTextRange& range) const;
2683
2684 /// Do a split, returning an object containing the second part, and setting
2685 /// the first part in 'this'.
2686 virtual wxRichTextObject* DoSplit(long pos);
2687
2688 /// Calculate range
2689 virtual void CalculateRange(long start, long& end);
2690
2691 /// Delete range
2692 virtual bool DeleteRange(const wxRichTextRange& range);
2693
2694 /// Returns true if the object is empty
2695 virtual bool IsEmpty() const { return m_text.empty(); }
2696
2697 /// Returns true if this object can merge itself with the given one.
2698 virtual bool CanMerge(wxRichTextObject* object) const;
2699
2700 /// Returns true if this object merged itself with the given one.
2701 /// The calling code will then delete the given object.
2702 virtual bool Merge(wxRichTextObject* object);
2703
2704 /// Dump to output stream for debugging
2705 virtual void Dump(wxTextOutputStream& stream);
2706
2707 /// Get the first position from pos that has a line break character.
2708 long GetFirstLineBreakPosition(long pos);
2709
2710 /// Does this object take note of paragraph attributes? Text and image objects don't.
2711 virtual bool UsesParagraphAttributes() const { return false; }
2712
2713 #if wxUSE_XML
2714 /// Import this object from XML
2715 virtual bool ImportFromXML(wxRichTextBuffer* buffer, wxXmlNode* node, wxRichTextXMLHandler* handler, bool* recurse);
2716 #endif
2717
2718 #if wxRICHTEXT_HAVE_DIRECT_OUTPUT
2719 /// Export this object directly to the given stream.
2720 virtual bool ExportXML(wxOutputStream& stream, int indent, wxRichTextXMLHandler* handler);
2721 #endif
2722
2723 #if wxRICHTEXT_HAVE_XMLDOCUMENT_OUTPUT
2724 /// Export this object to the given parent node, usually creating at least one child node.
2725 virtual bool ExportXML(wxXmlNode* parent, wxRichTextXMLHandler* handler);
2726 #endif
2727
2728 /// What is the XML node name of this object?
2729 virtual wxString GetXMLNodeName() const { return wxT("text"); }
2730
2731 // Accessors
2732
2733 /// Get the text
2734 const wxString& GetText() const { return m_text; }
2735
2736 /// Set the text
2737 void SetText(const wxString& text) { m_text = text; }
2738
2739 // Operations
2740
2741 /// Copy
2742 void Copy(const wxRichTextPlainText& obj);
2743
2744 /// Clone
2745 virtual wxRichTextObject* Clone() const { return new wxRichTextPlainText(*this); }
2746 private:
2747 bool DrawTabbedString(wxDC& dc, const wxRichTextAttr& attr, const wxRect& rect, wxString& str, wxCoord& x, wxCoord& y, bool selected);
2748
2749 protected:
2750 wxString m_text;
2751 };
2752
2753 /*!
2754 * wxRichTextImageBlock stores information about an image, in binary in-memory form
2755 */
2756
2757 class WXDLLIMPEXP_FWD_BASE wxDataInputStream;
2758 class WXDLLIMPEXP_FWD_BASE wxDataOutputStream;
2759
2760 class WXDLLIMPEXP_RICHTEXT wxRichTextImageBlock: public wxObject
2761 {
2762 public:
2763 wxRichTextImageBlock();
2764 wxRichTextImageBlock(const wxRichTextImageBlock& block);
2765 virtual ~wxRichTextImageBlock();
2766
2767 void Init();
2768 void Clear();
2769
2770 // Load the original image into a memory block.
2771 // If the image is not a JPEG, we must convert it into a JPEG
2772 // to conserve space.
2773 // If it's not a JPEG we can make use of 'image', already scaled, so we don't have to
2774 // load the image a 2nd time.
2775 virtual bool MakeImageBlock(const wxString& filename, wxBitmapType imageType,
2776 wxImage& image, bool convertToJPEG = true);
2777
2778 // Make an image block from the wxImage in the given
2779 // format.
2780 virtual bool MakeImageBlock(wxImage& image, wxBitmapType imageType, int quality = 80);
2781
2782 // Uses a const wxImage for efficiency, but can't set quality (only relevant for JPEG)
2783 virtual bool MakeImageBlockDefaultQuality(const wxImage& image, wxBitmapType imageType);
2784
2785 // Makes the image block
2786 virtual bool DoMakeImageBlock(const wxImage& image, wxBitmapType imageType);
2787
2788 // Write to a file
2789 bool Write(const wxString& filename);
2790
2791 // Write data in hex to a stream
2792 bool WriteHex(wxOutputStream& stream);
2793
2794 // Read data in hex from a stream
2795 bool ReadHex(wxInputStream& stream, int length, wxBitmapType imageType);
2796
2797 // Copy from 'block'
2798 void Copy(const wxRichTextImageBlock& block);
2799
2800 // Load a wxImage from the block
2801 bool Load(wxImage& image);
2802
2803 //// Operators
2804 void operator=(const wxRichTextImageBlock& block);
2805
2806 //// Accessors
2807
2808 unsigned char* GetData() const { return m_data; }
2809 size_t GetDataSize() const { return m_dataSize; }
2810 wxBitmapType GetImageType() const { return m_imageType; }
2811
2812 void SetData(unsigned char* image) { m_data = image; }
2813 void SetDataSize(size_t size) { m_dataSize = size; }
2814 void SetImageType(wxBitmapType imageType) { m_imageType = imageType; }
2815
2816 bool Ok() const { return IsOk(); }
2817 bool IsOk() const { return GetData() != NULL; }
2818
2819 // Gets the extension for the block's type
2820 wxString GetExtension() const;
2821
2822 /// Implementation
2823
2824 // Allocate and read from stream as a block of memory
2825 static unsigned char* ReadBlock(wxInputStream& stream, size_t size);
2826 static unsigned char* ReadBlock(const wxString& filename, size_t size);
2827
2828 // Write memory block to stream
2829 static bool WriteBlock(wxOutputStream& stream, unsigned char* block, size_t size);
2830
2831 // Write memory block to file
2832 static bool WriteBlock(const wxString& filename, unsigned char* block, size_t size);
2833
2834 protected:
2835 // Size in bytes of the image stored.
2836 // This is in the raw, original form such as a JPEG file.
2837 unsigned char* m_data;
2838 size_t m_dataSize;
2839 wxBitmapType m_imageType;
2840 };
2841
2842 /*!
2843 * wxRichTextImage class declaration
2844 * This object represents an image.
2845 */
2846
2847 class WXDLLIMPEXP_RICHTEXT wxRichTextImage: public wxRichTextObject
2848 {
2849 DECLARE_DYNAMIC_CLASS(wxRichTextImage)
2850 public:
2851 // Constructors
2852
2853 wxRichTextImage(wxRichTextObject* parent = NULL): wxRichTextObject(parent) { }
2854 wxRichTextImage(const wxImage& image, wxRichTextObject* parent = NULL, wxRichTextAttr* charStyle = NULL);
2855 wxRichTextImage(const wxRichTextImageBlock& imageBlock, wxRichTextObject* parent = NULL, wxRichTextAttr* charStyle = NULL);
2856 wxRichTextImage(const wxRichTextImage& obj): wxRichTextObject(obj) { Copy(obj); }
2857
2858 // Overrideables
2859
2860 /// Draw the item
2861 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
2862
2863 /// Lay the item out
2864 virtual bool Layout(wxDC& dc, const wxRect& rect, int style);
2865
2866 /// Get the object size for the given range. Returns false if the range
2867 /// is invalid for this object.
2868 virtual bool GetRangeSize(const wxRichTextRange& range, wxSize& size, int& descent, wxDC& dc, int flags, wxPoint position = wxPoint(0,0), wxArrayInt* partialExtents = NULL) const;
2869
2870 /// Get the 'natural' size for an object. For an image, it would be the
2871 /// image size.
2872 virtual wxTextAttrSize GetNaturalSize() const;
2873
2874 /// Returns true if the object is empty. An image is never empty; if the image is broken, that's not the same thing as empty.
2875 virtual bool IsEmpty() const { return false; /* !m_imageBlock.Ok(); */ }
2876
2877 /// Can we edit properties via a GUI?
2878 virtual bool CanEditProperties() const { return true; }
2879
2880 /// Edit properties via a GUI
2881 virtual bool EditProperties(wxWindow* parent, wxRichTextBuffer* buffer);
2882
2883 /// Return the label to be used for the properties context menu item.
2884 virtual wxString GetPropertiesMenuLabel() const { return _("&Picture"); }
2885
2886 /// Does this object take note of paragraph attributes? Text and image objects don't.
2887 virtual bool UsesParagraphAttributes() const { return false; }
2888
2889 #if wxUSE_XML
2890 /// Import this object from XML
2891 virtual bool ImportFromXML(wxRichTextBuffer* buffer, wxXmlNode* node, wxRichTextXMLHandler* handler, bool* recurse);
2892 #endif
2893
2894 #if wxRICHTEXT_HAVE_DIRECT_OUTPUT
2895 /// Export this object directly to the given stream.
2896 virtual bool ExportXML(wxOutputStream& stream, int indent, wxRichTextXMLHandler* handler);
2897 #endif
2898
2899 #if wxRICHTEXT_HAVE_XMLDOCUMENT_OUTPUT
2900 /// Export this object to the given parent node, usually creating at least one child node.
2901 virtual bool ExportXML(wxXmlNode* parent, wxRichTextXMLHandler* handler);
2902 #endif
2903
2904 // Images can be floatable (optionally).
2905 virtual bool IsFloatable() const { return true; }
2906
2907 /// What is the XML node name of this object?
2908 virtual wxString GetXMLNodeName() const { return wxT("image"); }
2909
2910 // Accessors
2911
2912 /// Get the image cache (scaled bitmap)
2913 const wxBitmap& GetImageCache() const { return m_imageCache; }
2914
2915 /// Set the image cache
2916 void SetImageCache(const wxBitmap& bitmap) { m_imageCache = bitmap; }
2917
2918 /// Reset the image cache
2919 void ResetImageCache() { m_imageCache = wxNullBitmap; }
2920
2921 /// Get the image block containing the raw data
2922 wxRichTextImageBlock& GetImageBlock() { return m_imageBlock; }
2923
2924 // Operations
2925
2926 /// Copy
2927 void Copy(const wxRichTextImage& obj);
2928
2929 /// Clone
2930 virtual wxRichTextObject* Clone() const { return new wxRichTextImage(*this); }
2931
2932 /// Create a cached image at the required size
2933 virtual bool LoadImageCache(wxDC& dc, bool resetCache = false);
2934
2935 protected:
2936 wxRichTextImageBlock m_imageBlock;
2937 wxBitmap m_imageCache;
2938 };
2939
2940
2941 /*!
2942 * wxRichTextBuffer class declaration
2943 * This is a kind of box, used to represent the whole buffer
2944 */
2945
2946 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextCommand;
2947 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextAction;
2948
2949 class WXDLLIMPEXP_RICHTEXT wxRichTextBuffer: public wxRichTextParagraphLayoutBox
2950 {
2951 DECLARE_DYNAMIC_CLASS(wxRichTextBuffer)
2952 public:
2953 // Constructors
2954
2955 wxRichTextBuffer() { Init(); }
2956 wxRichTextBuffer(const wxRichTextBuffer& obj): wxRichTextParagraphLayoutBox() { Init(); Copy(obj); }
2957 virtual ~wxRichTextBuffer() ;
2958
2959 // Accessors
2960
2961 /// Gets the command processor
2962 wxCommandProcessor* GetCommandProcessor() const { return m_commandProcessor; }
2963
2964 /// Set style sheet, if any.
2965 void SetStyleSheet(wxRichTextStyleSheet* styleSheet) { m_styleSheet = styleSheet; }
2966 virtual wxRichTextStyleSheet* GetStyleSheet() const { return m_styleSheet; }
2967
2968 /// Set style sheet and notify of the change
2969 bool SetStyleSheetAndNotify(wxRichTextStyleSheet* sheet);
2970
2971 /// Push style sheet to top of stack
2972 bool PushStyleSheet(wxRichTextStyleSheet* styleSheet);
2973
2974 /// Pop style sheet from top of stack
2975 wxRichTextStyleSheet* PopStyleSheet();
2976
2977 /// Set/get table storing fonts
2978 wxRichTextFontTable& GetFontTable() { return m_fontTable; }
2979 const wxRichTextFontTable& GetFontTable() const { return m_fontTable; }
2980 void SetFontTable(const wxRichTextFontTable& table) { m_fontTable = table; }
2981
2982 // Operations
2983
2984 /// Initialisation
2985 void Init();
2986
2987 /// Clears the buffer, adds an empty paragraph, and clears the command processor.
2988 virtual void ResetAndClearCommands();
2989
2990 /// Load a file
2991 virtual bool LoadFile(const wxString& filename, wxRichTextFileType type = wxRICHTEXT_TYPE_ANY);
2992
2993 /// Save a file
2994 virtual bool SaveFile(const wxString& filename, wxRichTextFileType type = wxRICHTEXT_TYPE_ANY);
2995
2996 /// Load from a stream
2997 virtual bool LoadFile(wxInputStream& stream, wxRichTextFileType type = wxRICHTEXT_TYPE_ANY);
2998
2999 /// Save to a stream
3000 virtual bool SaveFile(wxOutputStream& stream, wxRichTextFileType type = wxRICHTEXT_TYPE_ANY);
3001
3002 /// Set the handler flags, controlling loading and saving
3003 void SetHandlerFlags(int flags) { m_handlerFlags = flags; }
3004
3005 /// Get the handler flags, controlling loading and saving
3006 int GetHandlerFlags() const { return m_handlerFlags; }
3007
3008 /// Convenience function to add a paragraph of text
3009 virtual wxRichTextRange AddParagraph(const wxString& text, wxRichTextAttr* paraStyle = NULL) { Modify(); return wxRichTextParagraphLayoutBox::AddParagraph(text, paraStyle); }
3010
3011 /// Begin collapsing undo/redo commands. Note that this may not work properly
3012 /// if combining commands that delete or insert content, changing ranges for
3013 /// subsequent actions.
3014 virtual bool BeginBatchUndo(const wxString& cmdName);
3015
3016 /// End collapsing undo/redo commands
3017 virtual bool EndBatchUndo();
3018
3019 /// Collapsing commands?
3020 virtual bool BatchingUndo() const { return m_batchedCommandDepth > 0; }
3021
3022 /// Submit immediately, or delay according to whether collapsing is on
3023 virtual bool SubmitAction(wxRichTextAction* action);
3024
3025 /// Get collapsed command
3026 virtual wxRichTextCommand* GetBatchedCommand() const { return m_batchedCommand; }
3027
3028 /// Begin suppressing undo/redo commands. The way undo is suppressed may be implemented
3029 /// differently by each command. If not dealt with by a command implementation, then
3030 /// it will be implemented automatically by not storing the command in the undo history
3031 /// when the action is submitted to the command processor.
3032 virtual bool BeginSuppressUndo();
3033
3034 /// End suppressing undo/redo commands.
3035 virtual bool EndSuppressUndo();
3036
3037 /// Collapsing commands?
3038 virtual bool SuppressingUndo() const { return m_suppressUndo > 0; }
3039
3040 /// Copy the range to the clipboard
3041 virtual bool CopyToClipboard(const wxRichTextRange& range);
3042
3043 /// Paste the clipboard content to the buffer
3044 virtual bool PasteFromClipboard(long position);
3045
3046 /// Can we paste from the clipboard?
3047 virtual bool CanPasteFromClipboard() const;
3048
3049 /// Begin using a style
3050 virtual bool BeginStyle(const wxRichTextAttr& style);
3051
3052 /// End the style
3053 virtual bool EndStyle();
3054
3055 /// End all styles
3056 virtual bool EndAllStyles();
3057
3058 /// Clear the style stack
3059 virtual void ClearStyleStack();
3060
3061 /// Get the size of the style stack, for example to check correct nesting
3062 virtual size_t GetStyleStackSize() const { return m_attributeStack.GetCount(); }
3063
3064 /// Begin using bold
3065 bool BeginBold();
3066
3067 /// End using bold
3068 bool EndBold() { return EndStyle(); }
3069
3070 /// Begin using italic
3071 bool BeginItalic();
3072
3073 /// End using italic
3074 bool EndItalic() { return EndStyle(); }
3075
3076 /// Begin using underline
3077 bool BeginUnderline();
3078
3079 /// End using underline
3080 bool EndUnderline() { return EndStyle(); }
3081
3082 /// Begin using point size
3083 bool BeginFontSize(int pointSize);
3084
3085 /// End using point size
3086 bool EndFontSize() { return EndStyle(); }
3087
3088 /// Begin using this font
3089 bool BeginFont(const wxFont& font);
3090
3091 /// End using a font
3092 bool EndFont() { return EndStyle(); }
3093
3094 /// Begin using this colour
3095 bool BeginTextColour(const wxColour& colour);
3096
3097 /// End using a colour
3098 bool EndTextColour() { return EndStyle(); }
3099
3100 /// Begin using alignment
3101 bool BeginAlignment(wxTextAttrAlignment alignment);
3102
3103 /// End alignment
3104 bool EndAlignment() { return EndStyle(); }
3105
3106 /// Begin left indent
3107 bool BeginLeftIndent(int leftIndent, int leftSubIndent = 0);
3108
3109 /// End left indent
3110 bool EndLeftIndent() { return EndStyle(); }
3111
3112 /// Begin right indent
3113 bool BeginRightIndent(int rightIndent);
3114
3115 /// End right indent
3116 bool EndRightIndent() { return EndStyle(); }
3117
3118 /// Begin paragraph spacing
3119 bool BeginParagraphSpacing(int before, int after);
3120
3121 /// End paragraph spacing
3122 bool EndParagraphSpacing() { return EndStyle(); }
3123
3124 /// Begin line spacing
3125 bool BeginLineSpacing(int lineSpacing);
3126
3127 /// End line spacing
3128 bool EndLineSpacing() { return EndStyle(); }
3129
3130 /// Begin numbered bullet
3131 bool BeginNumberedBullet(int bulletNumber, int leftIndent, int leftSubIndent, int bulletStyle = wxTEXT_ATTR_BULLET_STYLE_ARABIC|wxTEXT_ATTR_BULLET_STYLE_PERIOD);
3132
3133 /// End numbered bullet
3134 bool EndNumberedBullet() { return EndStyle(); }
3135
3136 /// Begin symbol bullet
3137 bool BeginSymbolBullet(const wxString& symbol, int leftIndent, int leftSubIndent, int bulletStyle = wxTEXT_ATTR_BULLET_STYLE_SYMBOL);
3138
3139 /// End symbol bullet
3140 bool EndSymbolBullet() { return EndStyle(); }
3141
3142 /// Begin standard bullet
3143 bool BeginStandardBullet(const wxString& bulletName, int leftIndent, int leftSubIndent, int bulletStyle = wxTEXT_ATTR_BULLET_STYLE_STANDARD);
3144
3145 /// End standard bullet
3146 bool EndStandardBullet() { return EndStyle(); }
3147
3148 /// Begin named character style
3149 bool BeginCharacterStyle(const wxString& characterStyle);
3150
3151 /// End named character style
3152 bool EndCharacterStyle() { return EndStyle(); }
3153
3154 /// Begin named paragraph style
3155 bool BeginParagraphStyle(const wxString& paragraphStyle);
3156
3157 /// End named character style
3158 bool EndParagraphStyle() { return EndStyle(); }
3159
3160 /// Begin named list style
3161 bool BeginListStyle(const wxString& listStyle, int level = 1, int number = 1);
3162
3163 /// End named character style
3164 bool EndListStyle() { return EndStyle(); }
3165
3166 /// Begin URL
3167 bool BeginURL(const wxString& url, const wxString& characterStyle = wxEmptyString);
3168
3169 /// End URL
3170 bool EndURL() { return EndStyle(); }
3171
3172 // Event handling
3173
3174 /// Add an event handler
3175 bool AddEventHandler(wxEvtHandler* handler);
3176
3177 /// Remove an event handler
3178 bool RemoveEventHandler(wxEvtHandler* handler, bool deleteHandler = false);
3179
3180 /// Clear event handlers
3181 void ClearEventHandlers();
3182
3183 /// Send event to event handlers. If sendToAll is true, will send to all event handlers,
3184 /// otherwise will stop at the first successful one.
3185 bool SendEvent(wxEvent& event, bool sendToAll = true);
3186
3187 // Implementation
3188
3189 /// Hit-testing: returns a flag indicating hit test details, plus
3190 /// information about position
3191 virtual int HitTest(wxDC& dc, const wxPoint& pt, long& textPosition, wxRichTextObject** obj, wxRichTextObject** contextObj, int flags = 0);
3192
3193 /// Copy
3194 void Copy(const wxRichTextBuffer& obj);
3195
3196 /// Assignment
3197 void operator= (const wxRichTextBuffer& obj) { Copy(obj); }
3198
3199 /// Clone
3200 virtual wxRichTextObject* Clone() const { return new wxRichTextBuffer(*this); }
3201
3202 /// Submit command to insert paragraphs
3203 bool InsertParagraphsWithUndo(long pos, const wxRichTextParagraphLayoutBox& paragraphs, wxRichTextCtrl* ctrl, int flags = 0);
3204
3205 /// Submit command to insert the given text
3206 bool InsertTextWithUndo(long pos, const wxString& text, wxRichTextCtrl* ctrl, int flags = 0);
3207
3208 /// Submit command to insert a newline
3209 bool InsertNewlineWithUndo(long pos, wxRichTextCtrl* ctrl, int flags = 0);
3210
3211 /// Submit command to insert the given image
3212 bool InsertImageWithUndo(long pos, const wxRichTextImageBlock& imageBlock, wxRichTextCtrl* ctrl, int flags = 0,
3213 const wxRichTextAttr& textAttr = wxRichTextAttr());
3214
3215 /// Submit command to insert an object
3216 wxRichTextObject* InsertObjectWithUndo(long pos, wxRichTextObject *object, wxRichTextCtrl* ctrl, int flags);
3217
3218 /// Submit command to delete this range
3219 bool DeleteRangeWithUndo(const wxRichTextRange& range, wxRichTextCtrl* ctrl);
3220
3221 /// Mark modified
3222 void Modify(bool modify = true) { m_modified = modify; }
3223 bool IsModified() const { return m_modified; }
3224
3225 /// Dumps contents of buffer for debugging purposes
3226 virtual void Dump();
3227 virtual void Dump(wxTextOutputStream& stream) { wxRichTextParagraphLayoutBox::Dump(stream); }
3228
3229 /// Returns the file handlers
3230 static wxList& GetHandlers() { return sm_handlers; }
3231
3232 /// Adds a handler to the end
3233 static void AddHandler(wxRichTextFileHandler *handler);
3234
3235 /// Inserts a handler at the front
3236 static void InsertHandler(wxRichTextFileHandler *handler);
3237
3238 /// Removes a handler
3239 static bool RemoveHandler(const wxString& name);
3240
3241 /// Finds a handler by name
3242 static wxRichTextFileHandler *FindHandler(const wxString& name);
3243
3244 /// Finds a handler by extension and type
3245 static wxRichTextFileHandler *FindHandler(const wxString& extension, wxRichTextFileType imageType);
3246
3247 /// Finds a handler by filename or, if supplied, type
3248 static wxRichTextFileHandler *FindHandlerFilenameOrType(const wxString& filename,
3249 wxRichTextFileType imageType);
3250
3251 /// Finds a handler by type
3252 static wxRichTextFileHandler *FindHandler(wxRichTextFileType imageType);
3253
3254 /// Gets a wildcard incorporating all visible handlers. If 'types' is present,
3255 /// will be filled with the file type corresponding to each filter. This can be
3256 /// used to determine the type to pass to LoadFile given a selected filter.
3257 static wxString GetExtWildcard(bool combine = false, bool save = false, wxArrayInt* types = NULL);
3258
3259 /// Clean up handlers
3260 static void CleanUpHandlers();
3261
3262 /// Initialise the standard handlers
3263 static void InitStandardHandlers();
3264
3265 /// Get renderer
3266 static wxRichTextRenderer* GetRenderer() { return sm_renderer; }
3267
3268 /// Set renderer, deleting old one
3269 static void SetRenderer(wxRichTextRenderer* renderer);
3270
3271 /// Minimum margin between bullet and paragraph in 10ths of a mm
3272 static int GetBulletRightMargin() { return sm_bulletRightMargin; }
3273 static void SetBulletRightMargin(int margin) { sm_bulletRightMargin = margin; }
3274
3275 /// Factor to multiply by character height to get a reasonable bullet size
3276 static float GetBulletProportion() { return sm_bulletProportion; }
3277 static void SetBulletProportion(float prop) { sm_bulletProportion = prop; }
3278
3279 /// Scale factor for calculating dimensions
3280 double GetScale() const { return m_scale; }
3281 void SetScale(double scale) { m_scale = scale; }
3282
3283 protected:
3284
3285 /// Command processor
3286 wxCommandProcessor* m_commandProcessor;
3287
3288 /// Table storing fonts
3289 wxRichTextFontTable m_fontTable;
3290
3291 /// Has been modified?
3292 bool m_modified;
3293
3294 /// Collapsed command stack
3295 int m_batchedCommandDepth;
3296
3297 /// Name for collapsed command
3298 wxString m_batchedCommandsName;
3299
3300 /// Current collapsed command accumulating actions
3301 wxRichTextCommand* m_batchedCommand;
3302
3303 /// Whether to suppress undo
3304 int m_suppressUndo;
3305
3306 /// Style sheet, if any
3307 wxRichTextStyleSheet* m_styleSheet;
3308
3309 /// List of event handlers that will be notified of events
3310 wxList m_eventHandlers;
3311
3312 /// Stack of attributes for convenience functions
3313 wxList m_attributeStack;
3314
3315 /// Flags to be passed to handlers
3316 int m_handlerFlags;
3317
3318 /// File handlers
3319 static wxList sm_handlers;
3320
3321 /// Renderer
3322 static wxRichTextRenderer* sm_renderer;
3323
3324 /// Minimum margin between bullet and paragraph in 10ths of a mm
3325 static int sm_bulletRightMargin;
3326
3327 /// Factor to multiply by character height to get a reasonable bullet size
3328 static float sm_bulletProportion;
3329
3330 /// Scaling factor in use: needed to calculate correct dimensions when printing
3331 double m_scale;
3332 };
3333
3334 /**
3335 @class wxRichTextCell
3336
3337 wxRichTextCell is the cell in a table.
3338 */
3339
3340 class WXDLLIMPEXP_RICHTEXT wxRichTextCell: public wxRichTextBox
3341 {
3342 DECLARE_DYNAMIC_CLASS(wxRichTextCell)
3343 public:
3344 // Constructors
3345
3346 /**
3347 Default constructor; optionally pass the parent object.
3348 */
3349
3350 wxRichTextCell(wxRichTextObject* parent = NULL);
3351
3352 /**
3353 Copy constructor.
3354 */
3355
3356 wxRichTextCell(const wxRichTextCell& obj): wxRichTextBox() { Copy(obj); }
3357
3358 // Overrideables
3359
3360 /**
3361 Draws the item.
3362 */
3363
3364 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
3365
3366 /**
3367 Returns the XML node name of this object.
3368 */
3369
3370 virtual wxString GetXMLNodeName() const { return wxT("cell"); }
3371
3372 /// Can we edit properties via a GUI?
3373 virtual bool CanEditProperties() const { return true; }
3374
3375 /// Edit properties via a GUI
3376 virtual bool EditProperties(wxWindow* parent, wxRichTextBuffer* buffer);
3377
3378 /// Return the label to be used for the properties context menu item.
3379 virtual wxString GetPropertiesMenuLabel() const { return _("&Cell"); }
3380
3381 // Accessors
3382
3383 // Operations
3384
3385 /**
3386 Makes a clone of this object.
3387 */
3388 virtual wxRichTextObject* Clone() const { return new wxRichTextCell(*this); }
3389
3390 /**
3391 Copies this object.
3392 */
3393 void Copy(const wxRichTextCell& obj);
3394
3395 protected:
3396 };
3397
3398 /**
3399 @class wxRichTextTable
3400
3401 wxRichTextTable represents a table with arbitrary columns and rows.
3402 */
3403
3404 WX_DEFINE_ARRAY_PTR(wxRichTextObject*, wxRichTextObjectPtrArray);
3405 WX_DECLARE_OBJARRAY(wxRichTextObjectPtrArray, wxRichTextObjectPtrArrayArray);
3406
3407 class WXDLLIMPEXP_RICHTEXT wxRichTextTable: public wxRichTextBox
3408 {
3409 DECLARE_DYNAMIC_CLASS(wxRichTextTable)
3410 public:
3411
3412 // Constructors
3413
3414 /**
3415 Default constructor; optionally pass the parent object.
3416 */
3417
3418 wxRichTextTable(wxRichTextObject* parent = NULL);
3419
3420 /**
3421 Copy constructor.
3422 */
3423
3424 wxRichTextTable(const wxRichTextTable& obj): wxRichTextBox() { Copy(obj); }
3425
3426 // Overrideables
3427
3428 // Draws the object.
3429 virtual bool Draw(wxDC& dc, const wxRichTextRange& range, const wxRichTextSelection& selection, const wxRect& rect, int descent, int style);
3430
3431 // Returns the XML node name of this object.
3432 virtual wxString GetXMLNodeName() const { return wxT("table"); }
3433
3434 // Lays the object out.
3435 virtual bool Layout(wxDC& dc, const wxRect& rect, int style);
3436
3437 // Gets the range size.
3438 virtual bool GetRangeSize(const wxRichTextRange& range, wxSize& size, int& descent, wxDC& dc, int flags, wxPoint position = wxPoint(0,0), wxArrayInt* partialExtents = NULL) const;
3439
3440 // Deletes content in the given range.
3441 virtual bool DeleteRange(const wxRichTextRange& range);
3442
3443 // Gets any text in this object for the given range.
3444 virtual wxString GetTextForRange(const wxRichTextRange& range) const;
3445
3446 #if wxUSE_XML
3447 // Import this object from XML
3448 virtual bool ImportFromXML(wxRichTextBuffer* buffer, wxXmlNode* node, wxRichTextXMLHandler* handler, bool* recurse);
3449 #endif
3450
3451 #if wxRICHTEXT_HAVE_DIRECT_OUTPUT
3452 // Export this object directly to the given stream.
3453 virtual bool ExportXML(wxOutputStream& stream, int indent, wxRichTextXMLHandler* handler);
3454 #endif
3455
3456 #if wxRICHTEXT_HAVE_XMLDOCUMENT_OUTPUT
3457 // Export this object to the given parent node, usually creating at least one child node.
3458 virtual bool ExportXML(wxXmlNode* parent, wxRichTextXMLHandler* handler);
3459 #endif
3460
3461 /// Finds the absolute position and row height for the given character position
3462 virtual bool FindPosition(wxDC& dc, long index, wxPoint& pt, int* height, bool forceLineStart);
3463
3464 /// Calculate range
3465 virtual void CalculateRange(long start, long& end);
3466
3467 /// Can this object handle the selections of its children? FOr example, a table.
3468 virtual bool HandlesChildSelections() const { return true; }
3469
3470 /// Returns a selection object specifying the selections between start and end character positions.
3471 /// For example, a table would deduce what cells (of range length 1) are selected when dragging across the table.
3472 virtual wxRichTextSelection GetSelection(long start, long end) const;
3473
3474 /// Can we edit properties via a GUI?
3475 virtual bool CanEditProperties() const { return true; }
3476
3477 /// Edit properties via a GUI
3478 virtual bool EditProperties(wxWindow* parent, wxRichTextBuffer* buffer);
3479
3480 /// Return the label to be used for the properties context menu item.
3481 virtual wxString GetPropertiesMenuLabel() const { return _("&Table"); }
3482
3483 /// Returns true if objects of this class can accept the focus, i.e. a call to SetFocusObject
3484 /// is possible. For example, containers supporting text, such as a text box object, can accept the focus,
3485 /// but a table can't (set the focus to individual cells instead).
3486 virtual bool AcceptsFocus() const { return false; }
3487
3488 // Accessors
3489
3490 const wxRichTextObjectPtrArrayArray& GetCells() const { return m_cells; }
3491 wxRichTextObjectPtrArrayArray& GetCells() { return m_cells; }
3492
3493 int GetRowCount() const { return m_rowCount; }
3494 int GetColumnCount() const { return m_colCount; }
3495
3496 /// Get the cell at the given row/column position
3497 virtual wxRichTextCell* GetCell(int row, int col) const;
3498
3499 /// Get the cell at the given character position (in the range of the table).
3500 virtual wxRichTextCell* GetCell(long pos) const;
3501
3502 /// Get the row/column for a given character position
3503 virtual bool GetCellRowColumnPosition(long pos, int& row, int& col) const;
3504
3505 // Operations
3506
3507 /**
3508 Clears the table.
3509 */
3510
3511 virtual void ClearTable();
3512
3513 /**
3514 Creates a table of the given dimensions.
3515 */
3516
3517 virtual bool CreateTable(int rows, int cols);
3518
3519 /**
3520 Sets the attributes for the cells specified by the selection.
3521 */
3522
3523 virtual bool SetCellStyle(const wxRichTextSelection& selection, const wxRichTextAttr& style, int flags = wxRICHTEXT_SETSTYLE_WITH_UNDO);
3524
3525 /**
3526 Deletes rows from the given row position.
3527 */
3528
3529 virtual bool DeleteRows(int startRow, int noRows = 1);
3530
3531 /**
3532 Deletes columns from the given column position.
3533 */
3534
3535 virtual bool DeleteColumns(int startCol, int noCols = 1);
3536
3537 /**
3538 Adds rows from the given row position.
3539 */
3540
3541 virtual bool AddRows(int startRow, int noRows = 1, const wxRichTextAttr& attr = wxRichTextAttr());
3542
3543 /**
3544 Adds columns from the given column position.
3545 */
3546
3547 virtual bool AddColumns(int startCol, int noCols = 1, const wxRichTextAttr& attr = wxRichTextAttr());
3548
3549 // Makes a clone of this object.
3550 virtual wxRichTextObject* Clone() const { return new wxRichTextTable(*this); }
3551
3552 // Copies this object.
3553 void Copy(const wxRichTextTable& obj);
3554
3555 protected:
3556
3557 int m_rowCount;
3558 int m_colCount;
3559
3560 // An array of rows, each of which is a wxRichTextObjectPtrArray containing
3561 // the cell objects. The cell objects are also children of this object.
3562 // Problem: if boxes are immediate children of a box, this will cause problems
3563 // with wxRichTextParagraphLayoutBox functions (and functions elsewhere) that
3564 // expect to find just paragraphs. May have to adjust the way we handle the
3565 // hierarchy to accept non-paragraph objects in a a paragraph layout box.
3566 // We'll be overriding much wxRichTextParagraphLayoutBox functionality so this
3567 // may not be such a problem. Perhaps the table should derive from a different
3568 // class?
3569 wxRichTextObjectPtrArrayArray m_cells;
3570 };
3571
3572
3573 /*!
3574 * The command identifiers
3575 *
3576 */
3577
3578 enum wxRichTextCommandId
3579 {
3580 wxRICHTEXT_INSERT,
3581 wxRICHTEXT_DELETE,
3582 wxRICHTEXT_CHANGE_ATTRIBUTES,
3583 wxRICHTEXT_CHANGE_STYLE,
3584 wxRICHTEXT_CHANGE_OBJECT
3585 };
3586
3587 /*!
3588 * A class for specifying an object anywhere in an object hierarchy,
3589 * without using a pointer, necessary since wxRTC commands may delete
3590 * and recreate sub-objects so physical object addresses change. An array
3591 * of positions (one per hierarchy level) is used.
3592 *
3593 */
3594
3595 class WXDLLIMPEXP_RICHTEXT wxRichTextObjectAddress
3596 {
3597 public:
3598 // Creates the address given container and object.
3599 wxRichTextObjectAddress(wxRichTextParagraphLayoutBox* topLevelContainer, wxRichTextObject* obj) { Create(topLevelContainer, obj); }
3600 wxRichTextObjectAddress() { Init(); }
3601 wxRichTextObjectAddress(const wxRichTextObjectAddress& address) { Copy(address); }
3602
3603 void Init() {}
3604 void Copy(const wxRichTextObjectAddress& address) { m_address = address.m_address; }
3605 void operator=(const wxRichTextObjectAddress& address) { Copy(address); }
3606
3607 wxRichTextObject* GetObject(wxRichTextParagraphLayoutBox* topLevelContainer) const;
3608 bool Create(wxRichTextParagraphLayoutBox* topLevelContainer, wxRichTextObject* obj);
3609
3610 wxArrayInt& GetAddress() { return m_address; }
3611 const wxArrayInt& GetAddress() const { return m_address; }
3612 void SetAddress(const wxArrayInt& address) { m_address = address; }
3613
3614 protected:
3615
3616 wxArrayInt m_address;
3617 };
3618
3619 /*!
3620 * Command classes for undo/redo
3621 *
3622 */
3623
3624 class WXDLLIMPEXP_FWD_RICHTEXT wxRichTextAction;
3625 class WXDLLIMPEXP_RICHTEXT wxRichTextCommand: public wxCommand
3626 {
3627 public:
3628 // Ctor for one action
3629 wxRichTextCommand(const wxString& name, wxRichTextCommandId id, wxRichTextBuffer* buffer,
3630 wxRichTextParagraphLayoutBox* container, wxRichTextCtrl* ctrl, bool ignoreFirstTime = false);
3631
3632 // Ctor for multiple actions
3633 wxRichTextCommand(const wxString& name);
3634
3635 virtual ~wxRichTextCommand();
3636
3637 bool Do();
3638 bool Undo();
3639
3640 void AddAction(wxRichTextAction* action);
3641 void ClearActions();
3642
3643 wxList& GetActions() { return m_actions; }
3644
3645 protected:
3646
3647 wxList m_actions;
3648 };
3649
3650 /*!
3651 * wxRichTextAction class declaration
3652 * There can be more than one action in a command.
3653 */
3654
3655 class WXDLLIMPEXP_RICHTEXT wxRichTextAction: public wxObject
3656 {
3657 public:
3658 /// Constructor. 'buffer' is the top-level buffer, while 'container' is the object within
3659 /// which the action is taking place. In the simplest case, they are the same.
3660 wxRichTextAction(wxRichTextCommand* cmd, const wxString& name, wxRichTextCommandId id,
3661 wxRichTextBuffer* buffer, wxRichTextParagraphLayoutBox* container,
3662 wxRichTextCtrl* ctrl, bool ignoreFirstTime = false);
3663
3664 virtual ~wxRichTextAction();
3665
3666 bool Do();
3667 bool Undo();
3668
3669 /// Update the control appearance
3670 void UpdateAppearance(long caretPosition, bool sendUpdateEvent = false,
3671 wxArrayInt* optimizationLineCharPositions = NULL, wxArrayInt* optimizationLineYPositions = NULL, bool isDoCmd = true);
3672
3673 /// Replace the buffer paragraphs with the given fragment.
3674 void ApplyParagraphs(const wxRichTextParagraphLayoutBox& fragment);
3675
3676 /// Get the fragments
3677 wxRichTextParagraphLayoutBox& GetNewParagraphs() { return m_newParagraphs; }
3678 wxRichTextParagraphLayoutBox& GetOldParagraphs() { return m_oldParagraphs; }
3679
3680 /// Get the attributes
3681 wxRichTextAttr& GetAttributes() { return m_attributes; }
3682
3683 /// An object to replace the one at the position
3684 /// defined by the container address and the action's range start position.
3685 wxRichTextObject* GetObject() const { return m_object; }
3686 void SetObject(wxRichTextObject* obj) { m_object = obj; m_objectAddress.Create(m_buffer, m_object); }
3687 void MakeObject(wxRichTextObject* obj) { m_objectAddress.Create(m_buffer, obj); }
3688
3689 /// Calculate arrays for refresh optimization
3690 void CalculateRefreshOptimizations(wxArrayInt& optimizationLineCharPositions, wxArrayInt& optimizationLineYPositions);
3691
3692 /// Set/get the position used for e.g. insertion
3693 void SetPosition(long pos) { m_position = pos; }
3694 long GetPosition() const { return m_position; }
3695
3696 /// Set/get the range for e.g. deletion
3697 void SetRange(const wxRichTextRange& range) { m_range = range; }
3698 const wxRichTextRange& GetRange() const { return m_range; }
3699
3700 /// The address (nested position) of the container within the buffer being manipulated
3701 wxRichTextObjectAddress& GetContainerAddress() { return m_containerAddress; }
3702 const wxRichTextObjectAddress& GetContainerAddress() const { return m_containerAddress; }
3703 void SetContainerAddress(const wxRichTextObjectAddress& address) { m_containerAddress = address; }
3704 void SetContainerAddress(wxRichTextParagraphLayoutBox* container, wxRichTextObject* obj) { m_containerAddress.Create(container, obj); }
3705
3706 /// Returns the container that this action refers to, using the container address and top-level buffer.
3707 wxRichTextParagraphLayoutBox* GetContainer() const;
3708 /// Get name
3709 const wxString& GetName() const { return m_name; }
3710
3711 protected:
3712 // Action name
3713 wxString m_name;
3714
3715 // Buffer
3716 wxRichTextBuffer* m_buffer;
3717
3718 // The address (nested position) of the container being manipulated.
3719 // This is necessary because objects are deleted, and we can't
3720 // therefore store actual pointers.
3721 wxRichTextObjectAddress m_containerAddress;
3722
3723 // Control
3724 wxRichTextCtrl* m_ctrl;
3725
3726 // Stores the new paragraphs
3727 wxRichTextParagraphLayoutBox m_newParagraphs;
3728
3729 // Stores the old paragraphs
3730 wxRichTextParagraphLayoutBox m_oldParagraphs;
3731
3732 // Stores an object to replace the one at the position
3733 // defined by the container address and the action's range start position.
3734 wxRichTextObject* m_object;
3735
3736 // Stores the attributes
3737 wxRichTextAttr m_attributes;
3738
3739 // The address of the object being manipulated (used for changing an individual object or its attributes)
3740 wxRichTextObjectAddress m_objectAddress;
3741
3742 // Stores the old attributes
3743 // wxRichTextAttr m_oldAttributes;
3744
3745 // The affected range
3746 wxRichTextRange m_range;
3747
3748 // The insertion point for this command
3749 long m_position;
3750
3751 // Ignore 1st 'Do' operation because we already did it
3752 bool m_ignoreThis;
3753
3754 // The command identifier
3755 wxRichTextCommandId m_cmdId;
3756 };
3757
3758 /*!
3759 * Handler flags
3760 */
3761
3762 // Include style sheet when loading and saving
3763 #define wxRICHTEXT_HANDLER_INCLUDE_STYLESHEET 0x0001
3764
3765 // Save images to memory file system in HTML handler
3766 #define wxRICHTEXT_HANDLER_SAVE_IMAGES_TO_MEMORY 0x0010
3767
3768 // Save images to files in HTML handler
3769 #define wxRICHTEXT_HANDLER_SAVE_IMAGES_TO_FILES 0x0020
3770
3771 // Save images as inline base64 data in HTML handler
3772 #define wxRICHTEXT_HANDLER_SAVE_IMAGES_TO_BASE64 0x0040
3773
3774 // Don't write header and footer (or BODY), so we can include the fragment
3775 // in a larger document
3776 #define wxRICHTEXT_HANDLER_NO_HEADER_FOOTER 0x0080
3777
3778 // Convert the more common face names to names that will work on the current platform
3779 // in a larger document
3780 #define wxRICHTEXT_HANDLER_CONVERT_FACENAMES 0x0100
3781
3782 /*!
3783 * wxRichTextFileHandler
3784 * Base class for file handlers
3785 */
3786
3787 class WXDLLIMPEXP_RICHTEXT wxRichTextFileHandler: public wxObject
3788 {
3789 DECLARE_CLASS(wxRichTextFileHandler)
3790 public:
3791 wxRichTextFileHandler(const wxString& name = wxEmptyString, const wxString& ext = wxEmptyString, int type = 0)
3792 : m_name(name), m_extension(ext), m_type(type), m_flags(0), m_visible(true)
3793 { }
3794
3795 #if wxUSE_STREAMS
3796 bool LoadFile(wxRichTextBuffer *buffer, wxInputStream& stream)
3797 { return DoLoadFile(buffer, stream); }
3798 bool SaveFile(wxRichTextBuffer *buffer, wxOutputStream& stream)
3799 { return DoSaveFile(buffer, stream); }
3800 #endif
3801
3802 #if wxUSE_FFILE && wxUSE_STREAMS
3803 virtual bool LoadFile(wxRichTextBuffer *buffer, const wxString& filename);
3804 virtual bool SaveFile(wxRichTextBuffer *buffer, const wxString& filename);
3805 #endif // wxUSE_STREAMS && wxUSE_STREAMS
3806
3807 /// Can we handle this filename (if using files)? By default, checks the extension.
3808 virtual bool CanHandle(const wxString& filename) const;
3809
3810 /// Can we save using this handler?
3811 virtual bool CanSave() const { return false; }
3812
3813 /// Can we load using this handler?
3814 virtual bool CanLoad() const { return false; }
3815
3816 /// Should this handler be visible to the user?
3817 virtual bool IsVisible() const { return m_visible; }
3818 virtual void SetVisible(bool visible) { m_visible = visible; }
3819
3820 /// The name of the nandler
3821 void SetName(const wxString& name) { m_name = name; }
3822 wxString GetName() const { return m_name; }
3823
3824 /// The default extension to recognise
3825 void SetExtension(const wxString& ext) { m_extension = ext; }
3826 wxString GetExtension() const { return m_extension; }
3827
3828 /// The handler type
3829 void SetType(int type) { m_type = type; }
3830 int GetType() const { return m_type; }
3831
3832 /// Flags controlling how loading and saving is done
3833 void SetFlags(int flags) { m_flags = flags; }
3834 int GetFlags() const { return m_flags; }
3835
3836 /// Encoding to use when saving a file. If empty, a suitable encoding is chosen
3837 void SetEncoding(const wxString& encoding) { m_encoding = encoding; }
3838 const wxString& GetEncoding() const { return m_encoding; }
3839
3840 protected:
3841
3842 #if wxUSE_STREAMS
3843 virtual bool DoLoadFile(wxRichTextBuffer *buffer, wxInputStream& stream) = 0;
3844 virtual bool DoSaveFile(wxRichTextBuffer *buffer, wxOutputStream& stream) = 0;
3845 #endif
3846
3847 wxString m_name;
3848 wxString m_encoding;
3849 wxString m_extension;
3850 int m_type;
3851 int m_flags;
3852 bool m_visible;
3853 };
3854
3855 /*!
3856 * wxRichTextPlainTextHandler
3857 * Plain text handler
3858 */
3859
3860 class WXDLLIMPEXP_RICHTEXT wxRichTextPlainTextHandler: public wxRichTextFileHandler
3861 {
3862 DECLARE_CLASS(wxRichTextPlainTextHandler)
3863 public:
3864 wxRichTextPlainTextHandler(const wxString& name = wxT("Text"),
3865 const wxString& ext = wxT("txt"),
3866 wxRichTextFileType type = wxRICHTEXT_TYPE_TEXT)
3867 : wxRichTextFileHandler(name, ext, type)
3868 { }
3869
3870 /// Can we save using this handler?
3871 virtual bool CanSave() const { return true; }
3872
3873 /// Can we load using this handler?
3874 virtual bool CanLoad() const { return true; }
3875
3876 protected:
3877
3878 #if wxUSE_STREAMS
3879 virtual bool DoLoadFile(wxRichTextBuffer *buffer, wxInputStream& stream);
3880 virtual bool DoSaveFile(wxRichTextBuffer *buffer, wxOutputStream& stream);
3881 #endif
3882
3883 };
3884
3885 #if wxUSE_DATAOBJ
3886
3887 /*!
3888 * The data object for a wxRichTextBuffer
3889 */
3890
3891 class WXDLLIMPEXP_RICHTEXT wxRichTextBufferDataObject: public wxDataObjectSimple
3892 {
3893 public:
3894 // ctor doesn't copy the pointer, so it shouldn't go away while this object
3895 // is alive
3896 wxRichTextBufferDataObject(wxRichTextBuffer* richTextBuffer = NULL);
3897 virtual ~wxRichTextBufferDataObject();
3898
3899 // after a call to this function, the buffer is owned by the caller and it
3900 // is responsible for deleting it
3901 wxRichTextBuffer* GetRichTextBuffer();
3902
3903 // Returns the id for the new data format
3904 static const wxChar* GetRichTextBufferFormatId() { return ms_richTextBufferFormatId; }
3905
3906 // base class pure virtuals
3907
3908 virtual wxDataFormat GetPreferredFormat(Direction dir) const;
3909 virtual size_t GetDataSize() const;
3910 virtual bool GetDataHere(void *pBuf) const;
3911 virtual bool SetData(size_t len, const void *buf);
3912
3913 // prevent warnings
3914
3915 virtual size_t GetDataSize(const wxDataFormat&) const { return GetDataSize(); }
3916 virtual bool GetDataHere(const wxDataFormat&, void *buf) const { return GetDataHere(buf); }
3917 virtual bool SetData(const wxDataFormat&, size_t len, const void *buf) { return SetData(len, buf); }
3918
3919 private:
3920 wxDataFormat m_formatRichTextBuffer; // our custom format
3921 wxRichTextBuffer* m_richTextBuffer; // our data
3922 static const wxChar* ms_richTextBufferFormatId; // our format id
3923 };
3924
3925 #endif
3926
3927 /*!
3928 * wxRichTextRenderer isolates common drawing functionality
3929 */
3930
3931 class WXDLLIMPEXP_RICHTEXT wxRichTextRenderer: public wxObject
3932 {
3933 public:
3934 wxRichTextRenderer() {}
3935 virtual ~wxRichTextRenderer() {}
3936
3937 /// Draw a standard bullet, as specified by the value of GetBulletName
3938 virtual bool DrawStandardBullet(wxRichTextParagraph* paragraph, wxDC& dc, const wxRichTextAttr& attr, const wxRect& rect) = 0;
3939
3940 /// Draw a bullet that can be described by text, such as numbered or symbol bullets
3941 virtual bool DrawTextBullet(wxRichTextParagraph* paragraph, wxDC& dc, const wxRichTextAttr& attr, const wxRect& rect, const wxString& text) = 0;
3942
3943 /// Draw a bitmap bullet, where the bullet bitmap is specified by the value of GetBulletName
3944 virtual bool DrawBitmapBullet(wxRichTextParagraph* paragraph, wxDC& dc, const wxRichTextAttr& attr, const wxRect& rect) = 0;
3945
3946 /// Enumerate the standard bullet names currently supported
3947 virtual bool EnumerateStandardBulletNames(wxArrayString& bulletNames) = 0;
3948 };
3949
3950 /*!
3951 * wxRichTextStdRenderer: standard renderer
3952 */
3953
3954 class WXDLLIMPEXP_RICHTEXT wxRichTextStdRenderer: public wxRichTextRenderer
3955 {
3956 public:
3957 wxRichTextStdRenderer() {}
3958
3959 /// Draw a standard bullet, as specified by the value of GetBulletName
3960 virtual bool DrawStandardBullet(wxRichTextParagraph* paragraph, wxDC& dc, const wxRichTextAttr& attr, const wxRect& rect);
3961
3962 /// Draw a bullet that can be described by text, such as numbered or symbol bullets
3963 virtual bool DrawTextBullet(wxRichTextParagraph* paragraph, wxDC& dc, const wxRichTextAttr& attr, const wxRect& rect, const wxString& text);
3964
3965 /// Draw a bitmap bullet, where the bullet bitmap is specified by the value of GetBulletName
3966 virtual bool DrawBitmapBullet(wxRichTextParagraph* paragraph, wxDC& dc, const wxRichTextAttr& attr, const wxRect& rect);
3967
3968 /// Enumerate the standard bullet names currently supported
3969 virtual bool EnumerateStandardBulletNames(wxArrayString& bulletNames);
3970 };
3971
3972 /*!
3973 * Utilities
3974 *
3975 */
3976
3977 inline bool wxRichTextHasStyle(int flags, int style)
3978 {
3979 return ((flags & style) == style);
3980 }
3981
3982 /// Compare two attribute objects
3983 WXDLLIMPEXP_RICHTEXT bool wxTextAttrEq(const wxRichTextAttr& attr1, const wxRichTextAttr& attr2);
3984 WXDLLIMPEXP_RICHTEXT bool wxTextAttrEq(const wxRichTextAttr& attr1, const wxRichTextAttr& attr2);
3985
3986 /// Compare two attribute objects, but take into account the flags
3987 /// specifying attributes of interest.
3988 WXDLLIMPEXP_RICHTEXT bool wxTextAttrEqPartial(const wxRichTextAttr& attr1, const wxRichTextAttr& attr2);
3989
3990 /// Apply one style to another
3991 WXDLLIMPEXP_RICHTEXT bool wxRichTextApplyStyle(wxRichTextAttr& destStyle, const wxRichTextAttr& style, wxRichTextAttr* compareWith = NULL);
3992
3993 // Remove attributes
3994 WXDLLIMPEXP_RICHTEXT bool wxRichTextRemoveStyle(wxRichTextAttr& destStyle, const wxRichTextAttr& style);
3995
3996 /// Combine two bitlists
3997 WXDLLIMPEXP_RICHTEXT bool wxRichTextCombineBitlists(int& valueA, int valueB, int& flagsA, int flagsB);
3998
3999 /// Compare two bitlists
4000 WXDLLIMPEXP_RICHTEXT bool wxRichTextBitlistsEqPartial(int valueA, int valueB, int flags);
4001
4002 /// Split into paragraph and character styles
4003 WXDLLIMPEXP_RICHTEXT bool wxRichTextSplitParaCharStyles(const wxRichTextAttr& style, wxRichTextAttr& parStyle, wxRichTextAttr& charStyle);
4004
4005 /// Compare tabs
4006 WXDLLIMPEXP_RICHTEXT bool wxRichTextTabsEq(const wxArrayInt& tabs1, const wxArrayInt& tabs2);
4007
4008 /// Convert a decimal to Roman numerals
4009 WXDLLIMPEXP_RICHTEXT wxString wxRichTextDecimalToRoman(long n);
4010
4011 // Collects the attributes that are common to a range of content, building up a note of
4012 // which attributes are absent in some objects and which clash in some objects.
4013 WXDLLIMPEXP_RICHTEXT void wxTextAttrCollectCommonAttributes(wxTextAttr& currentStyle, const wxTextAttr& attr, wxTextAttr& clashingAttr, wxTextAttr& absentAttr);
4014
4015 WXDLLIMPEXP_RICHTEXT void wxRichTextModuleInit();
4016
4017 #endif
4018 // wxUSE_RICHTEXT
4019
4020 #endif
4021 // _WX_RICHTEXTBUFFER_H_
4022