markupparserattr.h 7.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231
  1. ///////////////////////////////////////////////////////////////////////////////
  2. // Name: wx/private/markupparserattr.h
  3. // Purpose: Classes mapping markup attributes to wxFont/wxColour.
  4. // Author: Vadim Zeitlin
  5. // Created: 2011-02-18
  6. // Copyright: (c) 2011 Vadim Zeitlin <vadim@wxwidgets.org>
  7. // Licence: wxWindows licence
  8. ///////////////////////////////////////////////////////////////////////////////
  9. #ifndef _WX_PRIVATE_MARKUPPARSERATTR_H_
  10. #define _WX_PRIVATE_MARKUPPARSERATTR_H_
  11. #include "wx/private/markupparser.h"
  12. #include "wx/stack.h"
  13. #include "wx/colour.h"
  14. #include "wx/font.h"
  15. // ----------------------------------------------------------------------------
  16. // wxMarkupParserAttrOutput: simplified wxFont-using version of the above.
  17. // ----------------------------------------------------------------------------
  18. // This class assumes that wxFont and wxColour are used to perform all the
  19. // markup tags and implements the base class virtual functions in terms of
  20. // OnAttr{Start,End}() only.
  21. //
  22. // Notice that you still must implement OnText() inherited from the base class
  23. // when deriving from this one.
  24. class wxMarkupParserAttrOutput : public wxMarkupParserOutput
  25. {
  26. public:
  27. // A simple container of font and colours.
  28. struct Attr
  29. {
  30. Attr(const wxFont& font_,
  31. const wxColour& foreground_ = wxColour(),
  32. const wxColour& background_ = wxColour())
  33. : font(font_), foreground(foreground_), background(background_)
  34. {
  35. }
  36. wxFont font;
  37. wxColour foreground,
  38. background;
  39. };
  40. // This object must be initialized with the font and colours to use
  41. // initially, i.e. the ones used before any tags in the string.
  42. wxMarkupParserAttrOutput(const wxFont& font,
  43. const wxColour& foreground,
  44. const wxColour& background)
  45. {
  46. m_attrs.push(Attr(font, foreground, background));
  47. }
  48. // Indicates the change of the font and/or colours used. Any of the
  49. // fields of the argument may be invalid indicating that the corresponding
  50. // attribute didn't actually change.
  51. virtual void OnAttrStart(const Attr& attr) = 0;
  52. // Indicates the end of the region affected by the given attributes
  53. // (the same ones that were passed to the matching OnAttrStart(), use
  54. // GetAttr() to get the ones that will be used from now on).
  55. virtual void OnAttrEnd(const Attr& attr) = 0;
  56. // Implement all pure virtual methods inherited from the base class in
  57. // terms of our own ones.
  58. virtual void OnBoldStart() { DoChangeFont(&wxFont::Bold); }
  59. virtual void OnBoldEnd() { DoEndAttr(); }
  60. virtual void OnItalicStart() { DoChangeFont(&wxFont::Italic); }
  61. virtual void OnItalicEnd() { DoEndAttr(); }
  62. virtual void OnUnderlinedStart() { DoChangeFont(&wxFont::Underlined); }
  63. virtual void OnUnderlinedEnd() { DoEndAttr(); }
  64. virtual void OnStrikethroughStart() { DoChangeFont(&wxFont::Strikethrough); }
  65. virtual void OnStrikethroughEnd() { DoEndAttr(); }
  66. virtual void OnBigStart() { DoChangeFont(&wxFont::Larger); }
  67. virtual void OnBigEnd() { DoEndAttr(); }
  68. virtual void OnSmallStart() { DoChangeFont(&wxFont::Smaller); }
  69. virtual void OnSmallEnd() { DoEndAttr(); }
  70. virtual void OnTeletypeStart()
  71. {
  72. wxFont font(GetFont());
  73. font.SetFamily(wxFONTFAMILY_TELETYPE);
  74. DoSetFont(font);
  75. }
  76. virtual void OnTeletypeEnd() { DoEndAttr(); }
  77. virtual void OnSpanStart(const wxMarkupSpanAttributes& spanAttr)
  78. {
  79. wxFont font(GetFont());
  80. if ( !spanAttr.m_fontFace.empty() )
  81. font.SetFaceName(spanAttr.m_fontFace);
  82. FontModifier<wxFontWeight>()(spanAttr.m_isBold,
  83. font, &wxFont::SetWeight,
  84. wxFONTWEIGHT_NORMAL, wxFONTWEIGHT_BOLD);
  85. FontModifier<wxFontStyle>()(spanAttr.m_isItalic,
  86. font, &wxFont::SetStyle,
  87. wxFONTSTYLE_NORMAL, wxFONTSTYLE_ITALIC);
  88. FontModifier<bool>()(spanAttr.m_isUnderlined,
  89. font, &wxFont::SetUnderlined,
  90. false, true);
  91. // TODO: No support for strike-through yet.
  92. switch ( spanAttr.m_sizeKind )
  93. {
  94. case wxMarkupSpanAttributes::Size_Unspecified:
  95. break;
  96. case wxMarkupSpanAttributes::Size_Relative:
  97. if ( spanAttr.m_fontSize > 0 )
  98. font.MakeLarger();
  99. else
  100. font.MakeSmaller();
  101. break;
  102. case wxMarkupSpanAttributes::Size_Symbolic:
  103. // The values of font size intentionally coincide with the
  104. // values of wxFontSymbolicSize enum elements so simply cast
  105. // one to the other.
  106. font.SetSymbolicSize(
  107. static_cast<wxFontSymbolicSize>(spanAttr.m_fontSize)
  108. );
  109. break;
  110. case wxMarkupSpanAttributes::Size_PointParts:
  111. font.SetPointSize((spanAttr.m_fontSize + 1023)/1024);
  112. break;
  113. }
  114. const Attr attr(font, spanAttr.m_fgCol, spanAttr.m_bgCol);
  115. OnAttrStart(attr);
  116. m_attrs.push(attr);
  117. }
  118. virtual void OnSpanEnd(const wxMarkupSpanAttributes& WXUNUSED(spanAttr))
  119. {
  120. DoEndAttr();
  121. }
  122. protected:
  123. // Get the current attributes, i.e. the ones that should be used for
  124. // rendering (or measuring or whatever) the text at the current position in
  125. // the string.
  126. //
  127. // It may be called from OnAttrStart() to get the old attributes used
  128. // before and from OnAttrEnd() to get the new attributes that will be used
  129. // from now on but is mostly meant to be used from overridden OnText()
  130. // implementations.
  131. const Attr& GetAttr() const { return m_attrs.top(); }
  132. // A shortcut for accessing the font of the current attribute.
  133. const wxFont& GetFont() const { return GetAttr().font; }
  134. private:
  135. // Change only the font to the given one. Call OnAttrStart() to notify
  136. // about the change and update the attributes stack.
  137. void DoSetFont(const wxFont& font)
  138. {
  139. const Attr attr(font);
  140. OnAttrStart(attr);
  141. m_attrs.push(attr);
  142. }
  143. // Apply the given function to the font currently on top of the font stack,
  144. // push the new font on the stack and call OnAttrStart() with it.
  145. void DoChangeFont(wxFont (wxFont::*func)() const)
  146. {
  147. DoSetFont((GetFont().*func)());
  148. }
  149. void DoEndAttr()
  150. {
  151. const Attr attr(m_attrs.top());
  152. m_attrs.pop();
  153. OnAttrEnd(attr);
  154. }
  155. // A helper class used to apply the given function to a wxFont object
  156. // depending on the value of an OptionalBool.
  157. template <typename T>
  158. struct FontModifier
  159. {
  160. FontModifier() { }
  161. void operator()(wxMarkupSpanAttributes::OptionalBool isIt,
  162. wxFont& font,
  163. void (wxFont::*func)(T),
  164. T noValue,
  165. T yesValue)
  166. {
  167. switch ( isIt )
  168. {
  169. case wxMarkupSpanAttributes::Unspecified:
  170. break;
  171. case wxMarkupSpanAttributes::No:
  172. (font.*func)(noValue);
  173. break;
  174. case wxMarkupSpanAttributes::Yes:
  175. (font.*func)(yesValue);
  176. break;
  177. }
  178. }
  179. };
  180. wxStack<Attr> m_attrs;
  181. wxDECLARE_NO_COPY_CLASS(wxMarkupParserAttrOutput);
  182. };
  183. #endif // _WX_PRIVATE_MARKUPPARSERATTR_H_