]> git.saurik.com Git - wxWidgets.git/commitdiff
Add support for stricken-through fonts.
authorVadim Zeitlin <vadim@wxwidgets.org>
Mon, 23 Jan 2012 11:28:28 +0000 (11:28 +0000)
committerVadim Zeitlin <vadim@wxwidgets.org>
Mon, 23 Jan 2012 11:28:28 +0000 (11:28 +0000)
Support stricken-through fonts in wxMSW and wxGTK (including special support
in wxStaticText and wxTextCtrl).

Closes #9907.

git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@70446 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

18 files changed:
docs/changes.txt
include/wx/font.h
include/wx/fontutil.h
include/wx/gtk/font.h
include/wx/gtk/private.h
include/wx/msw/font.h
include/wx/textctrl.h
interface/wx/font.h
samples/font/font.cpp
src/common/fontcmn.cpp
src/common/textcmn.cpp
src/gtk/dcclient.cpp
src/gtk/font.cpp
src/gtk/gnome/gprint.cpp
src/gtk/print.cpp
src/gtk/stattext.cpp
src/gtk/textctrl.cpp
src/msw/font.cpp

index 236c2c93efd3f17d61689eb6c437c6c795476590..f058577236ef36b659ab1580d6836f118f35a70b 100644 (file)
@@ -457,6 +457,7 @@ All:
 
 All (GUI):
 
+- Added strike-through support to wxFont (Igor Korot).
 - Added wxFilePickerCtrl::SetInitialDirectory().
 - Added wxDataViewItemAttr::SetBackgroundColour() and implemented it in generic
   wxDataViewCtrl (Andrew Xu).
index 0a7623ee49b9861fe0088a7ead9dea26a9b430cc..27f42bbca8588a81560a421699d1ade932f91657 100644 (file)
@@ -227,6 +227,7 @@ public:
     virtual wxFontStyle GetStyle() const = 0;
     virtual wxFontWeight GetWeight() const = 0;
     virtual bool GetUnderlined() const = 0;
+    virtual bool GetStrikethrough() const { return false; }
     virtual wxString GetFaceName() const = 0;
     virtual wxFontEncoding GetEncoding() const = 0;
     virtual const wxNativeFontInfo *GetNativeFontInfo() const = 0;
@@ -244,6 +245,7 @@ public:
     virtual void SetWeight( wxFontWeight weight ) = 0;
 
     virtual void SetUnderlined( bool underlined ) = 0;
+    virtual void SetStrikethrough( bool WXUNUSED(strikethrough) ) {}
     virtual void SetEncoding(wxFontEncoding encoding) = 0;
     virtual bool SetFaceName( const wxString& faceName );
     void SetNativeFontInfo(const wxNativeFontInfo& info)
@@ -356,6 +358,7 @@ WXDLLIMPEXP_CORE bool wxFromString(const wxString& str, wxFontBase* font);
     wxFont& MakeBold(); \
     wxFont& MakeItalic(); \
     wxFont& MakeUnderlined(); \
+    wxFont& MakeStrikethrough(); \
     wxFont& MakeLarger() { return Scale(1.2f); } \
     wxFont& MakeSmaller() { return Scale(1/1.2f); } \
     wxFont& Scale(float x); \
@@ -363,6 +366,7 @@ WXDLLIMPEXP_CORE bool wxFromString(const wxString& str, wxFontBase* font);
     wxFont Bold() const; \
     wxFont Italic() const; \
     wxFont Underlined() const; \
+    wxFont Strikethrough() const; \
     wxFont Larger() const { return Scaled(1.2f); } \
     wxFont Smaller() const { return Scaled(1/1.2f); } \
     wxFont Scaled(float x) const
index d52a6e3b771bb089e21bfcb2e8a432e1c359ccea..0291b9217622c406036469ecf95b3123fe9f9d85 100644 (file)
@@ -172,6 +172,7 @@ public:
     wxFontStyle   m_style;
     wxFontWeight  m_weight;
     bool          m_underlined;
+    bool          m_strikethrough;
     wxString      m_faceName;
     wxFontEncoding m_encoding;
 public :
@@ -187,6 +188,7 @@ public :
     wxFontStyle   style;
     wxFontWeight  weight;
     bool          underlined;
+    bool          strikethrough;
     wxString      faceName;
     wxFontEncoding encoding;
 #endif // platforms
@@ -224,6 +226,7 @@ public:
         SetStyle((wxFontStyle)font.GetStyle());
         SetWeight((wxFontWeight)font.GetWeight());
         SetUnderlined(font.GetUnderlined());
+        SetStrikethrough(font.GetStrikethrough());
 #if defined(__WXMSW__)
         if ( font.IsUsingSizeInPixels() )
             SetPixelSize(font.GetPixelSize());
@@ -252,6 +255,7 @@ public:
     wxFontStyle GetStyle() const;
     wxFontWeight GetWeight() const;
     bool GetUnderlined() const;
+    bool GetStrikethrough() const;
     wxString GetFaceName() const;
     wxFontFamily GetFamily() const;
     wxFontEncoding GetEncoding() const;
@@ -261,6 +265,7 @@ public:
     void SetStyle(wxFontStyle style);
     void SetWeight(wxFontWeight weight);
     void SetUnderlined(bool underlined);
+    void SetStrikethrough(bool strikethrough);
     bool SetFaceName(const wxString& facename);
     void SetFamily(wxFontFamily family);
     void SetEncoding(wxFontEncoding encoding);
index a73e9669cbca891f3df46920ace57e2dff6c37ce..d1c04e2d8be81c6fdd2463662ecdd3f0fe33751a 100644 (file)
@@ -88,6 +88,7 @@ public:
     virtual wxFontWeight GetWeight() const;
     virtual wxString GetFaceName() const;
     virtual bool GetUnderlined() const;
+    virtual bool GetStrikethrough() const;
     virtual wxFontEncoding GetEncoding() const;
     virtual const wxNativeFontInfo *GetNativeFontInfo() const;
     virtual bool IsFixedWidth() const;
@@ -98,6 +99,7 @@ public:
     virtual void SetWeight(wxFontWeight weight);
     virtual bool SetFaceName( const wxString& faceName );
     virtual void SetUnderlined( bool underlined );
+    virtual void SetStrikethrough(bool strikethrough);
     virtual void SetEncoding(wxFontEncoding encoding);
 
     wxDECLARE_COMMON_FONT_METHODS();
index 3ac71b7f5c06d953c3dbf0d403ab8558580cd8fa..261f483ee9e68b4bbeb4ab057f729e6bf9a3917e 100644 (file)
@@ -111,6 +111,21 @@ GtkWidget *GetSplitterWidget();
 GtkWidget *GetTextEntryWidget();
 GtkWidget *GetTreeWidget();
 
+// Set Pango attributes corresponding to the given font for the span 0..len (or
+// without any bounds if len == 0) in the specified layout. Currently only
+// underlined and strike-through attributes are handled by this function.
+//
+// Special "addDummyAttrs" parameter is used to work around a bug in old Pango
+// versions in wxWindowDCImpl::DoDrawText(), see comment there.
+//
+// If neither of them is specified, returns false, otherwise sets up the
+// attributes and returns true.
+//
+// This function is implemented in src/gtk/dcclient.cpp.
+bool
+SetPangoAttrsForFont(const wxFont& font, PangoLayout* layout, size_t len = 0,
+                     bool addDummyAttrs = false);
+
 } // wxGTKPrivate
 
 #endif // _WX_GTK_PRIVATE_H_
index eb4ed5b17e7f7c87127795f9cae2c99a067e0369..7a83f7665375fee5cac1ac0f14195a60c8373ded 100644 (file)
@@ -123,6 +123,7 @@ public:
     virtual wxFontStyle GetStyle() const;
     virtual wxFontWeight GetWeight() const;
     virtual bool GetUnderlined() const;
+    virtual bool GetStrikethrough() const;
     virtual wxString GetFaceName() const;
     virtual wxFontEncoding GetEncoding() const;
     virtual const wxNativeFontInfo *GetNativeFontInfo() const;
@@ -134,6 +135,7 @@ public:
     virtual void SetWeight(wxFontWeight weight);
     virtual bool SetFaceName(const wxString& faceName);
     virtual void SetUnderlined(bool underlined);
+    virtual void SetStrikethrough(bool strikethrough);
     virtual void SetEncoding(wxFontEncoding encoding);
 
     wxDECLARE_COMMON_FONT_METHODS();
index 94a7d55ed52c6dfe28324f3e71453d40b20d761f..f6833830de201cbcec4bde2e82c63698d7e0ed99 100644 (file)
@@ -171,11 +171,12 @@ enum wxTextAttrFlags
     wxTEXT_ATTR_FONT_WEIGHT          = 0x00000010,
     wxTEXT_ATTR_FONT_ITALIC          = 0x00000020,
     wxTEXT_ATTR_FONT_UNDERLINE       = 0x00000040,
+    wxTEXT_ATTR_FONT_STRIKETHROUGH   = 0x08000000,
     wxTEXT_ATTR_FONT_ENCODING        = 0x02000000,
     wxTEXT_ATTR_FONT_FAMILY          = 0x04000000,
     wxTEXT_ATTR_FONT = \
         ( wxTEXT_ATTR_FONT_FACE | wxTEXT_ATTR_FONT_SIZE | wxTEXT_ATTR_FONT_WEIGHT | \
-            wxTEXT_ATTR_FONT_ITALIC | wxTEXT_ATTR_FONT_UNDERLINE | wxTEXT_ATTR_FONT_ENCODING | wxTEXT_ATTR_FONT_FAMILY ),
+            wxTEXT_ATTR_FONT_ITALIC | wxTEXT_ATTR_FONT_UNDERLINE | wxTEXT_ATTR_FONT_STRIKETHROUGH | wxTEXT_ATTR_FONT_ENCODING | wxTEXT_ATTR_FONT_FAMILY ),
 
     wxTEXT_ATTR_ALIGNMENT            = 0x00000080,
     wxTEXT_ATTR_LEFT_INDENT          = 0x00000100,
@@ -317,6 +318,7 @@ public:
     void SetFontWeight(wxFontWeight fontWeight) { m_fontWeight = fontWeight; m_flags |= wxTEXT_ATTR_FONT_WEIGHT; }
     void SetFontFaceName(const wxString& faceName) { m_fontFaceName = faceName; m_flags |= wxTEXT_ATTR_FONT_FACE; }
     void SetFontUnderlined(bool underlined) { m_fontUnderlined = underlined; m_flags |= wxTEXT_ATTR_FONT_UNDERLINE; }
+    void SetFontStrikethrough(bool strikethrough) { m_fontStrikethrough = strikethrough; m_flags |= wxTEXT_ATTR_FONT_STRIKETHROUGH; }
     void SetFontEncoding(wxFontEncoding encoding) { m_fontEncoding = encoding; m_flags |= wxTEXT_ATTR_FONT_ENCODING; }
     void SetFontFamily(wxFontFamily family) { m_fontFamily = family; m_flags |= wxTEXT_ATTR_FONT_FAMILY; }
 
@@ -355,6 +357,7 @@ public:
     wxFontStyle GetFontStyle() const { return m_fontStyle; }
     wxFontWeight GetFontWeight() const { return m_fontWeight; }
     bool GetFontUnderlined() const { return m_fontUnderlined; }
+    bool GetFontStrikethrough() const { return m_fontStrikethrough; }
     const wxString& GetFontFaceName() const { return m_fontFaceName; }
     wxFontEncoding GetFontEncoding() const { return m_fontEncoding; }
     wxFontFamily GetFontFamily() const { return m_fontFamily; }
@@ -389,6 +392,7 @@ public:
     bool HasFontSize() const { return HasFlag(wxTEXT_ATTR_FONT_SIZE); }
     bool HasFontItalic() const { return HasFlag(wxTEXT_ATTR_FONT_ITALIC); }
     bool HasFontUnderlined() const { return HasFlag(wxTEXT_ATTR_FONT_UNDERLINE); }
+    bool HasFontStrikethrough() const { return HasFlag(wxTEXT_ATTR_FONT_STRIKETHROUGH); }
     bool HasFontFaceName() const { return HasFlag(wxTEXT_ATTR_FONT_FACE); }
     bool HasFontEncoding() const { return HasFlag(wxTEXT_ATTR_FONT_ENCODING); }
     bool HasFontFamily() const { return HasFlag(wxTEXT_ATTR_FONT_FAMILY); }
@@ -500,6 +504,7 @@ private:
     wxFontWeight        m_fontWeight;
     wxFontFamily        m_fontFamily;
     bool                m_fontUnderlined;
+    bool                m_fontStrikethrough;
     wxString            m_fontFaceName;
 
     // Character style
index cde804883bd4471945a1196871b6dca6d51b54e0..1304eaecb577c6d43f1578d330d777211f69359b 100644 (file)
@@ -112,8 +112,10 @@ enum wxFontFlag
     wxFONTFLAG_ANTIALIASED      = 1 << 4,
     wxFONTFLAG_NOT_ANTIALIASED  = 1 << 5,
 
-    /// underlined/strikethrough flags (default: no lines)
+    /// Underlined style (not underlined by default).
     wxFONTFLAG_UNDERLINED       = 1 << 6,
+
+    /// Strike-through style (only supported in wxMSW and wxGTK currently).
     wxFONTFLAG_STRIKETHROUGH    = 1 << 7,
 
     /// the mask of all currently used flags
@@ -404,6 +406,9 @@ public:
         The meaning of the remaining arguments is the same as in the other
         constructors, please see their documentation for details.
 
+        Notice that this constructor provides the only way of creating fonts
+        with strike-through style.
+
         @since 2.9.4
      */
     wxFont(int pointSize, wxFontFamily family, int flags,
@@ -541,6 +546,15 @@ public:
     */
     virtual bool GetUnderlined() const;
 
+    /**
+        Returns @true if the font is stricken-through, @false otherwise.
+
+        @see SetStrikethrough()
+
+        @since 2.9.4
+     */
+    virtual bool GetStrikethrough() const;
+
     /**
         Gets the font weight. See ::wxFontWeight for a list of valid weight identifiers.
 
@@ -627,6 +641,17 @@ public:
      */
     wxFont Underlined() const;
 
+    /**
+        Returns stricken-through version of this font.
+
+        Currently stricken-through fonts are only supported in wxMSW and wxGTK.
+
+        @see MakeStrikethrough()
+
+        @since 2.9.4
+     */
+    wxFont Strikethrough() const;
+
     /**
         Changes this font to be bold.
 
@@ -678,6 +703,17 @@ public:
      */
     wxFont& MakeUnderlined();
 
+    /**
+        Changes this font to be stricken-through.
+
+        Currently stricken-through fonts are only supported in wxMSW and wxGTK.
+
+        @see Strikethrough()
+
+        @since 2.9.4
+    */
+    wxFont& MakeStrikethrough();
+
     /**
         Changes the size of this font.
 
@@ -869,6 +905,20 @@ public:
     */
     virtual void SetUnderlined(bool underlined);
 
+    /**
+        Sets strike-through attribute of the font.
+
+        Currently stricken-through fonts are only supported in wxMSW and wxGTK.
+
+        @param strikethrough
+            @true to add strike-through style, @false to remove it.
+
+        @see GetStrikethrough()
+
+        @since 2.9.4
+    */
+    virtual void SetStrikethrough(bool strikethrough);
+
     /**
         Sets the font weight.
 
index 14d26792314641cbde5e44764b1f9a1653210394..4c78adc24d281d8d2010646baf6e653d547bb4dd 100644 (file)
@@ -107,6 +107,7 @@ public:
     void OnSlant(wxCommandEvent& event);
 
     void OnUnderline(wxCommandEvent& event);
+    void OnStrikethrough(wxCommandEvent& event);
 
     void OnwxPointerFont(wxCommandEvent& event);
     void OnwxSystemSettingsFont(wxCommandEvent& event);
@@ -178,6 +179,7 @@ enum
     Font_Slant,
 
     Font_Underlined,
+    Font_Strikethrough,
 
     // standard global wxFont objects:
     Font_wxNORMAL_FONT,
@@ -231,6 +233,7 @@ BEGIN_EVENT_TABLE(MyFrame, wxFrame)
     EVT_MENU(Font_Slant, MyFrame::OnSlant)
 
     EVT_MENU(Font_Underlined, MyFrame::OnUnderline)
+    EVT_MENU(Font_Strikethrough, MyFrame::OnStrikethrough)
 
     EVT_MENU(Font_wxNORMAL_FONT, MyFrame::OnwxPointerFont)
     EVT_MENU(Font_wxSMALL_FONT, MyFrame::OnwxPointerFont)
@@ -330,6 +333,8 @@ MyFrame::MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size)
     menuFont->AppendSeparator();
     menuFont->AppendCheckItem(Font_Underlined, wxT("&Underlined\tCtrl-U"),
                               wxT("Toggle underlined state"));
+    menuFont->AppendCheckItem(Font_Strikethrough, wxT("&Strikethrough"),
+                              wxT("Toggle strikethrough state"));
 
     menuFont->AppendSeparator();
     menuFont->Append(Font_SetNativeDesc,
@@ -735,6 +740,13 @@ void MyFrame::OnUnderline(wxCommandEvent& event)
     DoChangeFont(font);
 }
 
+void MyFrame::OnStrikethrough(wxCommandEvent& event)
+{
+    wxFont font = m_canvas->GetTextFont();
+    font.SetStrikethrough(event.IsChecked());
+    DoChangeFont(font);
+}
+
 void MyFrame::OnwxPointerFont(wxCommandEvent& event)
 {
     wxFont font;
@@ -813,6 +825,7 @@ void MyFrame::DoChangeFont(const wxFont& font, const wxColour& col)
     m_textctrl->SetFont(font);
     if ( col.IsOk() )
         m_textctrl->SetForegroundColour(col);
+    m_textctrl->Refresh();
 
     // update the state of the bold/italic/underlined menu items
     wxMenuBar *mbar = GetMenuBar();
@@ -827,6 +840,7 @@ void MyFrame::DoChangeFont(const wxFont& font, const wxColour& col)
 #endif
 
         mbar->Check(Font_Underlined, font.GetUnderlined());
+        mbar->Check(Font_Strikethrough, font.GetStrikethrough());
     }
 }
 
index de35aa96d1a96fb3bf36f74fbefec1ab004bfc76..fed694a96d433a7217a9f106c897c36d2733d777 100644 (file)
@@ -113,6 +113,8 @@ wxPROPERTY( Weight, wxFontWeight, SetWeight, GetWeight, (wxFontWeight)wxNORMAL,
            wxT("Helpstring"), wxT("group")) // wxFontWeight
 wxPROPERTY( Underlined, bool, SetUnderlined, GetUnderlined, false, 0 /*flags*/, \
            wxT("Helpstring"), wxT("group"))
+wxPROPERTY( Strikethrough, bool, SetStrikethrough, GetStrikethrough, false, 0, \
+                   wxT("Helpstring"), wxT("group"))
 wxPROPERTY( Face, wxString, SetFaceName, GetFaceName, wxEMPTY_PARAMETER_VALUE, \
            0 /*flags*/, wxT("Helpstring"), wxT("group"))
 wxPROPERTY( Encoding, wxFontEncoding, SetEncoding, GetEncoding, \
@@ -307,6 +309,7 @@ void wxFontBase::DoSetNativeFontInfo(const wxNativeFontInfo& info)
     SetStyle(info.style);
     SetWeight(info.weight);
     SetUnderlined(info.underlined);
+    SetStrikethrough(info.strikethrough);
     SetFaceName(info.faceName);
     SetEncoding(info.encoding);
 #else
@@ -394,6 +397,7 @@ bool wxFontBase::operator==(const wxFont& font) const
             GetStyle() == font.GetStyle() &&
             GetWeight() == font.GetWeight() &&
             GetUnderlined() == font.GetUnderlined() &&
+            GetStrikethrough() == font.GetStrikethrough() &&
             GetFaceName().IsSameAs(font.GetFaceName(), false) &&
             GetEncoding() == font.GetEncoding()
            );
@@ -533,6 +537,19 @@ wxFont wxFont::Underlined() const
     return font;
 }
 
+wxFont wxFont::Strikethrough() const
+{
+    wxFont font(*this);
+    font.MakeStrikethrough();
+    return font;
+}
+
+wxFont& wxFont::MakeStrikethrough()
+{
+    SetStrikethrough(true);
+    return *this;
+}
+
 wxFont& wxFont::Scale(float x)
 {
     SetPointSize(int(x*GetPointSize() + 0.5));
@@ -577,19 +594,22 @@ void wxNativeFontInfo::SetFaceName(const wxArrayString& facenames)
 
 // These are the generic forms of FromString()/ToString.
 //
-// convert to/from the string representation: format is
-//      version;pointsize;family;style;weight;underlined;facename;encoding
+// convert to/from the string representation: the general format is
+// "version;the rest..." with currently defined versions being:
+//
+//      0;pointsize;family;style;weight;underlined;facename;encoding
+//      1;pointsize;family;style;weight;underlined;strikethrough;facename;encoding
 
 bool wxNativeFontInfo::FromString(const wxString& s)
 {
     long l;
+    short version;
 
     wxStringTokenizer tokenizer(s, wxT(";"));
 
     wxString token = tokenizer.GetNextToken();
-    //
-    //  Ignore the version for now
-    //
+    if ( !token.ToLong(&version) || version < 0 || version > 1 )
+        return false;
 
     token = tokenizer.GetNextToken();
     if ( !token.ToLong(&l) )
@@ -616,6 +636,14 @@ bool wxNativeFontInfo::FromString(const wxString& s)
         return false;
     underlined = l != 0;
 
+    if ( version == 1 )
+    {
+        token = tokenizer.GetNextToken();
+        if ( !token.ToLong(&l) )
+            return false;
+        strikethrough = l != 0;
+    }
+
     faceName = tokenizer.GetNextToken();
 
 #ifndef __WXMAC__
@@ -635,13 +663,14 @@ wxString wxNativeFontInfo::ToString() const
 {
     wxString s;
 
-    s.Printf(wxT("%d;%d;%d;%d;%d;%d;%s;%d"),
-             0,                                 // version
+    s.Printf(wxT("%d;%d;%d;%d;%d;%d;%d;%s;%d"),
+             1,                                 // version
              pointSize,
              family,
              (int)style,
              (int)weight,
              underlined,
+             strikethrough,
              faceName.GetData(),
              (int)encoding);
 
@@ -655,6 +684,7 @@ void wxNativeFontInfo::Init()
     style = wxFONTSTYLE_NORMAL;
     weight = wxFONTWEIGHT_NORMAL;
     underlined = false;
+    strikethrough = false;
     faceName.clear();
     encoding = wxFONTENCODING_DEFAULT;
 }
@@ -679,6 +709,11 @@ bool wxNativeFontInfo::GetUnderlined() const
     return underlined;
 }
 
+bool wxNativeFontInfo::GetStrikethrough() const
+{
+    return strikethrough;
+}
+
 wxString wxNativeFontInfo::GetFaceName() const
 {
     return faceName;
@@ -714,6 +749,11 @@ void wxNativeFontInfo::SetUnderlined(bool underlined_)
     underlined = underlined_;
 }
 
+void wxNativeFontInfo::SetStrikethrough(bool strikethrough_)
+{
+    strikethrough = strikethrough_;
+}
+
 bool wxNativeFontInfo::SetFaceName(const wxString& facename_)
 {
     faceName = facename_;
@@ -750,6 +790,11 @@ wxString wxNativeFontInfo::ToUserString() const
         desc << _("underlined");
     }
 
+    if ( GetStrikethrough() )
+    {
+        desc << _("strikethrough");
+    }
+
     switch ( GetWeight() )
     {
         default:
@@ -922,6 +967,10 @@ bool wxNativeFontInfo::FromUserString(const wxString& s)
         {
             SetUnderlined(true);
         }
+        else if ( token == wxT("strikethrough") || token == _("strikethrough") )
+        {
+            SetStrikethrough(true);
+        }
         else if ( token == wxT("light") || token == _("light") )
         {
             SetWeight(wxFONTWEIGHT_LIGHT);
index d64baccfb743c73d8cf8a6f0a9cc7409638e4320..3b75cba9c8a889cafd4cb80fb8929710430bb89a 100644 (file)
@@ -403,6 +403,10 @@ wxFont wxTextAttr::GetFont() const
     if (HasFontUnderlined())
         underlined = GetFontUnderlined();
 
+    bool strikethrough = false;
+    if ( HasFontStrikethrough() )
+        strikethrough = GetFontStrikethrough();
+
     wxString fontFaceName;
     if (HasFontFaceName())
         fontFaceName = GetFontFaceName();
@@ -416,6 +420,8 @@ wxFont wxTextAttr::GetFont() const
         fontFamily = GetFontFamily();
 
     wxFont font(fontSize, fontFamily, fontStyle, fontWeight, underlined, fontFaceName, encoding);
+    if ( strikethrough )
+        font.SetStrikethrough( true );
     return font;
 }
 
@@ -437,6 +443,9 @@ bool wxTextAttr::GetFontAttributes(const wxFont& font, int flags)
     if (flags & wxTEXT_ATTR_FONT_UNDERLINE)
         m_fontUnderlined = font.GetUnderlined();
 
+    if (flags & wxTEXT_ATTR_FONT_STRIKETHROUGH)
+        m_fontStrikethrough = font.GetStrikethrough();
+
     if (flags & wxTEXT_ATTR_FONT_FACE)
         m_fontFaceName = font.GetFaceName();
 
@@ -500,6 +509,12 @@ bool wxTextAttr::Apply(const wxTextAttr& style, const wxTextAttr* compareWith)
             destStyle.SetFontUnderlined(style.GetFontUnderlined());
     }
 
+    if (style.HasFontStrikethrough())
+    {
+        if (!(compareWith && compareWith->HasFontStrikethrough() && compareWith->GetFontStrikethrough() == style.GetFontStrikethrough()))
+            destStyle.SetFontStrikethrough(style.GetFontStrikethrough());
+    }
+
     if (style.HasFontFaceName())
     {
         if (!(compareWith && compareWith->HasFontFaceName() && compareWith->GetFontFaceName() == style.GetFontFaceName()))
index f9a123a20f2caaf4810ddc73b483e409b7839b0a..398d319bd8787c552577c21480f770db6d5992c9 100644 (file)
@@ -26,6 +26,8 @@
 #include "wx/gtk/private.h"
 #include "wx/gtk/private/object.h"
 
+using wxGTKPrivate::SetPangoAttrsForFont;
+
 //-----------------------------------------------------------------------------
 // local defines
 //-----------------------------------------------------------------------------
@@ -1408,33 +1410,8 @@ void wxWindowDCImpl::DoDrawText(const wxString& text,
     }
 
     pango_layout_set_text(m_layout, data, datalen);
-
-    if (underlined)
-    {
-        PangoAttrList *attrs = pango_attr_list_new();
-        PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
-        a->start_index = 0;
-        a->end_index = datalen;
-        pango_attr_list_insert(attrs, a);
-
-        if (needshack)
-        {
-            // dummy colour for the leading space
-            a = pango_attr_foreground_new (0x0057, 0x52A9, 0xD614);
-            a->start_index = 0;
-            a->end_index = 1;
-            pango_attr_list_insert(attrs, a);
-
-            // dummy colour for the trailing space
-            a = pango_attr_foreground_new (0x0057, 0x52A9, 0xD614);
-            a->start_index = datalen - 1;
-            a->end_index = datalen;
-            pango_attr_list_insert(attrs, a);
-        }
-
-        pango_layout_set_attributes(m_layout, attrs);
-        pango_attr_list_unref(attrs);
-    }
+    const bool
+        setAttrs = SetPangoAttrsForFont(m_font, m_layout, datalen, needshack);
 
     int oldSize = 0;
     const bool isScaled = fabs(m_scaleY - 1.0) > 0.00001;
@@ -1473,7 +1450,7 @@ void wxWindowDCImpl::DoDrawText(const wxString& text,
          // actually apply unscaled font
          pango_layout_set_font_description( m_layout, m_fontdesc );
     }
-    if (underlined)
+    if (setAttrs)
     {
         // undo underline attributes setting:
         pango_layout_set_attributes(m_layout, NULL);
@@ -1499,16 +1476,7 @@ void wxWindowDCImpl::DoDrawRotatedText( const wxString &text, wxCoord x, wxCoord
         y = YLOG2DEV(y);
 
         pango_layout_set_text(m_layout, wxGTK_CONV(text), -1);
-
-        if (m_font.GetUnderlined())
-        {
-            PangoAttrList *attrs = pango_attr_list_new();
-            PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
-            pango_attr_list_insert(attrs, a);
-            pango_layout_set_attributes(m_layout, attrs);
-            pango_attr_list_unref(attrs);
-        }
-
+        SetPangoAttrsForFont( m_font, m_layout );
         int oldSize = 0;
         const bool isScaled = fabs(m_scaleY - 1.0) > 0.00001;
         if (isScaled)
@@ -1561,7 +1529,7 @@ void wxWindowDCImpl::DoDrawRotatedText( const wxString &text, wxCoord x, wxCoord
         gdk_draw_layout_with_colors(m_gdkwindow, m_textGC, x+minX, y+minY,
                                     m_layout, NULL, bg_col);
 
-        if (m_font.GetUnderlined())
+        if (m_font.GetUnderlined() || m_font.GetStrikethrough())
             pango_layout_set_attributes(m_layout, NULL);
 
         // clean up the transformation matrix
@@ -2304,6 +2272,62 @@ int wxWindowDCImpl::GetDepth() const
     return gdk_drawable_get_depth(m_gdkwindow);
 }
 
+bool
+wxGTKPrivate::SetPangoAttrsForFont(const wxFont& font,
+                                   PangoLayout *layout,
+                                   size_t len,
+                                   bool addDummyAttrs)
+{
+    if ( !font.IsOk() || !(font.GetUnderlined() || font.GetStrikethrough()) )
+        return false;
+
+    PangoAttrList* attrs = pango_attr_list_new();
+
+    if ( font.GetUnderlined() )
+    {
+        PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
+        if ( len )
+        {
+            a->start_index = 0;
+            a->end_index = len;
+        }
+        pango_attr_list_insert(attrs, a);
+
+        // Add dummy attributes (use colour as it's invisible anyhow for 0
+        // width spaces) to ensure that the spaces in the beginning/end of the
+        // string are underlined too.
+        if ( addDummyAttrs )
+        {
+            wxASSERT_MSG( len > 2, "Must have 0-width spaces at string ends" );
+
+            a = pango_attr_foreground_new (0x0057, 0x52A9, 0xD614);
+            a->start_index = 0;
+            a->end_index = 1;
+            pango_attr_list_insert(attrs, a);
+
+            a = pango_attr_foreground_new (0x0057, 0x52A9, 0xD614);
+            a->start_index = len - 1;
+            a->end_index = len;
+            pango_attr_list_insert(attrs, a);
+        }
+    }
+
+    if ( font.GetStrikethrough() )
+    {
+        PangoAttribute *a = pango_attr_strikethrough_new( TRUE );
+        if ( len )
+        {
+            a->start_index = 0;
+            a->end_index = len;
+        }
+        pango_attr_list_insert(attrs, a);
+    }
+
+    pango_layout_set_attributes(layout, attrs);
+    pango_attr_list_unref(attrs);
+
+    return true;
+}
 
 //-----------------------------------------------------------------------------
 // wxClientDCImpl
index 5ca1b2b600049bccc51795395affeebb107bf003..1ae79d7eb7bbc4f73d2bcc91dc8a2750735e44ec 100644 (file)
@@ -52,6 +52,7 @@ public:
                   wxFontStyle style = wxFONTSTYLE_NORMAL,
                   wxFontWeight weight = wxFONTWEIGHT_NORMAL,
                   bool underlined = false,
+                  bool strikethrough = false,
                   const wxString& faceName = wxEmptyString,
                   wxFontEncoding encoding = wxFONTENCODING_DEFAULT);
 
@@ -69,6 +70,7 @@ public:
     void SetStyle(wxFontStyle style);
     void SetWeight(wxFontWeight weight);
     void SetUnderlined(bool underlined);
+    void SetStrikethrough(bool strikethrough);
     bool SetFaceName(const wxString& facename);
     void SetEncoding(wxFontEncoding encoding);
 
@@ -82,6 +84,7 @@ protected:
               wxFontStyle style,
               wxFontWeight weight,
               bool underlined,
+              bool strikethrough,
               const wxString& faceName,
               wxFontEncoding encoding);
 
@@ -90,7 +93,7 @@ protected:
 
 private:
     bool            m_underlined;
-
+    bool            m_strikethrough;
     // The native font info: basically a PangoFontDescription
     wxNativeFontInfo m_nativeFontInfo;
 
@@ -108,6 +111,7 @@ void wxFontRefData::Init(int pointSize,
                          wxFontStyle style,
                          wxFontWeight weight,
                          bool underlined,
+                         bool strikethrough,
                          const wxString& faceName,
                          wxFontEncoding WXUNUSED(encoding))
 {
@@ -115,6 +119,7 @@ void wxFontRefData::Init(int pointSize,
         family = wxFONTFAMILY_SWISS;
 
     m_underlined = underlined;
+    m_strikethrough = strikethrough;
 
     // Create native font info
     m_nativeFontInfo.description = pango_font_description_new();
@@ -149,12 +154,14 @@ void wxFontRefData::InitFromNative()
 
     // Pango description are never underlined
     m_underlined = false;
+    m_strikethrough = false;
 }
 
 wxFontRefData::wxFontRefData( const wxFontRefData& data )
              : wxGDIRefData()
 {
     m_underlined = data.m_underlined;
+    m_strikethrough = data.m_strikethrough;
 
     // Forces a copy of the internal data.  wxNativeFontInfo should probably
     // have a copy ctor and assignment operator to fix this properly but that
@@ -163,11 +170,11 @@ wxFontRefData::wxFontRefData( const wxFontRefData& data )
 }
 
 wxFontRefData::wxFontRefData(int size, wxFontFamily family, wxFontStyle style,
-                             wxFontWeight weight, bool underlined,
+                             wxFontWeight weight, bool underlined, bool strikethrough,
                              const wxString& faceName,
                              wxFontEncoding encoding)
 {
-    Init(size, family, style, weight, underlined, faceName, encoding);
+    Init(size, family, style, weight, underlined, strikethrough, faceName, encoding);
 }
 
 wxFontRefData::wxFontRefData(const wxString& nativeFontInfoString)
@@ -244,6 +251,11 @@ void wxFontRefData::SetUnderlined(bool underlined)
     // here we just need to save the underlined attribute
 }
 
+void wxFontRefData::SetStrikethrough(bool strikethrough)
+{
+    m_strikethrough = strikethrough;
+}
+
 bool wxFontRefData::SetFaceName(const wxString& facename)
 {
     return m_nativeFontInfo.SetFaceName(facename);
@@ -287,7 +299,7 @@ wxFont::wxFont(int pointSize,
                                   GetStyleFromFlags(flags),
                                   GetWeightFromFlags(flags),
                                   GetUnderlinedFromFlags(flags),
-                                  face, encoding);
+                                  false, face, encoding);
 }
 
 bool wxFont::Create( int pointSize,
@@ -301,7 +313,7 @@ bool wxFont::Create( int pointSize,
     UnRef();
 
     m_refData = new wxFontRefData(pointSize, family, style, weight,
-                                  underlined, face, encoding);
+                                  underlined, false, face, encoding);
 
     return true;
 }
@@ -369,6 +381,13 @@ bool wxFont::GetUnderlined() const
     return M_FONTDATA->m_underlined;
 }
 
+bool wxFont::GetStrikethrough() const
+{
+    wxCHECK_MSG( IsOk(), false, wxT("invalid font") );
+
+    return M_FONTDATA->m_strikethrough;
+}
+
 wxFontEncoding wxFont::GetEncoding() const
 {
     wxCHECK_MSG( IsOk(), wxFONTENCODING_SYSTEM, wxT("invalid font") );
@@ -438,6 +457,13 @@ void wxFont::SetUnderlined(bool underlined)
     M_FONTDATA->SetUnderlined(underlined);
 }
 
+void wxFont::SetStrikethrough(bool strikethrough)
+{
+    AllocExclusive();
+
+    M_FONTDATA->SetStrikethrough(strikethrough);
+}
+
 void wxFont::SetEncoding(wxFontEncoding encoding)
 {
     AllocExclusive();
index 59023144174fd76209ae3aba8cbf2217019e2266..807477e2e06f05aa4c4b1ff1fe8de30cb2c1dfb4 100644 (file)
@@ -1592,23 +1592,13 @@ void wxGnomePrinterDCImpl::DoDrawRotatedText(const wxString& text, wxCoord x, wx
     double xx = XLOG2DEV(x);
     double yy = YLOG2DEV(y);
 
-    bool underlined = m_font.IsOk() && m_font.GetUnderlined();
-
     const wxScopedCharBuffer data(text.utf8_str());
 
     size_t datalen = strlen(data);
     pango_layout_set_text( m_layout, data, datalen);
 
-    if (underlined)
-    {
-        PangoAttrList *attrs = pango_attr_list_new();
-        PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
-        a->start_index = 0;
-        a->end_index = datalen;
-        pango_attr_list_insert(attrs, a);
-        pango_layout_set_attributes(m_layout, attrs);
-        pango_attr_list_unref(attrs);
-    }
+    const bool
+      setAttrs = wxGTKPrivate::SetPangoAttrsForFont(m_font, m_layout, datalen);
 
     if (m_textForegroundColour.IsOk())
     {
@@ -1656,7 +1646,7 @@ void wxGnomePrinterDCImpl::DoDrawRotatedText(const wxString& text, wxCoord x, wx
 
     gs_libGnomePrint->gnome_print_grestore( m_gpc );
 
-    if (underlined)
+    if (setAttrs)
     {
         // undo underline attributes setting:
         pango_layout_set_attributes(m_layout, NULL);
index ec14f2c4c9467a13e98c3db58b2bb667da251de0..bb207524c0a486d3b169b9d5e091eeb64efc67ac 100644 (file)
@@ -1738,24 +1738,13 @@ void wxGtkPrinterDCImpl::DoDrawRotatedText(const wxString& text, wxCoord x, wxCo
 
     angle = -angle;
 
-    bool underlined = m_font.IsOk() && m_font.GetUnderlined();
-
     const wxScopedCharBuffer data = text.utf8_str();
 
     size_t datalen = strlen(data);
     pango_layout_set_text( m_layout, data, datalen);
 
-    if (underlined)
-    {
-        PangoAttrList *attrs = pango_attr_list_new();
-        PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
-        a->start_index = 0;
-        a->end_index = datalen;
-        pango_attr_list_insert(attrs, a);
-        pango_layout_set_attributes(m_layout, attrs);
-        pango_attr_list_unref(attrs);
-    }
-
+    const bool
+      setAttrs = wxGTKPrivate::SetPangoAttrsForFont(m_font, m_layout, datalen);
     if (m_textForegroundColour.IsOk())
     {
         unsigned char red = m_textForegroundColour.Red();
@@ -1816,7 +1805,7 @@ void wxGtkPrinterDCImpl::DoDrawRotatedText(const wxString& text, wxCoord x, wxCo
 
     cairo_restore( m_cairo );
 
-    if (underlined)
+    if (setAttrs)
     {
         // Undo underline attributes setting
         pango_layout_set_attributes(m_layout, NULL);
index 7e8bfead1e8843db9c9ec2de4f32a8d5cfb86b64..24618217144e86ab498743c5470c639d344efe27 100644 (file)
@@ -153,31 +153,48 @@ bool wxStaticText::DoSetLabelMarkup(const wxString& markup)
 bool wxStaticText::SetFont( const wxFont &font )
 {
     const bool wasUnderlined = GetFont().GetUnderlined();
+    const bool wasStrickenThrough = GetFont().GetStrikethrough();
 
     bool ret = wxControl::SetFont(font);
 
-    if ( font.GetUnderlined() != wasUnderlined )
-    {
-        // the underlines for mnemonics are incompatible with using attributes
-        // so turn them off when setting underlined font and restore them when
-        // unsetting it
-        gtk_label_set_use_underline(GTK_LABEL(m_widget), wasUnderlined);
+    const bool isUnderlined = GetFont().GetUnderlined();
+    const bool isStrickenThrough = GetFont().GetStrikethrough();
 
-        if ( wasUnderlined )
-        {
-            // it's not underlined any more, remove the attributes we set
-            gtk_label_set_attributes(GTK_LABEL(m_widget), NULL);
-        }
-        else // the text is underlined now
+    if ( (isUnderlined != wasUnderlined) ||
+            (isStrickenThrough != wasStrickenThrough) )
+    {
+        // We need to update the Pango attributes used for the text.
+        if ( isUnderlined || isStrickenThrough )
         {
-            PangoAttrList *attrs = pango_attr_list_new();
-            PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
-            a->start_index = 0;
-            a->end_index = (guint)-1;
-            pango_attr_list_insert(attrs, a);
+            PangoAttrList* const attrs = pango_attr_list_new();
+            if ( isUnderlined )
+            {
+                PangoAttribute *a = pango_attr_underline_new(PANGO_UNDERLINE_SINGLE);
+                a->start_index = 0;
+                a->end_index = (guint)-1;
+                pango_attr_list_insert(attrs, a);
+            }
+
+            if ( isStrickenThrough )
+            {
+                PangoAttribute *a = pango_attr_strikethrough_new( TRUE );
+                a->start_index = 0;
+                a->end_index = (guint) -1;
+                pango_attr_list_insert(attrs, a);
+            }
+
             gtk_label_set_attributes(GTK_LABEL(m_widget), attrs);
             pango_attr_list_unref(attrs);
         }
+        else // No special attributes any more.
+        {
+            // Just remove any attributes we had set.
+            gtk_label_set_attributes(GTK_LABEL(m_widget), NULL);
+        }
+
+        // The underlines for mnemonics are incompatible with using attributes
+        // so turn them off when setting underlined font.
+        gtk_label_set_use_underline(GTK_LABEL(m_widget), !isUnderlined);
     }
 
     // adjust the label size to the new label unless disabled
index 6920e299b687104cc4f6f68c022ccfd051bcf781..8a395587999542fe668e9e5e2cb766afb2de0858 100644 (file)
@@ -110,6 +110,18 @@ static void wxGtkTextApplyTagsFromAttr(GtkWidget *text,
                                                   NULL );
             gtk_text_buffer_apply_tag (text_buffer, tag, start, end);
         }
+        if ( font.GetStrikethrough() )
+        {
+            g_snprintf(buf, sizeof(buf), "WXFONTSTRIKETHROUGH");
+            tag = gtk_text_tag_table_lookup( gtk_text_buffer_get_tag_table( text_buffer ),
+                                             buf );
+            if (!tag)
+                tag = gtk_text_buffer_create_tag( text_buffer, buf,
+                                                  "strikethrough-set", TRUE,
+                                                  "strikethrough", TRUE,
+                                                  NULL );
+            gtk_text_buffer_apply_tag (text_buffer, tag, start, end);
+        }
     }
 
     if (attr.HasTextColour())
index 72294a58b189f31095de95e4ec37ca248dd0578c..b0e73148cbd842f02ba35b1f7e20702c51b7ef65 100644 (file)
@@ -63,7 +63,7 @@ public:
     wxFontRefData()
     {
         Init(-1, wxSize(0,0), false, wxFONTFAMILY_DEFAULT, wxFONTSTYLE_NORMAL,
-             wxFONTWEIGHT_NORMAL, false, wxEmptyString,
+             wxFONTWEIGHT_NORMAL, false, false, wxEmptyString,
              wxFONTENCODING_DEFAULT);
     }
 
@@ -74,11 +74,12 @@ public:
                   wxFontStyle style,
                   wxFontWeight weight,
                   bool underlined,
+                  bool strikethrough,
                   const wxString& faceName,
                   wxFontEncoding encoding)
     {
         Init(size, pixelSize, sizeUsingPixels, family, style, weight,
-             underlined, faceName, encoding);
+             underlined, strikethrough, faceName, encoding);
     }
 
     wxFontRefData(const wxNativeFontInfo& info, WXHFONT hFont = 0)
@@ -134,6 +135,11 @@ public:
         return m_nativeFontInfo.GetUnderlined();
     }
 
+    bool GetStrikethrough() const
+    {
+        return m_nativeFontInfo.GetStrikethrough();
+    }
+
     wxString GetFaceName() const
     {
         wxString facename = m_nativeFontInfo.GetFaceName();
@@ -225,6 +231,13 @@ public:
         m_nativeFontInfo.SetUnderlined(underlined);
     }
 
+    void SetStrikethrough(bool strikethrough)
+    {
+        Free();
+
+        m_nativeFontInfo.SetStrikethrough(strikethrough);
+    }
+
     void SetEncoding(wxFontEncoding encoding)
     {
         Free();
@@ -262,6 +275,7 @@ protected:
               wxFontStyle style,
               wxFontWeight weight,
               bool underlined,
+              bool strikethrough,
               const wxString& faceName,
               wxFontEncoding encoding);
 
@@ -336,6 +350,7 @@ void wxFontRefData::Init(int pointSize,
                          wxFontStyle style,
                          wxFontWeight weight,
                          bool underlined,
+                         bool strikethrough,
                          const wxString& faceName,
                          wxFontEncoding encoding)
 {
@@ -350,6 +365,7 @@ void wxFontRefData::Init(int pointSize,
     SetStyle(style);
     SetWeight(weight);
     SetUnderlined(underlined);
+    SetStrikethrough(strikethrough);
 
     // set the family/facename
     SetFamily(family);
@@ -463,6 +479,11 @@ bool wxNativeFontInfo::GetUnderlined() const
     return lf.lfUnderline != 0;
 }
 
+bool wxNativeFontInfo::GetStrikethrough() const
+{
+    return lf.lfStrikeOut != 0;
+}
+
 wxString wxNativeFontInfo::GetFaceName() const
 {
     return lf.lfFaceName;
@@ -583,6 +604,11 @@ void wxNativeFontInfo::SetUnderlined(bool underlined)
     lf.lfUnderline = underlined;
 }
 
+void wxNativeFontInfo::SetStrikethrough(bool strikethrough)
+{
+    lf.lfStrikeOut = strikethrough;
+}
+
 bool wxNativeFontInfo::SetFaceName(const wxString& facename)
 {
     wxStrlcpy(lf.lfFaceName, facename.c_str(), WXSIZEOF(lf.lfFaceName));
@@ -789,7 +815,7 @@ wxFont::wxFont(int pointSize,
                                   GetStyleFromFlags(flags),
                                   GetWeightFromFlags(flags),
                                   GetUnderlinedFromFlags(flags),
-                                  face, encoding);
+                                  false, face, encoding);
 }
 
 bool wxFont::Create(const wxNativeFontInfo& info, WXHFONT hFont)
@@ -822,7 +848,7 @@ bool wxFont::DoCreate(int pointSize,
 
     m_refData = new wxFontRefData(pointSize, pixelSize, sizeUsingPixels,
                                   family, style, weight,
-                                  underlined, faceName, encoding);
+                                  underlined, false, faceName, encoding);
 
     return RealizeResource();
 }
@@ -944,6 +970,13 @@ void wxFont::SetUnderlined(bool underlined)
     M_FONTDATA->SetUnderlined(underlined);
 }
 
+void wxFont::SetStrikethrough(bool strikethrough)
+{
+    AllocExclusive();
+
+    M_FONTDATA->SetStrikethrough(strikethrough);
+}
+
 void wxFont::SetEncoding(wxFontEncoding encoding)
 {
     AllocExclusive();
@@ -1009,6 +1042,13 @@ bool wxFont::GetUnderlined() const
     return M_FONTDATA->GetUnderlined();
 }
 
+bool wxFont::GetStrikethrough() const
+{
+    wxCHECK_MSG( IsOk(), false, wxT("invalid font") );
+
+    return M_FONTDATA->GetStrikethrough();
+}
+
 wxString wxFont::GetFaceName() const
 {
     wxCHECK_MSG( IsOk(), wxEmptyString, wxT("invalid font") );