[Libreoffice-commits] core.git: vcl/headless vcl/inc vcl/Library_vcl.mk vcl/quartz vcl/source vcl/unx vcl/win

Chris Sherlock chris.sherlock79 at gmail.com
Mon Jan 11 21:36:29 PST 2016


 vcl/Library_vcl.mk                             |    1 
 vcl/headless/svptext.cxx                       |    5 
 vcl/inc/cairotextrender.hxx                    |    3 
 vcl/inc/fontattributes.hxx                     |  144 ------------
 vcl/inc/fontinstance.hxx                       |    9 
 vcl/inc/headless/svpgdi.hxx                    |    3 
 vcl/inc/impfontmetricdata.hxx                  |  182 ++++++++++++++++
 vcl/inc/quartz/salgdi.h                        |    5 
 vcl/inc/salgdi.hxx                             |    4 
 vcl/inc/textrender.hxx                         |    3 
 vcl/inc/unx/genpspgraphics.h                   |    3 
 vcl/inc/unx/glyphcache.hxx                     |   15 -
 vcl/inc/unx/salgdi.h                           |    2 
 vcl/inc/win/salgdi.h                           |    3 
 vcl/quartz/ctfonts.cxx                         |   20 -
 vcl/quartz/salgdi.cxx                          |    6 
 vcl/source/font/fontattributes.cxx             |  275 ------------------------
 vcl/source/font/fontinstance.cxx               |    2 
 vcl/source/font/fontmetric.cxx                 |  279 +++++++++++++++++++++++++
 vcl/source/gdi/pdfwriter_impl.cxx              |   84 +++----
 vcl/source/gdi/pdfwriter_impl.hxx              |    1 
 vcl/source/gdi/print.cxx                       |    2 
 vcl/source/gdi/virdev.cxx                      |    5 
 vcl/source/outdev/font.cxx                     |   35 +--
 vcl/source/outdev/text.cxx                     |    8 
 vcl/source/outdev/textline.cxx                 |   62 ++---
 vcl/unx/generic/gdi/cairotextrender.cxx        |    5 
 vcl/unx/generic/gdi/salgdi3.cxx                |    4 
 vcl/unx/generic/glyphs/freetype_glyphcache.cxx |    4 
 vcl/unx/generic/print/genpspgraphics.cxx       |   25 +-
 vcl/win/gdi/salfont.cxx                        |   59 ++---
 vcl/win/gdi/winlayout.cxx                      |    2 
 32 files changed, 660 insertions(+), 600 deletions(-)

New commits:
commit b4b0cc2a5eef42434444e51fda4a13fc48183aa0
Author: Chris Sherlock <chris.sherlock79 at gmail.com>
Date:   Tue Jan 12 14:47:34 2016 +1100

    vcl: resplit FontAttributes from ImplFontMetricData
    
    The change I made in commit 7b974e056df3 ("vcl: merge
    ImplFontMetricData with ImplFontAttributes") was... ill-advised. For
    starters, there really needs to be this split as FontSelectPattern
    needs it, and PhysicalFontFace only requires the font attributes, not
    the metric data.
    
    So the merge was unfortunately, in my mind, a failure and I'm manually
    backing it out now.
    
    Change-Id: Iac38f0815f984541e2f55099c965376dd88eeb43
    Reviewed-on: https://gerrit.libreoffice.org/21380
    Tested-by: Jenkins <ci at libreoffice.org>
    Reviewed-by: Chris Sherlock <chris.sherlock79 at gmail.com>

diff --git a/vcl/Library_vcl.mk b/vcl/Library_vcl.mk
index f35ce6e..d9bc47f 100644
--- a/vcl/Library_vcl.mk
+++ b/vcl/Library_vcl.mk
@@ -396,6 +396,7 @@ $(eval $(call gb_Library_add_exception_objects,vcl,\
     vcl/source/font/fontinstance \
     vcl/source/font/fontcache \
     vcl/source/font/fontcharmap \
+    vcl/source/font/fontmetric \
     vcl/source/fontsubset/cff \
     vcl/source/fontsubset/fontsubset \
     vcl/source/fontsubset/gsub \
diff --git a/vcl/headless/svptext.cxx b/vcl/headless/svptext.cxx
index 4201649..4c40086 100644
--- a/vcl/headless/svptext.cxx
+++ b/vcl/headless/svptext.cxx
@@ -22,15 +22,16 @@
 #include <basegfx/range/b2ibox.hxx>
 #include "headless/svpgdi.hxx"
 #include <config_cairo_canvas.h>
+#include "impfontmetricdata.hxx"
 
 sal_uInt16 SvpSalGraphics::SetFont( FontSelectPattern* pIFSD, int nFallbackLevel )
 {
     return m_aTextRenderImpl.SetFont(pIFSD, nFallbackLevel);
 }
 
-void SvpSalGraphics::GetFontAttributes( FontAttributes* pFontAttributes, int nFallbackLevel )
+void SvpSalGraphics::GetFontMetric( ImplFontMetricData* pFontMetric, int nFallbackLevel )
 {
-    m_aTextRenderImpl.GetFontAttributes(pFontAttributes, nFallbackLevel);
+    m_aTextRenderImpl.GetFontMetric(pFontMetric, nFallbackLevel);
 }
 
 const FontCharMapPtr SvpSalGraphics::GetFontCharMap() const
diff --git a/vcl/inc/cairotextrender.hxx b/vcl/inc/cairotextrender.hxx
index fdd719b..027d885 100644
--- a/vcl/inc/cairotextrender.hxx
+++ b/vcl/inc/cairotextrender.hxx
@@ -33,6 +33,7 @@ class ImplLayoutArgs;
 class ServerFontLayout;
 class PhysicalFontCollection;
 class PhysicalFontFace;
+class ImplFontMetricData;
 typedef struct _cairo cairo_t;
 
 class VCL_DLLPUBLIC CairoFontsCache
@@ -89,7 +90,7 @@ public:
 
     virtual void                SetTextColor( SalColor nSalColor ) override;
     virtual sal_uInt16          SetFont( FontSelectPattern*, int nFallbackLevel ) override;
-    virtual void                GetFontAttributes( FontAttributes*, int nFallbackLevel ) override;
+    virtual void                GetFontMetric( ImplFontMetricData*, int nFallbackLevel ) override;
     virtual const FontCharMapPtr GetFontCharMap() const override;
     virtual bool                GetFontCapabilities(vcl::FontCapabilities &rFontCapabilities) const override;
     virtual void                GetDevFontList( PhysicalFontCollection* ) override;
diff --git a/vcl/inc/fontattributes.hxx b/vcl/inc/fontattributes.hxx
index 9ff1b7c..63ab8c3 100644
--- a/vcl/inc/fontattributes.hxx
+++ b/vcl/inc/fontattributes.hxx
@@ -34,9 +34,6 @@ class FontSelectPattern;
 class FontAttributes
 {
 public:
-    explicit        FontAttributes();
-    explicit        FontAttributes( const FontSelectPattern& );
-
     // device independent font functions
     const OUString& GetFamilyName() const                       { return maFamilyName; }
     FontFamily      GetFamilyType() const                       { return meFamily; }
@@ -97,99 +94,6 @@ public:
     void            SetSubsettableFlag( bool bSubsettable )     { mbSubsettable = bSubsettable; }
     void            SetOrientationFlag( bool bCanRotate )       { mbOrientation = bCanRotate; }
 
-    // Font metrics below
-
-    // font instance attributes from the font request
-    long            GetWidth()                                  { return mnWidth; }
-    short           GetOrientation()                            { return mnOrientation; }
-
-    void            SetWidth(long nWidth)                       { mnWidth=nWidth; }
-    void            SetOrientation(short nOrientation)          { mnOrientation=nOrientation; }
-
-    // font metrics measured for the font instance
-    long            GetAscent()                                 { return mnAscent; }
-    long            GetDescent()                                { return mnDescent; }
-    long            GetInternalLeading()                        { return mnIntLeading; }
-    long            GetExternalLeading()                        { return mnExtLeading; }
-    int             GetSlant()                                  { return mnSlant; }
-    long            GetMinKashida()                             { return mnMinKashida; }
-
-    void            SetAscent(long nAscent)                     { mnAscent=nAscent; }
-    void            SetDescent(long nDescent)                   { mnDescent=nDescent; }
-    void            SetInternalLeading(long nIntLeading)        { mnIntLeading = nIntLeading; }
-    void            SetExternalLeading(long nExtLeading)        { mnExtLeading = nExtLeading; }
-    void            SetSlant(int nSlant)                        { mnSlant=nSlant; }
-    void            SetMinKashida( long nMinKashida )           { mnMinKashida=nMinKashida; }
-
-    // font attributes queried from the font instance
-    bool            IsScalable()                                { return mbScalableFont; }
-    bool            IsTrueTypeFont()                            { return mbTrueTypeFont; }
-    bool            IsKernable()                                { return mbKernableFont; }
-    bool            IsFullstopCentered()                        { return mbFullstopCentered; }
-    long            GetBulletOffset()                           { return mnBulletOffset; }
-
-    void            SetScalableFlag(bool bScalable)             { mbScalableFont = bScalable; }
-    void            SetTrueTypeFlag(bool bTrueTypeFont)         { mbTrueTypeFont = bTrueTypeFont; }
-    void            SetKernableFlag(bool bKernable)             { mbKernableFont = bKernable; }
-    void            SetFullstopCenteredFlag(bool bFullstopCentered) { mbFullstopCentered = bFullstopCentered; }
-    void            SetBulletOffset(long nBulletOffset)         { mnBulletOffset = nBulletOffset; }
-
-    // font metrics that are usually derived from the measurements
-    long            GetUnderlineSize()                          { return mnUnderlineSize; }
-    long            GetUnderlineOffset()                        { return mnUnderlineOffset; }
-    long            GetBoldUnderlineSize()                      { return mnBUnderlineSize; }
-    long            GetBoldUnderlineOffset()                    { return mnBUnderlineOffset; }
-    long            GetDoubleUnderlineSize()                    { return mnDUnderlineSize; }
-    long            GetDoubleUnderlineOffset1()                 { return mnDUnderlineOffset1; }
-    long            GetDoubleUnderlineOffset2()                 { return mnDUnderlineOffset2; }
-    long            GetWavelineUnderlineSize()                  { return mnWUnderlineSize; }
-    long            GetWavelineUnderlineOffset()                { return mnWUnderlineOffset; }
-    long            GetAboveUnderlineSize()                     { return mnAboveUnderlineSize; }
-    long            GetAboveUnderlineOffset()                   { return mnAboveUnderlineOffset; }
-    long            GetAboveBoldUnderlineSize()                 { return mnAboveBUnderlineSize; }
-    long            GetAboveBoldUnderlineOffset()               { return mnAboveBUnderlineOffset; }
-    long            GetAboveDoubleUnderlineSize()               { return mnAboveDUnderlineSize; }
-    long            GetAboveDoubleUnderlineOffset1()            { return mnAboveDUnderlineOffset1; }
-    long            GetAboveDoubleUnderlineOffset2()            { return mnAboveDUnderlineOffset2; }
-    long            GetAboveWavelineUnderlineSize()             { return mnAboveWUnderlineSize; }
-    long            GetAboveWavelineUnderlineOffset()           { return mnAboveWUnderlineOffset; }
-    long            GetStrikeoutSize()                          { return mnStrikeoutSize; }
-    long            GetStrikeoutOffset()                        { return mnStrikeoutOffset; }
-    long            GetBoldStrikeoutSize()                      { return mnBStrikeoutSize; }
-    long            GetBoldStrikeoutOffset()                    { return mnBStrikeoutOffset; }
-    long            GetDoubleStrikeoutSize()                    { return mnDStrikeoutSize; }
-    long            GetDoubleStrikeoutOffset1()                 { return mnDStrikeoutOffset1; }
-    long            GetDoubleStrikeoutOffset2()                 { return mnDStrikeoutOffset2; }
-
-    void            SetUnderlineSize( long nUnderlineSize )                         { mnUnderlineSize = nUnderlineSize; }
-    void            SetUnderlineOffset( long nUnderlineOffset )                     { mnUnderlineOffset = nUnderlineOffset; }
-    void            SetBoldUnderlineSize( long nBUnderlineSize )                    { mnBUnderlineSize = nBUnderlineSize; }
-    void            SetBoldUnderlineOffset( long nBUnderlineOffset )                { mnBUnderlineOffset = nBUnderlineOffset; }
-    void            SetDoubleUnderlineSize( long nDUnderlineSize )                  { mnDUnderlineSize = nDUnderlineSize; }
-    void            SetDoubleUnderlineOffset1( long nDUnderlineOffset1 )            { mnDUnderlineOffset1 = nDUnderlineOffset1; }
-    void            SetDoubleUnderlineOffset2( long nDUnderlineOffset2 )            { mnDUnderlineOffset2 = nDUnderlineOffset2; }
-    void            SetWavelineUnderlineSize( long nWUnderlineSize )                { mnWUnderlineSize = nWUnderlineSize; }
-    void            SetWavelineUnderlineOffset( long nWUnderlineOffset )            { mnWUnderlineOffset = nWUnderlineOffset; }
-    void            SetAboveUnderlineSize( long nAboveUnderlineSize )               { mnAboveUnderlineSize = nAboveUnderlineSize; }
-    void            SetAboveUnderlineOffset( long nAboveUnderlineOffset )           { mnAboveUnderlineOffset = nAboveUnderlineOffset; }
-    void            SetAboveBoldUnderlineSize( long nAboveBUnderlineSize )          { mnAboveBUnderlineSize = nAboveBUnderlineSize; }
-    void            SetAboveBoldUnderlineOffset( long nAboveBUnderlineOffset )      { mnAboveBUnderlineOffset = nAboveBUnderlineOffset; }
-    void            SetAboveDoubleUnderlineSize( long nAboveDUnderlineSize )        { mnAboveDUnderlineSize = nAboveDUnderlineSize; }
-    void            SetAboveDoubleUnderlineOffset1( long nAboveDUnderlineOffset1 )  { mnAboveDUnderlineOffset1 = nAboveDUnderlineOffset1; }
-    void            SetAboveDoubleUnderlineOffset2( long nAboveDUnderlineOffset2 )  { mnAboveDUnderlineOffset2 = nAboveDUnderlineOffset2; }
-    void            SetAboveWavelineUnderlineSize( long nAboveWUnderlineSize )      { mnAboveWUnderlineSize = nAboveWUnderlineSize; }
-    void            SetAboveWavelineUnderlineOffset( long nAboveWUnderlineOffset )  { mnAboveWUnderlineOffset = nAboveWUnderlineOffset; }
-    void            SetStrikeoutSize( long nStrikeoutSize )                         { mnStrikeoutSize = nStrikeoutSize; }
-    void            SetStrikeoutOffset( long nStrikeoutOffset )                     { mnStrikeoutOffset = nStrikeoutOffset; }
-    void            SetBoldStrikeoutSize( long nBStrikeoutSize )                    { mnBStrikeoutSize = nBStrikeoutSize; }
-    void            SetBoldStrikeoutOffset( long nBStrikeoutOffset )                { mnBStrikeoutOffset = nBStrikeoutOffset; }
-    void            SetDoubleStrikeoutSize( long nDStrikeoutSize )                  { mnDStrikeoutSize = nDStrikeoutSize; }
-    void            SetDoubleStrikeoutOffset1( long nDStrikeoutOffset1 )            { mnDStrikeoutOffset1 = nDStrikeoutOffset1; }
-    void            SetDoubleStrikeoutOffset2( long nDStrikeoutOffset2 )            { mnDStrikeoutOffset2 = nDStrikeoutOffset2; }
-
-    void            ImplInitTextLineSize( const OutputDevice* pDev );
-    void            ImplInitAboveTextLineSize();
-
 private:
     // device independent variables
     OUString        maFamilyName;               // Font Family Name
@@ -209,54 +113,6 @@ private:
     bool            mbSubsettable;              // true: a subset of the font can be created
     bool            mbEmbeddable;               // true: the font can be embedded
 
-    // Font metrics below
-
-    // font instance attributes from the font request
-    long            mnWidth;                    // Reference Width
-    short           mnOrientation;              // Rotation in 1/10 degrees
-
-    // font metrics measured for the font instance
-    long            mnAscent;                   // Ascent
-    long            mnDescent;                  // Descent
-    long            mnIntLeading;               // Internal Leading
-    long            mnExtLeading;               // External Leading
-    int             mnSlant;                    // Slant (Italic/Oblique)
-    long            mnMinKashida;               // Minimal width of kashida (Arabic)
-
-    // font attributes queried from the font instance
-    bool            mbScalableFont;
-    bool            mbTrueTypeFont;
-    bool            mbKernableFont;
-    bool            mbFullstopCentered;
-    long            mnBulletOffset;             // Offset to position non-print character
-
-    // font metrics that are usually derived from the measurements
-    long            mnUnderlineSize;            // Lineheight of Underline
-    long            mnUnderlineOffset;          // Offset from Underline to Baseline
-    long            mnBUnderlineSize;           // Height of bold underline
-    long            mnBUnderlineOffset;         // Offset from bold underline to baseline
-    long            mnDUnderlineSize;           // Height of double underline
-    long            mnDUnderlineOffset1;        // Offset from double underline to baseline
-    long            mnDUnderlineOffset2;        // Offset from double underline to baseline
-    long            mnWUnderlineSize;           // Height of WaveLine underline
-    long            mnWUnderlineOffset;         // Offset from WaveLine underline to baseline, but centrered to WaveLine
-    long            mnAboveUnderlineSize;       // Height of single underline (for Vertical Right)
-    long            mnAboveUnderlineOffset;     // Offset from single underline to baseline (for Vertical Right)
-    long            mnAboveBUnderlineSize;      // Height of bold underline (for Vertical Right)
-    long            mnAboveBUnderlineOffset;    // Offset from bold underline to baseline (for Vertical Right)
-    long            mnAboveDUnderlineSize;      // Height of double underline (for Vertical Right)
-    long            mnAboveDUnderlineOffset1;   // Offset from double underline to baseline (for Vertical Right)
-    long            mnAboveDUnderlineOffset2;   // Offset from double underline to baseline (for Vertical Right)
-    long            mnAboveWUnderlineSize;      // Height of WaveLine-strike-out (for Vertical Right)
-    long            mnAboveWUnderlineOffset;    // Offset from WaveLine-strike-out to baseline, but centrered to the WaveLine (for Vertical Right)
-    long            mnStrikeoutSize;            // Height of single strike-out
-    long            mnStrikeoutOffset;          // Offset from single strike-out to baseline
-    long            mnBStrikeoutSize;           // Height of bold strike-out
-    long            mnBStrikeoutOffset;         // Offset of bold strike-out to baseline
-    long            mnDStrikeoutSize;           // Height of double strike-out
-    long            mnDStrikeoutOffset1;        // Offset of double strike-out to baseline
-    long            mnDStrikeoutOffset2;        // Offset of double strike-out to baseline
-
 };
 
 #endif // INCLUDED_VCL_INC_FONTATTRIBUTES_HXX
diff --git a/vcl/inc/fontinstance.hxx b/vcl/inc/fontinstance.hxx
index c790a92..54a74d0 100644
--- a/vcl/inc/fontinstance.hxx
+++ b/vcl/inc/fontinstance.hxx
@@ -25,6 +25,7 @@
 
 #include "fontselect.hxx"
 #include "fontattributes.hxx"
+#include "impfontmetricdata.hxx"
 
 #include <unordered_map>
 
@@ -41,16 +42,16 @@ public:
 
 public: // TODO: make data members private
     ImplFontCache * mpFontCache;
-    FontSelectPattern  maFontSelData;          // FontSelectionData
-    FontAttributes  maFontAttributes;       // Font attributes
-    const ConvertChar* mpConversion;           // used e.g. for StarBats->StarSymbol
+    FontSelectPattern  maFontSelData;       // FontSelectionData
+    ImplFontMetricData maFontMetric;        // Font attributes
+    const ConvertChar* mpConversion;        // used e.g. for StarBats->StarSymbol
 
     long            mnLineHeight;
     sal_uLong       mnRefCount;
     sal_uInt16      mnSetFontFlags;         // Flags returned by SalGraphics::SetFont()
     short           mnOwnOrientation;       // text angle if lower layers don't rotate text themselves
     short           mnOrientation;          // text angle in 3600 system
-    bool            mbInit;                 // true if maFontAttributes member is valid
+    bool            mbInit;                 // true if maFontMetric member is valid
 
     void            AddFallbackForUnicode( sal_UCS4, FontWeight eWeight, const OUString& rFontName );
     bool            GetFallbackForUnicode( sal_UCS4, FontWeight eWeight, OUString* pFontName ) const;
diff --git a/vcl/inc/headless/svpgdi.hxx b/vcl/inc/headless/svpgdi.hxx
index cb04f7b..e88701d 100644
--- a/vcl/inc/headless/svpgdi.hxx
+++ b/vcl/inc/headless/svpgdi.hxx
@@ -29,6 +29,7 @@
 #include "salgdi.hxx"
 #include "sallayout.hxx"
 #include "svpcairotextrender.hxx"
+#include "impfontmetricdata.hxx"
 
 #ifdef IOS
 #define SvpSalGraphics AquaSalGraphics
@@ -121,7 +122,7 @@ public:
 
     virtual void            SetTextColor( SalColor nSalColor ) override;
     virtual sal_uInt16      SetFont( FontSelectPattern*, int nFallbackLevel ) override;
-    virtual void            GetFontAttributes( FontAttributes*, int nFallbackLevel ) override;
+    virtual void            GetFontMetric( ImplFontMetricData*, int nFallbackLevel ) override;
     virtual const FontCharMapPtr GetFontCharMap() const override;
     virtual bool GetFontCapabilities(vcl::FontCapabilities &rFontCapabilities) const override;
     virtual void            GetDevFontList( PhysicalFontCollection* ) override;
diff --git a/vcl/inc/impfontmetricdata.hxx b/vcl/inc/impfontmetricdata.hxx
new file mode 100644
index 0000000..2ccee0d
--- /dev/null
+++ b/vcl/inc/impfontmetricdata.hxx
@@ -0,0 +1,182 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ *   Licensed to the Apache Software Foundation (ASF) under one or more
+ *   contributor license agreements. See the NOTICE file distributed
+ *   with this work for additional information regarding copyright
+ *   ownership. The ASF licenses this file to you under the Apache
+ *   License, Version 2.0 (the "License"); you may not use this file
+ *   except in compliance with the License. You may obtain a copy of
+ *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+
+#ifndef INCLUDED_VCL_INC_IMPFONTMETRICDATA_HXX
+#define INCLUDED_VCL_INC_IMPFONTMETRICDATA_HXX
+
+#include <sal/types.h>
+#include <i18nlangtag/lang.h>
+#include <unotools/fontdefs.hxx>
+#include <vcl/dllapi.h>
+#include <vcl/vclenum.hxx>
+
+#include "fontselect.hxx"
+#include "fontattributes.hxx"
+
+class OutputDevice;
+class FontSelectPattern;
+
+class ImplFontMetricData : public FontAttributes
+{
+public:
+    explicit        ImplFontMetricData( const FontSelectPattern& );
+
+    // font instance attributes from the font request
+    long            GetWidth()                                  { return mnWidth; }
+    short           GetOrientation()                            { return mnOrientation; }
+
+    void            SetWidth(long nWidth)                       { mnWidth=nWidth; }
+    void            SetOrientation(short nOrientation)          { mnOrientation=nOrientation; }
+
+    // font metrics measured for the font instance
+    long            GetAscent()                                 { return mnAscent; }
+    long            GetDescent()                                { return mnDescent; }
+    long            GetInternalLeading()                        { return mnIntLeading; }
+    long            GetExternalLeading()                        { return mnExtLeading; }
+    int             GetSlant()                                  { return mnSlant; }
+    long            GetMinKashida()                             { return mnMinKashida; }
+
+    void            SetAscent(long nAscent)                     { mnAscent=nAscent; }
+    void            SetDescent(long nDescent)                   { mnDescent=nDescent; }
+    void            SetInternalLeading(long nIntLeading)        { mnIntLeading = nIntLeading; }
+    void            SetExternalLeading(long nExtLeading)        { mnExtLeading = nExtLeading; }
+    void            SetSlant(int nSlant)                        { mnSlant=nSlant; }
+    void            SetMinKashida( long nMinKashida )           { mnMinKashida=nMinKashida; }
+
+    // font attributes queried from the font instance
+    bool            IsScalable()                                { return mbScalableFont; }
+    bool            IsTrueTypeFont()                            { return mbTrueTypeFont; }
+    bool            IsKernable()                                { return mbKernableFont; }
+    bool            IsFullstopCentered()                        { return mbFullstopCentered; }
+    long            GetBulletOffset()                           { return mnBulletOffset; }
+
+    void            SetScalableFlag(bool bScalable)             { mbScalableFont = bScalable; }
+    void            SetTrueTypeFlag(bool bTrueTypeFont)         { mbTrueTypeFont = bTrueTypeFont; }
+    void            SetKernableFlag(bool bKernable)             { mbKernableFont = bKernable; }
+    void            SetFullstopCenteredFlag(bool bFullstopCentered) { mbFullstopCentered = bFullstopCentered; }
+    void            SetBulletOffset(long nBulletOffset)         { mnBulletOffset = nBulletOffset; }
+
+    // font metrics that are usually derived from the measurements
+    long            GetUnderlineSize()                          { return mnUnderlineSize; }
+    long            GetUnderlineOffset()                        { return mnUnderlineOffset; }
+    long            GetBoldUnderlineSize()                      { return mnBUnderlineSize; }
+    long            GetBoldUnderlineOffset()                    { return mnBUnderlineOffset; }
+    long            GetDoubleUnderlineSize()                    { return mnDUnderlineSize; }
+    long            GetDoubleUnderlineOffset1()                 { return mnDUnderlineOffset1; }
+    long            GetDoubleUnderlineOffset2()                 { return mnDUnderlineOffset2; }
+    long            GetWavelineUnderlineSize()                  { return mnWUnderlineSize; }
+    long            GetWavelineUnderlineOffset()                { return mnWUnderlineOffset; }
+    long            GetAboveUnderlineSize()                     { return mnAboveUnderlineSize; }
+    long            GetAboveUnderlineOffset()                   { return mnAboveUnderlineOffset; }
+    long            GetAboveBoldUnderlineSize()                 { return mnAboveBUnderlineSize; }
+    long            GetAboveBoldUnderlineOffset()               { return mnAboveBUnderlineOffset; }
+    long            GetAboveDoubleUnderlineSize()               { return mnAboveDUnderlineSize; }
+    long            GetAboveDoubleUnderlineOffset1()            { return mnAboveDUnderlineOffset1; }
+    long            GetAboveDoubleUnderlineOffset2()            { return mnAboveDUnderlineOffset2; }
+    long            GetAboveWavelineUnderlineSize()             { return mnAboveWUnderlineSize; }
+    long            GetAboveWavelineUnderlineOffset()           { return mnAboveWUnderlineOffset; }
+    long            GetStrikeoutSize()                          { return mnStrikeoutSize; }
+    long            GetStrikeoutOffset()                        { return mnStrikeoutOffset; }
+    long            GetBoldStrikeoutSize()                      { return mnBStrikeoutSize; }
+    long            GetBoldStrikeoutOffset()                    { return mnBStrikeoutOffset; }
+    long            GetDoubleStrikeoutSize()                    { return mnDStrikeoutSize; }
+    long            GetDoubleStrikeoutOffset1()                 { return mnDStrikeoutOffset1; }
+    long            GetDoubleStrikeoutOffset2()                 { return mnDStrikeoutOffset2; }
+
+    void            SetUnderlineSize( long nUnderlineSize )                         { mnUnderlineSize = nUnderlineSize; }
+    void            SetUnderlineOffset( long nUnderlineOffset )                     { mnUnderlineOffset = nUnderlineOffset; }
+    void            SetBoldUnderlineSize( long nBUnderlineSize )                    { mnBUnderlineSize = nBUnderlineSize; }
+    void            SetBoldUnderlineOffset( long nBUnderlineOffset )                { mnBUnderlineOffset = nBUnderlineOffset; }
+    void            SetDoubleUnderlineSize( long nDUnderlineSize )                  { mnDUnderlineSize = nDUnderlineSize; }
+    void            SetDoubleUnderlineOffset1( long nDUnderlineOffset1 )            { mnDUnderlineOffset1 = nDUnderlineOffset1; }
+    void            SetDoubleUnderlineOffset2( long nDUnderlineOffset2 )            { mnDUnderlineOffset2 = nDUnderlineOffset2; }
+    void            SetWavelineUnderlineSize( long nWUnderlineSize )                { mnWUnderlineSize = nWUnderlineSize; }
+    void            SetWavelineUnderlineOffset( long nWUnderlineOffset )            { mnWUnderlineOffset = nWUnderlineOffset; }
+    void            SetAboveUnderlineSize( long nAboveUnderlineSize )               { mnAboveUnderlineSize = nAboveUnderlineSize; }
+    void            SetAboveUnderlineOffset( long nAboveUnderlineOffset )           { mnAboveUnderlineOffset = nAboveUnderlineOffset; }
+    void            SetAboveBoldUnderlineSize( long nAboveBUnderlineSize )          { mnAboveBUnderlineSize = nAboveBUnderlineSize; }
+    void            SetAboveBoldUnderlineOffset( long nAboveBUnderlineOffset )      { mnAboveBUnderlineOffset = nAboveBUnderlineOffset; }
+    void            SetAboveDoubleUnderlineSize( long nAboveDUnderlineSize )        { mnAboveDUnderlineSize = nAboveDUnderlineSize; }
+    void            SetAboveDoubleUnderlineOffset1( long nAboveDUnderlineOffset1 )  { mnAboveDUnderlineOffset1 = nAboveDUnderlineOffset1; }
+    void            SetAboveDoubleUnderlineOffset2( long nAboveDUnderlineOffset2 )  { mnAboveDUnderlineOffset2 = nAboveDUnderlineOffset2; }
+    void            SetAboveWavelineUnderlineSize( long nAboveWUnderlineSize )      { mnAboveWUnderlineSize = nAboveWUnderlineSize; }
+    void            SetAboveWavelineUnderlineOffset( long nAboveWUnderlineOffset )  { mnAboveWUnderlineOffset = nAboveWUnderlineOffset; }
+    void            SetStrikeoutSize( long nStrikeoutSize )                         { mnStrikeoutSize = nStrikeoutSize; }
+    void            SetStrikeoutOffset( long nStrikeoutOffset )                     { mnStrikeoutOffset = nStrikeoutOffset; }
+    void            SetBoldStrikeoutSize( long nBStrikeoutSize )                    { mnBStrikeoutSize = nBStrikeoutSize; }
+    void            SetBoldStrikeoutOffset( long nBStrikeoutOffset )                { mnBStrikeoutOffset = nBStrikeoutOffset; }
+    void            SetDoubleStrikeoutSize( long nDStrikeoutSize )                  { mnDStrikeoutSize = nDStrikeoutSize; }
+    void            SetDoubleStrikeoutOffset1( long nDStrikeoutOffset1 )            { mnDStrikeoutOffset1 = nDStrikeoutOffset1; }
+    void            SetDoubleStrikeoutOffset2( long nDStrikeoutOffset2 )            { mnDStrikeoutOffset2 = nDStrikeoutOffset2; }
+
+    void            ImplInitTextLineSize( const OutputDevice* pDev );
+    void            ImplInitAboveTextLineSize();
+
+private:
+    // font instance attributes from the font request
+    long            mnWidth;                    // Reference Width
+    short           mnOrientation;              // Rotation in 1/10 degrees
+
+    // font metrics measured for the font instance
+    long            mnAscent;                   // Ascent
+    long            mnDescent;                  // Descent
+    long            mnIntLeading;               // Internal Leading
+    long            mnExtLeading;               // External Leading
+    int             mnSlant;                    // Slant (Italic/Oblique)
+    long            mnMinKashida;               // Minimal width of kashida (Arabic)
+
+    // font attributes queried from the font instance
+    bool            mbScalableFont;
+    bool            mbTrueTypeFont;
+    bool            mbKernableFont;
+    bool            mbFullstopCentered;
+    long            mnBulletOffset;             // Offset to position non-print character
+
+    // font metrics that are usually derived from the measurements
+    long            mnUnderlineSize;            // Lineheight of Underline
+    long            mnUnderlineOffset;          // Offset from Underline to Baseline
+    long            mnBUnderlineSize;           // Height of bold underline
+    long            mnBUnderlineOffset;         // Offset from bold underline to baseline
+    long            mnDUnderlineSize;           // Height of double underline
+    long            mnDUnderlineOffset1;        // Offset from double underline to baseline
+    long            mnDUnderlineOffset2;        // Offset from double underline to baseline
+    long            mnWUnderlineSize;           // Height of WaveLine underline
+    long            mnWUnderlineOffset;         // Offset from WaveLine underline to baseline, but centrered to WaveLine
+    long            mnAboveUnderlineSize;       // Height of single underline (for Vertical Right)
+    long            mnAboveUnderlineOffset;     // Offset from single underline to baseline (for Vertical Right)
+    long            mnAboveBUnderlineSize;      // Height of bold underline (for Vertical Right)
+    long            mnAboveBUnderlineOffset;    // Offset from bold underline to baseline (for Vertical Right)
+    long            mnAboveDUnderlineSize;      // Height of double underline (for Vertical Right)
+    long            mnAboveDUnderlineOffset1;   // Offset from double underline to baseline (for Vertical Right)
+    long            mnAboveDUnderlineOffset2;   // Offset from double underline to baseline (for Vertical Right)
+    long            mnAboveWUnderlineSize;      // Height of WaveLine-strike-out (for Vertical Right)
+    long            mnAboveWUnderlineOffset;    // Offset from WaveLine-strike-out to baseline, but centrered to the WaveLine (for Vertical Right)
+    long            mnStrikeoutSize;            // Height of single strike-out
+    long            mnStrikeoutOffset;          // Offset from single strike-out to baseline
+    long            mnBStrikeoutSize;           // Height of bold strike-out
+    long            mnBStrikeoutOffset;         // Offset of bold strike-out to baseline
+    long            mnDStrikeoutSize;           // Height of double strike-out
+    long            mnDStrikeoutOffset1;        // Offset of double strike-out to baseline
+    long            mnDStrikeoutOffset2;        // Offset of double strike-out to baseline
+
+};
+
+#endif // INCLUDED_VCL_INC_IMPFONTMETRICDATA_HXX
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/inc/quartz/salgdi.h b/vcl/inc/quartz/salgdi.h
index 03ef055..a9628459 100644
--- a/vcl/inc/quartz/salgdi.h
+++ b/vcl/inc/quartz/salgdi.h
@@ -39,6 +39,7 @@
 #include <vcl/metric.hxx>
 
 #include "fontinstance.hxx"
+#include "impfontmetricdata.hxx"
 #include "PhysicalFontFace.hxx"
 #include "salgdi.hxx"
 
@@ -94,7 +95,7 @@ public:
 
     SalLayout* GetTextLayout( void ) const;
 
-    void       GetFontAttributes( FontAttributes& ) const;
+    void       GetFontMetric( ImplFontMetricData& ) const;
     bool       GetGlyphBoundRect( sal_GlyphId, Rectangle& ) const;
     bool       GetGlyphOutline( sal_GlyphId, basegfx::B2DPolyPolygon& ) const;
 
@@ -338,7 +339,7 @@ public:
     // set the font
     virtual sal_uInt16      SetFont( FontSelectPattern*, int nFallbackLevel ) override;
     // get the current font's metrics
-    virtual void            GetFontAttributes( FontAttributes*, int nFallbackLevel ) override;
+    virtual void            GetFontMetric( ImplFontMetricData*, int nFallbackLevel ) override;
     // get the repertoire of the current font
     virtual const FontCharMapPtr GetFontCharMap() const override;
     virtual bool            GetFontCapabilities(vcl::FontCapabilities &rFontCapabilities) const override;
diff --git a/vcl/inc/salgdi.hxx b/vcl/inc/salgdi.hxx
index 039e45f..ca2251f 100644
--- a/vcl/inc/salgdi.hxx
+++ b/vcl/inc/salgdi.hxx
@@ -29,6 +29,8 @@
 #include <vcl/salnativewidgets.hxx>
 #include <vcl/metric.hxx>
 
+#include "impfontmetricdata.hxx"
+
 #include "salgdiimpl.hxx"
 #include "salglyphid.hxx"
 #include "sallayout.hxx"
@@ -145,7 +147,7 @@ public:
     void                        ReleaseFonts() { SetFont( nullptr, 0 ); }
 
     // get the current font's metrics
-    virtual void                GetFontAttributes( FontAttributes*, int nFallbackLevel = 0 ) = 0;
+    virtual void                GetFontMetric( ImplFontMetricData*, int nFallbackLevel = 0 ) = 0;
 
     // get the repertoire of the current font
     virtual const FontCharMapPtr GetFontCharMap() const = 0;
diff --git a/vcl/inc/textrender.hxx b/vcl/inc/textrender.hxx
index 11a38cb..2c0bf7f 100644
--- a/vcl/inc/textrender.hxx
+++ b/vcl/inc/textrender.hxx
@@ -31,6 +31,7 @@
 #include <config_cairo_canvas.h>
 
 class ImplLayoutArgs;
+class ImplFontMetricData;
 class ServerFontLayout;
 class PhysicalFontCollection;
 class PhysicalFontFace;
@@ -42,7 +43,7 @@ public:
 
     virtual void                    SetTextColor( SalColor nSalColor ) = 0;
     virtual sal_uInt16              SetFont( FontSelectPattern*, int nFallbackLevel ) = 0;
-    virtual void                    GetFontAttributes( FontAttributes*, int nFallbackLevel ) = 0;
+    virtual void                    GetFontMetric( ImplFontMetricData*, int nFallbackLevel ) = 0;
     virtual const FontCharMapPtr    GetFontCharMap() const = 0;
     virtual bool                    GetFontCapabilities(vcl::FontCapabilities &rFontCapabilities) const = 0;
     virtual void                    GetDevFontList( PhysicalFontCollection* ) = 0;
diff --git a/vcl/inc/unx/genpspgraphics.h b/vcl/inc/unx/genpspgraphics.h
index 860f15b..850270c 100644
--- a/vcl/inc/unx/genpspgraphics.h
+++ b/vcl/inc/unx/genpspgraphics.h
@@ -37,6 +37,7 @@ class ServerFont;
 class FontAttributes;
 class SalInfoPrinter;
 class GlyphCache;
+class ImplFontMetricData;
 
 class VCL_DLLPUBLIC GenPspGraphics : public SalGraphics
 {
@@ -92,7 +93,7 @@ public:
 
     virtual void            SetTextColor( SalColor nSalColor ) override;
     virtual sal_uInt16      SetFont( FontSelectPattern*, int nFallbackLevel ) override;
-    virtual void            GetFontAttributes( FontAttributes*, int nFallbackLevel ) override;
+    virtual void            GetFontMetric( ImplFontMetricData*, int nFallbackLevel ) override;
     virtual const FontCharMapPtr GetFontCharMap() const override;
     virtual bool            GetFontCapabilities(vcl::FontCapabilities &rFontCapabilities) const override;
     virtual void            GetDevFontList( PhysicalFontCollection* ) override;
diff --git a/vcl/inc/unx/glyphcache.hxx b/vcl/inc/unx/glyphcache.hxx
index da8f29c..463c259 100644
--- a/vcl/inc/unx/glyphcache.hxx
+++ b/vcl/inc/unx/glyphcache.hxx
@@ -35,6 +35,7 @@
 #include <fontinstance.hxx>
 #include <sallayout.hxx>
 #include "fontattributes.hxx"
+#include "impfontmetricdata.hxx"
 
 #include <unordered_map>
 
@@ -127,18 +128,18 @@ class GlyphData
 public:
                             GlyphData() : mnLruValue(0) {}
 
-    const GlyphMetric&      GetMetric() const           { return maFontAttributes; }
+    const GlyphMetric&      GetMetric() const           { return maGlyphMetric; }
 
-    void                    SetSize( const Size& s)     { maFontAttributes.SetSize( s ); }
-    void                    SetOffset( int nX, int nY ) { maFontAttributes.SetOffset( nX, nY ); }
-    void                    SetDelta( int nX, int nY )  { maFontAttributes.SetDelta( nX, nY ); }
-    void                    SetCharWidth( long nW )     { maFontAttributes.SetCharWidth( nW ); }
+    void                    SetSize( const Size& s)     { maGlyphMetric.SetSize( s ); }
+    void                    SetOffset( int nX, int nY ) { maGlyphMetric.SetOffset( nX, nY ); }
+    void                    SetDelta( int nX, int nY )  { maGlyphMetric.SetDelta( nX, nY ); }
+    void                    SetCharWidth( long nW )     { maGlyphMetric.SetCharWidth( nW ); }
 
     void                    SetLruValue( int n ) const  { mnLruValue = n; }
     long                    GetLruValue() const         { return mnLruValue;}
 
 private:
-    GlyphMetric             maFontAttributes;
+    GlyphMetric             maGlyphMetric;
 
     // used by GlyphCache for cache LRU algorithm
     mutable long            mnLruValue;
@@ -161,7 +162,7 @@ public:
 
     const FontSelectPattern& GetFontSelData() const      { return maFontSelData; }
 
-    void                    FetchFontAttributes( FontAttributes&, long& rFactor ) const;
+    void                    FetchFontMetric( ImplFontMetricData&, long& rFactor ) const;
     const unsigned char*    GetTable( const char* pName, sal_uLong* pLength );
     int                     GetEmUnits() const { return maFaceFT->units_per_EM;}
     double                  GetStretch() { return mfStretch; }
diff --git a/vcl/inc/unx/salgdi.h b/vcl/inc/unx/salgdi.h
index 68a3bce..9f5b381 100644
--- a/vcl/inc/unx/salgdi.h
+++ b/vcl/inc/unx/salgdi.h
@@ -112,7 +112,7 @@ public:
 
     virtual void                    SetTextColor( SalColor nSalColor ) override;
     virtual sal_uInt16              SetFont( FontSelectPattern*, int nFallbackLevel ) override;
-    virtual void                    GetFontAttributes( FontAttributes*, int nFallbackLevel ) override;
+    virtual void                    GetFontMetric( ImplFontMetricData*, int nFallbackLevel ) override;
     virtual const FontCharMapPtr    GetFontCharMap() const override;
     virtual bool                    GetFontCapabilities(vcl::FontCapabilities &rFontCapabilities) const override;
     virtual void                    GetDevFontList( PhysicalFontCollection* ) override;
diff --git a/vcl/inc/win/salgdi.h b/vcl/inc/win/salgdi.h
index 83b5f39..8b89402 100644
--- a/vcl/inc/win/salgdi.h
+++ b/vcl/inc/win/salgdi.h
@@ -46,6 +46,7 @@ class OpenGLTexture;
 class PhysicalFontCollection;
 class SalGraphicsImpl;
 class WinOpenGLSalGraphicsImpl;
+class ImplFontMetricData;
 
 #define RGB_TO_PALRGB(nRGB)         ((nRGB)|0x02000000)
 #define PALRGB_TO_RGB(nPalRGB)      ((nPalRGB)&0x00ffffff)
@@ -361,7 +362,7 @@ public:
     // set the font
     virtual sal_uInt16      SetFont( FontSelectPattern*, int nFallbackLevel ) override;
     // get the current font's metrics
-    virtual void            GetFontAttributes( FontAttributes*, int nFallbackLevel ) override;
+    virtual void            GetFontMetric( ImplFontMetricData*, int nFallbackLevel ) override;
     // get the repertoire of the current font
     virtual const FontCharMapPtr GetFontCharMap() const override;
     // get the layout capabilities of the current font
diff --git a/vcl/quartz/ctfonts.cxx b/vcl/quartz/ctfonts.cxx
index 5052f78..ef8767f 100644
--- a/vcl/quartz/ctfonts.cxx
+++ b/vcl/quartz/ctfonts.cxx
@@ -117,7 +117,7 @@ CoreTextStyle::~CoreTextStyle()
         CFRelease( mpStyleDict );
 }
 
-void CoreTextStyle::GetFontAttributes( FontAttributes& rFontAttributes ) const
+void CoreTextStyle::GetFontMetric( ImplFontMetricData& rFontMetric ) const
 {
     // get the matching CoreText font handle
     // TODO: is it worth it to cache the CTFontRef in SetFont() and reuse it here?
@@ -125,20 +125,20 @@ void CoreTextStyle::GetFontAttributes( FontAttributes& rFontAttributes ) const
 
     const CGFloat fAscent = CTFontGetAscent( aCTFontRef );
     const CGFloat fCapHeight = CTFontGetCapHeight( aCTFontRef );
-    rFontAttributes.SetAscent( lrint( fAscent ) );
-    rFontAttributes.SetDescent( lrint( CTFontGetDescent( aCTFontRef )) );
-    rFontAttributes.SetExternalLeading( lrint( CTFontGetLeading( aCTFontRef )) );
-    rFontAttributes.SetInternalLeading( lrint( fAscent - fCapHeight ) );
+    rFontMetric.SetAscent( lrint( fAscent ) );
+    rFontMetric.SetDescent( lrint( CTFontGetDescent( aCTFontRef )) );
+    rFontMetric.SetExternalLeading( lrint( CTFontGetLeading( aCTFontRef )) );
+    rFontMetric.SetInternalLeading( lrint( fAscent - fCapHeight ) );
 
-    // since FontAttributes::mnWidth is only used for stretching/squeezing fonts
+    // since ImplFontMetricData::mnWidth is only used for stretching/squeezing fonts
     // setting this width to the pixel height of the fontsize is good enough
     // it also makes the calculation of the stretch factor simple
-    rFontAttributes.SetWidth( lrint( CTFontGetSize( aCTFontRef ) * mfFontStretch) );
+    rFontMetric.SetWidth( lrint( CTFontGetSize( aCTFontRef ) * mfFontStretch) );
 
     // all CoreText fonts are scalable
-    rFontAttributes.SetScalableFlag( true );
-    rFontAttributes.SetTrueTypeFlag( true ); // Not sure, but this field is used only for Windows so far
-    rFontAttributes.SetKernableFlag( true );
+    rFontMetric.SetScalableFlag( true );
+    rFontMetric.SetTrueTypeFlag( true ); // Not sure, but this field is used only for Windows so far
+    rFontMetric.SetKernableFlag( true );
 }
 
 bool CoreTextStyle::GetGlyphBoundRect( sal_GlyphId aGlyphId, Rectangle& rRect ) const
diff --git a/vcl/quartz/salgdi.cxx b/vcl/quartz/salgdi.cxx
index 9785126..fb9e8db 100644
--- a/vcl/quartz/salgdi.cxx
+++ b/vcl/quartz/salgdi.cxx
@@ -41,6 +41,8 @@
 #include "fontsubset.hxx"
 #include "impfont.hxx"
 #include "impfontcharmap.hxx"
+#include "impfontmetricdata.hxx"
+
 #ifdef MACOSX
 #include "osx/salframe.h"
 #endif
@@ -306,9 +308,9 @@ void AquaSalGraphics::SetTextColor( SalColor nSalColor )
     // SAL_ DEBUG(std::hex << nSalColor << std::dec << "={" << maTextColor.GetRed() << ", " << maTextColor.GetGreen() << ", " << maTextColor.GetBlue() << ", " << maTextColor.GetAlpha() << "}");
 }
 
-void AquaSalGraphics::GetFontAttributes( FontAttributes* pFontAttributes, int /*nFallbackLevel*/ )
+void AquaSalGraphics::GetFontMetric( ImplFontMetricData* pFontMetric, int /*nFallbackLevel*/ )
 {
-    mpTextStyle->GetFontAttributes( *pFontAttributes );
+    mpTextStyle->GetFontMetric( *pFontMetric );
 }
 
 static bool AddTempDevFont(const OUString& rFontFileURL)
diff --git a/vcl/source/font/fontattributes.cxx b/vcl/source/font/fontattributes.cxx
index 49060f0..e750e65 100644
--- a/vcl/source/font/fontattributes.cxx
+++ b/vcl/source/font/fontattributes.cxx
@@ -92,279 +92,4 @@ bool FontAttributes::CompareDeviceIndependentFontAttributes(const FontAttributes
     return true;
 }
 
-FontAttributes::FontAttributes()
-    : meWeight(WEIGHT_DONTKNOW)
-    , meItalic(ITALIC_DONTKNOW)
-    , meFamily(FAMILY_DONTKNOW)
-    , mePitch(PITCH_DONTKNOW)
-    , meWidthType(WIDTH_DONTKNOW)
-    , mbSymbolFlag(false)
-    , mnQuality(0)
-    , mbOrientation(false)
-    , mbDevice(false)
-    , mbSubsettable(false)
-    , mbEmbeddable(false)
-    , mnWidth ( 0 )
-    , mnOrientation( 0 )
-    , mnAscent( 0 )
-    , mnDescent( 0 )
-    , mnIntLeading( 0 )
-    , mnExtLeading( 0 )
-    , mnSlant( 0 )
-    , mnMinKashida( 0 )
-    , mbScalableFont( false )
-    , mbTrueTypeFont( false )
-    , mbKernableFont( false )
-    , mbFullstopCentered( false )
-    , mnBulletOffset( 0 )
-    , mnUnderlineSize( 0 )
-    , mnUnderlineOffset( 0 )
-    , mnBUnderlineSize( 0 )
-    , mnBUnderlineOffset( 0 )
-    , mnDUnderlineSize( 0 )
-    , mnDUnderlineOffset1( 0 )
-    , mnDUnderlineOffset2( 0 )
-    , mnWUnderlineSize( 0 )
-    , mnWUnderlineOffset( 0 )
-    , mnAboveUnderlineSize( 0 )
-    , mnAboveUnderlineOffset( 0 )
-    , mnAboveBUnderlineSize( 0 )
-    , mnAboveBUnderlineOffset( 0 )
-    , mnAboveDUnderlineSize( 0 )
-    , mnAboveDUnderlineOffset1( 0 )
-    , mnAboveDUnderlineOffset2( 0 )
-    , mnAboveWUnderlineSize( 0 )
-    , mnAboveWUnderlineOffset( 0 )
-    , mnStrikeoutSize( 0 )
-    , mnStrikeoutOffset( 0 )
-    , mnBStrikeoutSize( 0 )
-    , mnBStrikeoutOffset( 0 )
-    , mnDStrikeoutSize( 0 )
-    , mnDStrikeoutOffset1( 0 )
-    , mnDStrikeoutOffset2( 0 )
-{
-    // empty
-}
-
-FontAttributes::FontAttributes( const FontSelectPattern& rFontSelData )
-    : meWeight(WEIGHT_DONTKNOW)
-    , meItalic(ITALIC_DONTKNOW)
-    , meFamily(FAMILY_DONTKNOW)
-    , mePitch(PITCH_DONTKNOW)
-    , meWidthType(WIDTH_DONTKNOW)
-    , mbSymbolFlag(false)
-    , mnQuality(0)
-    , mbOrientation(false)
-    , mbDevice(false)
-    , mbSubsettable(false)
-    , mbEmbeddable(false)
-    , mnWidth ( rFontSelData.mnWidth )
-    , mnOrientation( (short)(rFontSelData.mnOrientation) )
-    , mnAscent( 0 )
-    , mnDescent( 0 )
-    , mnIntLeading( 0 )
-    , mnExtLeading( 0 )
-    , mnSlant( 0 )
-    , mnMinKashida( 0 )
-    , mbScalableFont( false )
-    , mbTrueTypeFont( false )
-    , mbKernableFont( false )
-    , mbFullstopCentered( false )
-    , mnBulletOffset( 0 )
-    , mnUnderlineSize( 0 )
-    , mnUnderlineOffset( 0 )
-    , mnBUnderlineSize( 0 )
-    , mnBUnderlineOffset( 0 )
-    , mnDUnderlineSize( 0 )
-    , mnDUnderlineOffset1( 0 )
-    , mnDUnderlineOffset2( 0 )
-    , mnWUnderlineSize( 0 )
-    , mnWUnderlineOffset( 0 )
-    , mnAboveUnderlineSize( 0 )
-    , mnAboveUnderlineOffset( 0 )
-    , mnAboveBUnderlineSize( 0 )
-    , mnAboveBUnderlineOffset( 0 )
-    , mnAboveDUnderlineSize( 0 )
-    , mnAboveDUnderlineOffset1( 0 )
-    , mnAboveDUnderlineOffset2( 0 )
-    , mnAboveWUnderlineSize( 0 )
-    , mnAboveWUnderlineOffset( 0 )
-    , mnStrikeoutSize( 0 )
-    , mnStrikeoutOffset( 0 )
-    , mnBStrikeoutSize( 0 )
-    , mnBStrikeoutOffset( 0 )
-    , mnDStrikeoutSize( 0 )
-    , mnDStrikeoutOffset1( 0 )
-    , mnDStrikeoutOffset2( 0 )
-{
-    // intialize the used font name
-    if( rFontSelData.mpFontData )
-    {
-        SetFamilyName( rFontSelData.mpFontData->GetFamilyName() );
-        SetStyleName( rFontSelData.mpFontData->GetStyleName() );
-        SetBuiltInFontFlag( rFontSelData.mpFontData->IsBuiltInFont() );
-        SetKernableFlag( true );
-    }
-    else
-    {
-        sal_Int32 nTokenPos = 0;
-        SetFamilyName( GetNextFontToken( rFontSelData.GetFamilyName(), nTokenPos ) );
-        SetStyleName( rFontSelData.GetStyleName() );
-        SetBuiltInFontFlag( false );
-        SetKernableFlag( false );
-    }
-}
-
-
-void FontAttributes::ImplInitTextLineSize( const OutputDevice* pDev )
-{
-    long nDescent = mnDescent;
-    if ( nDescent <= 0 )
-    {
-        nDescent = mnAscent / 10;
-        if ( !nDescent )
-            nDescent = 1;
-    }
-
-    // #i55341# for some fonts it is not a good idea to calculate
-    // their text line metrics from the real font descent
-    // => work around this problem just for these fonts
-    if( 3*nDescent > mnAscent )
-        nDescent = mnAscent / 3;
-
-    long nLineHeight = ((nDescent*25)+50) / 100;
-    if ( !nLineHeight )
-        nLineHeight = 1;
-    long nLineHeight2 = nLineHeight / 2;
-    if ( !nLineHeight2 )
-        nLineHeight2 = 1;
-
-    long nBLineHeight = ((nDescent*50)+50) / 100;
-    if ( nBLineHeight == nLineHeight )
-        nBLineHeight++;
-    long nBLineHeight2 = nBLineHeight/2;
-    if ( !nBLineHeight2 )
-        nBLineHeight2 = 1;
-
-    long n2LineHeight = ((nDescent*16)+50) / 100;
-    if ( !n2LineHeight )
-        n2LineHeight = 1;
-    long n2LineDY = n2LineHeight;
-     /* #117909#
-      * add some pixels to minimum double line distance on higher resolution devices
-      */
-    long nMin2LineDY = 1 + pDev->GetDPIY()/150;
-    if ( n2LineDY < nMin2LineDY )
-        n2LineDY = nMin2LineDY;
-    long n2LineDY2 = n2LineDY/2;
-    if ( !n2LineDY2 )
-        n2LineDY2 = 1;
-
-    long nUnderlineOffset = mnDescent/2 + 1;
-    long nStrikeoutOffset = -((mnAscent - mnIntLeading) / 3);
-
-    mnUnderlineSize        = nLineHeight;
-    mnUnderlineOffset      = nUnderlineOffset - nLineHeight2;
-
-    mnBUnderlineSize       = nBLineHeight;
-    mnBUnderlineOffset     = nUnderlineOffset - nBLineHeight2;
-
-    mnDUnderlineSize       = n2LineHeight;
-    mnDUnderlineOffset1    = nUnderlineOffset - n2LineDY2 - n2LineHeight;
-    mnDUnderlineOffset2    = mnDUnderlineOffset1 + n2LineDY + n2LineHeight;
-
-    long nWCalcSize = mnDescent;
-    if ( nWCalcSize < 6 )
-    {
-        if ( (nWCalcSize == 1) || (nWCalcSize == 2) )
-            mnWUnderlineSize = nWCalcSize;
-        else
-            mnWUnderlineSize = 3;
-    }
-    else
-        mnWUnderlineSize = ((nWCalcSize*50)+50) / 100;
-
-    // Don't assume that wavelines are never placed below the descent, because for most fonts the waveline
-    // is drawn into the text
-    mnWUnderlineOffset     = nUnderlineOffset;
-
-    mnStrikeoutSize        = nLineHeight;
-    mnStrikeoutOffset      = nStrikeoutOffset - nLineHeight2;
-
-    mnBStrikeoutSize       = nBLineHeight;
-    mnBStrikeoutOffset     = nStrikeoutOffset - nBLineHeight2;
-
-    mnDStrikeoutSize       = n2LineHeight;
-    mnDStrikeoutOffset1    = nStrikeoutOffset - n2LineDY2 - n2LineHeight;
-    mnDStrikeoutOffset2    = mnDStrikeoutOffset1 + n2LineDY + n2LineHeight;
-
-    const vcl::Font& rFont ( pDev->GetFont() );
-    bool bCentered = true;
-    if (MsLangId::isCJK(rFont.GetLanguage()))
-    {
-        const OUString sFullstop( sal_Unicode( 0x3001 ) ); // Fullwidth fullstop
-        Rectangle aRect;
-        pDev->GetTextBoundRect( aRect, sFullstop );
-        const sal_uInt16 nH = rFont.GetSize().Height();
-        const sal_uInt16 nB = aRect.Left();
-        // Use 18.75% as a threshold to define a centered fullwidth fullstop.
-        // In general, nB/nH < 5% for most Japanese fonts.
-        bCentered = nB > (((nH >> 1)+nH)>>3);
-    }
-    SetFullstopCenteredFlag( bCentered );
-
-    mnBulletOffset = ( pDev->GetTextWidth( OUString( sal_Unicode( 0x20 ) ) ) - pDev->GetTextWidth( OUString( sal_Unicode( 0xb7 ) ) ) ) >> 1 ;
-
-}
-
-void FontAttributes::ImplInitAboveTextLineSize()
-{
-    long nIntLeading = mnIntLeading;
-    // TODO: assess usage of nLeading below (changed in extleading CWS)
-    // if no leading is available, we assume 15% of the ascent
-    if ( nIntLeading <= 0 )
-    {
-        nIntLeading = mnAscent*15/100;
-        if ( !nIntLeading )
-            nIntLeading = 1;
-    }
-
-    long nLineHeight = ((nIntLeading*25)+50) / 100;
-    if ( !nLineHeight )
-        nLineHeight = 1;
-
-    long nBLineHeight = ((nIntLeading*50)+50) / 100;
-    if ( nBLineHeight == nLineHeight )
-        nBLineHeight++;
-
-    long n2LineHeight = ((nIntLeading*16)+50) / 100;
-    if ( !n2LineHeight )
-        n2LineHeight = 1;
-
-    long nCeiling = -mnAscent;
-
-    mnAboveUnderlineSize       = nLineHeight;
-    mnAboveUnderlineOffset     = nCeiling + (nIntLeading - nLineHeight + 1) / 2;
-
-    mnAboveBUnderlineSize      = nBLineHeight;
-    mnAboveBUnderlineOffset    = nCeiling + (nIntLeading - nBLineHeight + 1) / 2;
-
-    mnAboveDUnderlineSize      = n2LineHeight;
-    mnAboveDUnderlineOffset1   = nCeiling + (nIntLeading - 3*n2LineHeight + 1) / 2;
-    mnAboveDUnderlineOffset2   = nCeiling + (nIntLeading +   n2LineHeight + 1) / 2;
-
-    long nWCalcSize = nIntLeading;
-    if ( nWCalcSize < 6 )
-    {
-        if ( (nWCalcSize == 1) || (nWCalcSize == 2) )
-            mnAboveWUnderlineSize = nWCalcSize;
-        else
-            mnAboveWUnderlineSize = 3;
-    }
-    else
-        mnAboveWUnderlineSize = ((nWCalcSize*50)+50) / 100;
-
-    mnAboveWUnderlineOffset = nCeiling + (nIntLeading + 1) / 2;
-}
-
 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/source/font/fontinstance.cxx b/vcl/source/font/fontinstance.cxx
index 2b3490a..22fde5e 100644
--- a/vcl/source/font/fontinstance.cxx
+++ b/vcl/source/font/fontinstance.cxx
@@ -82,7 +82,7 @@ namespace std
 LogicalFontInstance::LogicalFontInstance( const FontSelectPattern& rFontSelData )
     : mpFontCache(nullptr)
     , maFontSelData( rFontSelData )
-    , maFontAttributes( rFontSelData )
+    , maFontMetric( rFontSelData )
     , mpConversion( nullptr )
     , mnLineHeight( 0 )
     , mnRefCount( 1 )
diff --git a/vcl/source/font/fontmetric.cxx b/vcl/source/font/fontmetric.cxx
new file mode 100644
index 0000000..6cd5c31
--- /dev/null
+++ b/vcl/source/font/fontmetric.cxx
@@ -0,0 +1,279 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ *
+ * This file incorporates work covered by the following license notice:
+ *
+ *   Licensed to the Apache Software Foundation (ASF) under one or more
+ *   contributor license agreements. See the NOTICE file distributed
+ *   with this work for additional information regarding copyright
+ *   ownership. The ASF licenses this file to you under the Apache
+ *   License, Version 2.0 (the "License"); you may not use this file
+ *   except in compliance with the License. You may obtain a copy of
+ *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
+ */
+
+#include "i18nlangtag/mslangid.hxx"
+
+#include <unotools/configmgr.hxx>
+#include <vcl/virdev.hxx>
+#include <vcl/print.hxx>
+#include <vcl/outdev.hxx>
+#include <vcl/edit.hxx>
+#include <vcl/settings.hxx>
+#include <vcl/sysdata.hxx>
+#include <vcl/fontcharmap.hxx>
+
+#include "sallayout.hxx"
+#include "svdata.hxx"
+
+#include "impfont.hxx"
+#include "outdata.hxx"
+#include "fontinstance.hxx"
+#include "fontattributes.hxx"
+#include "impfontmetricdata.hxx"
+
+#include "outdev.h"
+#include "window.h"
+
+#include "PhysicalFontCollection.hxx"
+#include "PhysicalFontFace.hxx"
+#include "PhysicalFontFamily.hxx"
+
+#include "svids.hrc"
+
+#include <config_graphite.h>
+#if ENABLE_GRAPHITE
+#include "graphite_features.hxx"
+#endif
+
+#include "../gdi/pdfwriter_impl.hxx"
+
+#include <boost/functional/hash.hpp>
+#include <cmath>
+#include <cstring>
+#include <memory>
+#include <algorithm>
+
+using namespace ::com::sun::star;
+using namespace ::com::sun::star::uno;
+using namespace ::rtl;
+using namespace ::utl;
+
+ImplFontMetricData::ImplFontMetricData( const FontSelectPattern& rFontSelData )
+    : FontAttributes( rFontSelData )
+    , mnWidth ( rFontSelData.mnWidth )
+    , mnOrientation( (short)(rFontSelData.mnOrientation) )
+    , mnAscent( 0 )
+    , mnDescent( 0 )
+    , mnIntLeading( 0 )
+    , mnExtLeading( 0 )
+    , mnSlant( 0 )
+    , mnMinKashida( 0 )
+    , mbScalableFont( false )
+    , mbTrueTypeFont( false )
+    , mbKernableFont( false )
+    , mbFullstopCentered( false )
+    , mnBulletOffset( 0 )
+    , mnUnderlineSize( 0 )
+    , mnUnderlineOffset( 0 )
+    , mnBUnderlineSize( 0 )
+    , mnBUnderlineOffset( 0 )
+    , mnDUnderlineSize( 0 )
+    , mnDUnderlineOffset1( 0 )
+    , mnDUnderlineOffset2( 0 )
+    , mnWUnderlineSize( 0 )
+    , mnWUnderlineOffset( 0 )
+    , mnAboveUnderlineSize( 0 )
+    , mnAboveUnderlineOffset( 0 )
+    , mnAboveBUnderlineSize( 0 )
+    , mnAboveBUnderlineOffset( 0 )
+    , mnAboveDUnderlineSize( 0 )
+    , mnAboveDUnderlineOffset1( 0 )
+    , mnAboveDUnderlineOffset2( 0 )
+    , mnAboveWUnderlineSize( 0 )
+    , mnAboveWUnderlineOffset( 0 )
+    , mnStrikeoutSize( 0 )
+    , mnStrikeoutOffset( 0 )
+    , mnBStrikeoutSize( 0 )
+    , mnBStrikeoutOffset( 0 )
+    , mnDStrikeoutSize( 0 )
+    , mnDStrikeoutOffset1( 0 )
+    , mnDStrikeoutOffset2( 0 )
+{
+    // intialize the used font name
+    if( rFontSelData.mpFontData )
+    {
+        SetFamilyName( rFontSelData.mpFontData->GetFamilyName() );
+        SetStyleName( rFontSelData.mpFontData->GetStyleName() );
+        SetBuiltInFontFlag( rFontSelData.mpFontData->IsBuiltInFont() );
+        SetKernableFlag( true );
+    }
+    else
+    {
+        sal_Int32 nTokenPos = 0;
+        SetFamilyName( GetNextFontToken( rFontSelData.GetFamilyName(), nTokenPos ) );
+        SetStyleName( rFontSelData.GetStyleName() );
+        SetBuiltInFontFlag( false );
+        SetKernableFlag( false );
+    }
+}
+
+
+void ImplFontMetricData::ImplInitTextLineSize( const OutputDevice* pDev )
+{
+    long nDescent = mnDescent;
+    if ( nDescent <= 0 )
+    {
+        nDescent = mnAscent / 10;
+        if ( !nDescent )
+            nDescent = 1;
+    }
+
+    // #i55341# for some fonts it is not a good idea to calculate
+    // their text line metrics from the real font descent
+    // => work around this problem just for these fonts
+    if( 3*nDescent > mnAscent )
+        nDescent = mnAscent / 3;
+
+    long nLineHeight = ((nDescent*25)+50) / 100;
+    if ( !nLineHeight )
+        nLineHeight = 1;
+    long nLineHeight2 = nLineHeight / 2;
+    if ( !nLineHeight2 )
+        nLineHeight2 = 1;
+
+    long nBLineHeight = ((nDescent*50)+50) / 100;
+    if ( nBLineHeight == nLineHeight )
+        nBLineHeight++;
+    long nBLineHeight2 = nBLineHeight/2;
+    if ( !nBLineHeight2 )
+        nBLineHeight2 = 1;
+
+    long n2LineHeight = ((nDescent*16)+50) / 100;
+    if ( !n2LineHeight )
+        n2LineHeight = 1;
+    long n2LineDY = n2LineHeight;
+     /* #117909#
+      * add some pixels to minimum double line distance on higher resolution devices
+      */
+    long nMin2LineDY = 1 + pDev->GetDPIY()/150;
+    if ( n2LineDY < nMin2LineDY )
+        n2LineDY = nMin2LineDY;
+    long n2LineDY2 = n2LineDY/2;
+    if ( !n2LineDY2 )
+        n2LineDY2 = 1;
+
+    long nUnderlineOffset = mnDescent/2 + 1;
+    long nStrikeoutOffset = -((mnAscent - mnIntLeading) / 3);
+
+    mnUnderlineSize        = nLineHeight;
+    mnUnderlineOffset      = nUnderlineOffset - nLineHeight2;
+
+    mnBUnderlineSize       = nBLineHeight;
+    mnBUnderlineOffset     = nUnderlineOffset - nBLineHeight2;
+
+    mnDUnderlineSize       = n2LineHeight;
+    mnDUnderlineOffset1    = nUnderlineOffset - n2LineDY2 - n2LineHeight;
+    mnDUnderlineOffset2    = mnDUnderlineOffset1 + n2LineDY + n2LineHeight;
+
+    long nWCalcSize = mnDescent;
+    if ( nWCalcSize < 6 )
+    {
+        if ( (nWCalcSize == 1) || (nWCalcSize == 2) )
+            mnWUnderlineSize = nWCalcSize;
+        else
+            mnWUnderlineSize = 3;
+    }
+    else
+        mnWUnderlineSize = ((nWCalcSize*50)+50) / 100;
+
+    // Don't assume that wavelines are never placed below the descent, because for most fonts the waveline
+    // is drawn into the text
+    mnWUnderlineOffset     = nUnderlineOffset;
+
+    mnStrikeoutSize        = nLineHeight;
+    mnStrikeoutOffset      = nStrikeoutOffset - nLineHeight2;
+
+    mnBStrikeoutSize       = nBLineHeight;
+    mnBStrikeoutOffset     = nStrikeoutOffset - nBLineHeight2;
+
+    mnDStrikeoutSize       = n2LineHeight;
+    mnDStrikeoutOffset1    = nStrikeoutOffset - n2LineDY2 - n2LineHeight;
+    mnDStrikeoutOffset2    = mnDStrikeoutOffset1 + n2LineDY + n2LineHeight;
+
+    const vcl::Font& rFont ( pDev->GetFont() );
+    bool bCentered = true;
+    if (MsLangId::isCJK(rFont.GetLanguage()))
+    {
+        const OUString sFullstop( sal_Unicode( 0x3001 ) ); // Fullwidth fullstop
+        Rectangle aRect;
+        pDev->GetTextBoundRect( aRect, sFullstop );
+        const sal_uInt16 nH = rFont.GetSize().Height();
+        const sal_uInt16 nB = aRect.Left();
+        // Use 18.75% as a threshold to define a centered fullwidth fullstop.
+        // In general, nB/nH < 5% for most Japanese fonts.
+        bCentered = nB > (((nH >> 1)+nH)>>3);
+    }
+    SetFullstopCenteredFlag( bCentered );
+
+    mnBulletOffset = ( pDev->GetTextWidth( OUString( sal_Unicode( 0x20 ) ) ) - pDev->GetTextWidth( OUString( sal_Unicode( 0xb7 ) ) ) ) >> 1 ;
+
+}
+
+
+void ImplFontMetricData::ImplInitAboveTextLineSize()
+{
+    long nIntLeading = mnIntLeading;
+    // TODO: assess usage of nLeading below (changed in extleading CWS)
+    // if no leading is available, we assume 15% of the ascent
+    if ( nIntLeading <= 0 )
+    {
+        nIntLeading = mnAscent*15/100;
+        if ( !nIntLeading )
+            nIntLeading = 1;
+    }
+
+    long nLineHeight = ((nIntLeading*25)+50) / 100;
+    if ( !nLineHeight )
+        nLineHeight = 1;
+
+    long nBLineHeight = ((nIntLeading*50)+50) / 100;
+    if ( nBLineHeight == nLineHeight )
+        nBLineHeight++;
+
+    long n2LineHeight = ((nIntLeading*16)+50) / 100;
+    if ( !n2LineHeight )
+        n2LineHeight = 1;
+
+    long nCeiling = -mnAscent;
+
+    mnAboveUnderlineSize       = nLineHeight;
+    mnAboveUnderlineOffset     = nCeiling + (nIntLeading - nLineHeight + 1) / 2;
+
+    mnAboveBUnderlineSize      = nBLineHeight;
+    mnAboveBUnderlineOffset    = nCeiling + (nIntLeading - nBLineHeight + 1) / 2;
+
+    mnAboveDUnderlineSize      = n2LineHeight;
+    mnAboveDUnderlineOffset1   = nCeiling + (nIntLeading - 3*n2LineHeight + 1) / 2;
+    mnAboveDUnderlineOffset2   = nCeiling + (nIntLeading +   n2LineHeight + 1) / 2;
+
+    long nWCalcSize = nIntLeading;
+    if ( nWCalcSize < 6 )
+    {
+        if ( (nWCalcSize == 1) || (nWCalcSize == 2) )
+            mnAboveWUnderlineSize = nWCalcSize;
+        else
+            mnAboveWUnderlineSize = 3;
+    }
+    else
+        mnAboveWUnderlineSize = ((nWCalcSize*50)+50) / 100;
+
+    mnAboveWUnderlineOffset = nCeiling + (nIntLeading + 1) / 2;
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/source/gdi/pdfwriter_impl.cxx b/vcl/source/gdi/pdfwriter_impl.cxx
index ce3e32f..05cc9bc 100644
--- a/vcl/source/gdi/pdfwriter_impl.cxx
+++ b/vcl/source/gdi/pdfwriter_impl.cxx
@@ -9168,18 +9168,18 @@ void PDFWriterImpl::drawLayout( SalLayout& rLayout, const OUString& rText, bool
         Point aOffset = Point(0,0);
 
         if ( nEmphMark & EMPHASISMARK_POS_BELOW )
-            aOffset.Y() += m_pReferenceDevice->mpFontInstance->maFontAttributes.GetDescent() + nEmphYOff;
+            aOffset.Y() += m_pReferenceDevice->mpFontInstance->maFontMetric.GetDescent() + nEmphYOff;
         else
-            aOffset.Y() -= m_pReferenceDevice->mpFontInstance->maFontAttributes.GetAscent() + nEmphYOff;
+            aOffset.Y() -= m_pReferenceDevice->mpFontInstance->maFontMetric.GetAscent() + nEmphYOff;
 
         long nEmphWidth2     = nEmphWidth / 2;
         long nEmphHeight2    = nEmphHeight / 2;
         aOffset += Point( nEmphWidth2, nEmphHeight2 );
 
         if ( eAlign == ALIGN_BOTTOM )
-            aOffset.Y() -= m_pReferenceDevice->mpFontInstance->maFontAttributes.GetDescent();
+            aOffset.Y() -= m_pReferenceDevice->mpFontInstance->maFontMetric.GetDescent();
         else if ( eAlign == ALIGN_TOP )
-            aOffset.Y() += m_pReferenceDevice->mpFontInstance->maFontAttributes.GetAscent();
+            aOffset.Y() += m_pReferenceDevice->mpFontInstance->maFontMetric.GetAscent();
 
         for( int nStart = 0;;)
         {
@@ -9497,17 +9497,17 @@ void PDFWriterImpl::drawWaveTextLine( OStringBuffer& aLine, long nWidth, FontUnd
 
     if ( bIsAbove )
     {
-        if ( !pFontInstance->maFontAttributes.GetAboveWavelineUnderlineSize() )
+        if ( !pFontInstance->maFontMetric.GetAboveWavelineUnderlineSize() )
             m_pReferenceDevice->ImplInitAboveTextLineSize();
-        nLineHeight = HCONV( pFontInstance->maFontAttributes.GetAboveWavelineUnderlineSize() );
-        nLinePos = HCONV( pFontInstance->maFontAttributes.GetAboveWavelineUnderlineOffset() );
+        nLineHeight = HCONV( pFontInstance->maFontMetric.GetAboveWavelineUnderlineSize() );
+        nLinePos = HCONV( pFontInstance->maFontMetric.GetAboveWavelineUnderlineOffset() );
     }
     else
     {
-        if ( !pFontInstance->maFontAttributes.GetWavelineUnderlineSize() )
+        if ( !pFontInstance->maFontMetric.GetWavelineUnderlineSize() )
             m_pReferenceDevice->ImplInitTextLineSize();
-        nLineHeight = HCONV( pFontInstance->maFontAttributes.GetWavelineUnderlineSize() );
-        nLinePos = HCONV( pFontInstance->maFontAttributes.GetWavelineUnderlineOffset() );
+        nLineHeight = HCONV( pFontInstance->maFontMetric.GetWavelineUnderlineSize() );
+        nLinePos = HCONV( pFontInstance->maFontMetric.GetWavelineUnderlineOffset() );
     }
     if ( (eTextLine == UNDERLINE_SMALLWAVE) && (nLineHeight > 3) )
         nLineHeight = 3;
@@ -9576,17 +9576,17 @@ void PDFWriterImpl::drawStraightTextLine( OStringBuffer& aLine, long nWidth, Fon
         case UNDERLINE_DASHDOTDOT:
             if ( bIsAbove )
             {
-                if ( !pFontInstance->maFontAttributes.GetAboveUnderlineSize() )
+                if ( !pFontInstance->maFontMetric.GetAboveUnderlineSize() )
                     m_pReferenceDevice->ImplInitAboveTextLineSize();
-                nLineHeight = HCONV( pFontInstance->maFontAttributes.GetAboveUnderlineSize() );
-                nLinePos    = HCONV( pFontInstance->maFontAttributes.GetAboveUnderlineOffset() );
+                nLineHeight = HCONV( pFontInstance->maFontMetric.GetAboveUnderlineSize() );
+                nLinePos    = HCONV( pFontInstance->maFontMetric.GetAboveUnderlineOffset() );
             }
             else
             {
-                if ( !pFontInstance->maFontAttributes.GetUnderlineSize() )
+                if ( !pFontInstance->maFontMetric.GetUnderlineSize() )
                     m_pReferenceDevice->ImplInitTextLineSize();
-                nLineHeight = HCONV( pFontInstance->maFontAttributes.GetUnderlineSize() );
-                nLinePos    = HCONV( pFontInstance->maFontAttributes.GetUnderlineOffset() );
+                nLineHeight = HCONV( pFontInstance->maFontMetric.GetUnderlineSize() );
+                nLinePos    = HCONV( pFontInstance->maFontMetric.GetUnderlineOffset() );
             }
             break;
         case UNDERLINE_BOLD:
@@ -9597,36 +9597,36 @@ void PDFWriterImpl::drawStraightTextLine( OStringBuffer& aLine, long nWidth, Fon
         case UNDERLINE_BOLDDASHDOTDOT:
             if ( bIsAbove )
             {
-                if ( !pFontInstance->maFontAttributes.GetAboveBoldUnderlineSize() )
+                if ( !pFontInstance->maFontMetric.GetAboveBoldUnderlineSize() )
                     m_pReferenceDevice->ImplInitAboveTextLineSize();
-                nLineHeight = HCONV( pFontInstance->maFontAttributes.GetAboveBoldUnderlineSize() );
-                nLinePos    = HCONV( pFontInstance->maFontAttributes.GetAboveBoldUnderlineOffset() );
+                nLineHeight = HCONV( pFontInstance->maFontMetric.GetAboveBoldUnderlineSize() );
+                nLinePos    = HCONV( pFontInstance->maFontMetric.GetAboveBoldUnderlineOffset() );
             }
             else
             {
-                if ( !pFontInstance->maFontAttributes.GetBoldUnderlineSize() )
+                if ( !pFontInstance->maFontMetric.GetBoldUnderlineSize() )
                     m_pReferenceDevice->ImplInitTextLineSize();
-                nLineHeight = HCONV( pFontInstance->maFontAttributes.GetBoldUnderlineSize() );
-                nLinePos    = HCONV( pFontInstance->maFontAttributes.GetBoldUnderlineOffset() );
+                nLineHeight = HCONV( pFontInstance->maFontMetric.GetBoldUnderlineSize() );
+                nLinePos    = HCONV( pFontInstance->maFontMetric.GetBoldUnderlineOffset() );
                 nLinePos += nLineHeight/2;
             }
             break;
         case UNDERLINE_DOUBLE:
             if ( bIsAbove )
             {
-                if ( !pFontInstance->maFontAttributes.GetAboveDoubleUnderlineSize() )
+                if ( !pFontInstance->maFontMetric.GetAboveDoubleUnderlineSize() )
                     m_pReferenceDevice->ImplInitAboveTextLineSize();
-                nLineHeight = HCONV( pFontInstance->maFontAttributes.GetAboveDoubleUnderlineSize() );
-                nLinePos    = HCONV( pFontInstance->maFontAttributes.GetAboveDoubleUnderlineOffset1() );
-                nLinePos2   = HCONV( pFontInstance->maFontAttributes.GetAboveDoubleUnderlineOffset2() );
+                nLineHeight = HCONV( pFontInstance->maFontMetric.GetAboveDoubleUnderlineSize() );
+                nLinePos    = HCONV( pFontInstance->maFontMetric.GetAboveDoubleUnderlineOffset1() );
+                nLinePos2   = HCONV( pFontInstance->maFontMetric.GetAboveDoubleUnderlineOffset2() );
             }
             else
             {
-                if ( !pFontInstance->maFontAttributes.GetDoubleUnderlineSize() )
+                if ( !pFontInstance->maFontMetric.GetDoubleUnderlineSize() )
                     m_pReferenceDevice->ImplInitTextLineSize();
-                nLineHeight = HCONV( pFontInstance->maFontAttributes.GetDoubleUnderlineSize() );
-                nLinePos    = HCONV( pFontInstance->maFontAttributes.GetDoubleUnderlineOffset1() );
-                nLinePos2   = HCONV( pFontInstance->maFontAttributes.GetDoubleUnderlineOffset2() );
+                nLineHeight = HCONV( pFontInstance->maFontMetric.GetDoubleUnderlineSize() );
+                nLinePos    = HCONV( pFontInstance->maFontMetric.GetDoubleUnderlineOffset1() );
+                nLinePos2   = HCONV( pFontInstance->maFontMetric.GetDoubleUnderlineOffset2() );
             }
             break;
         default:
@@ -9739,23 +9739,23 @@ void PDFWriterImpl::drawStrikeoutLine( OStringBuffer& aLine, long nWidth, FontSt
     switch ( eStrikeout )
     {
         case STRIKEOUT_SINGLE:
-            if ( !pFontInstance->maFontAttributes.GetStrikeoutSize() )
+            if ( !pFontInstance->maFontMetric.GetStrikeoutSize() )
                 m_pReferenceDevice->ImplInitTextLineSize();
-            nLineHeight = HCONV( pFontInstance->maFontAttributes.GetStrikeoutSize() );
-            nLinePos    = HCONV( pFontInstance->maFontAttributes.GetStrikeoutOffset() );
+            nLineHeight = HCONV( pFontInstance->maFontMetric.GetStrikeoutSize() );
+            nLinePos    = HCONV( pFontInstance->maFontMetric.GetStrikeoutOffset() );
             break;
         case STRIKEOUT_BOLD:
-            if ( !pFontInstance->maFontAttributes.GetBoldStrikeoutSize() )
+            if ( !pFontInstance->maFontMetric.GetBoldStrikeoutSize() )
                 m_pReferenceDevice->ImplInitTextLineSize();
-            nLineHeight = HCONV( pFontInstance->maFontAttributes.GetBoldStrikeoutSize() );
-            nLinePos    = HCONV( pFontInstance->maFontAttributes.GetBoldStrikeoutOffset() );
+            nLineHeight = HCONV( pFontInstance->maFontMetric.GetBoldStrikeoutSize() );
+            nLinePos    = HCONV( pFontInstance->maFontMetric.GetBoldStrikeoutOffset() );
             break;
         case STRIKEOUT_DOUBLE:
-            if ( !pFontInstance->maFontAttributes.GetDoubleStrikeoutSize() )
+            if ( !pFontInstance->maFontMetric.GetDoubleStrikeoutSize() )
                 m_pReferenceDevice->ImplInitTextLineSize();
-            nLineHeight = HCONV( pFontInstance->maFontAttributes.GetDoubleStrikeoutSize() );
-            nLinePos    = HCONV( pFontInstance->maFontAttributes.GetDoubleStrikeoutOffset1() );
-            nLinePos2   = HCONV( pFontInstance->maFontAttributes.GetDoubleStrikeoutOffset2() );
+            nLineHeight = HCONV( pFontInstance->maFontMetric.GetDoubleStrikeoutSize() );
+            nLinePos    = HCONV( pFontInstance->maFontMetric.GetDoubleStrikeoutOffset1() );
+            nLinePos2   = HCONV( pFontInstance->maFontMetric.GetDoubleStrikeoutOffset2() );
             break;
         default:
             break;
@@ -9876,9 +9876,9 @@ void PDFWriterImpl::drawTextLine( const Point& rPos, long nWidth, FontStrikeout
     Point aPos( rPos );
     TextAlign eAlign = m_aCurrentPDFState.m_aFont.GetAlign();
     if( eAlign == ALIGN_TOP )
-        aPos.Y() += HCONV( pFontInstance->maFontAttributes.GetAscent() );
+        aPos.Y() += HCONV( pFontInstance->maFontMetric.GetAscent() );
     else if( eAlign == ALIGN_BOTTOM )
-        aPos.Y() -= HCONV( pFontInstance->maFontAttributes.GetDescent() );
+        aPos.Y() -= HCONV( pFontInstance->maFontMetric.GetDescent() );
 
     OStringBuffer aLine( 512 );
     // save GS
diff --git a/vcl/source/gdi/pdfwriter_impl.hxx b/vcl/source/gdi/pdfwriter_impl.hxx
index 1a30f2f..67a465c 100644
--- a/vcl/source/gdi/pdfwriter_impl.hxx
+++ b/vcl/source/gdi/pdfwriter_impl.hxx
@@ -47,7 +47,6 @@
 
 class StyleSettings;
 class FontSelectPattern;
-class FontAttributes;
 class FontSubsetInfo;
 class ZCodec;
 class EncHashTransporter;
diff --git a/vcl/source/gdi/print.cxx b/vcl/source/gdi/print.cxx
index fa3a065..fcb25d5 100644
--- a/vcl/source/gdi/print.cxx
+++ b/vcl/source/gdi/print.cxx
@@ -1817,7 +1817,7 @@ void Printer::InitFont() const
 
 void Printer::SetFontOrientation( LogicalFontInstance* const pFontEntry ) const
 {
-    pFontEntry->mnOrientation = pFontEntry->maFontAttributes.GetOrientation();
+    pFontEntry->mnOrientation = pFontEntry->maFontMetric.GetOrientation();
 }
 
 void Printer::DrawImage( const Point&, const Image&, DrawImageFlags )
diff --git a/vcl/source/gdi/virdev.cxx b/vcl/source/gdi/virdev.cxx
index e3e129e..8e426ea 100644
--- a/vcl/source/gdi/virdev.cxx
+++ b/vcl/source/gdi/virdev.cxx
@@ -30,6 +30,7 @@
 #include <salvd.hxx>
 #include <outdev.h>
 #include "PhysicalFontCollection.hxx"
+#include "impfontmetricdata.hxx"
 #include <svdata.hxx>
 
 #include <vcl/ITiledRenderable.hxx>
@@ -564,9 +565,9 @@ long VirtualDevice::GetFontExtLeading() const
 #endif
 
     LogicalFontInstance* pFontInstance = mpFontInstance;
-    FontAttributes* pFontAttributes = &(pFontInstance->maFontAttributes);
+    ImplFontMetricData* pFontMetric = &(pFontInstance->maFontMetric);
 
-    return pFontAttributes->GetExternalLeading();
+    return pFontMetric->GetExternalLeading();
 }
 
 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/vcl/source/outdev/font.cxx b/vcl/source/outdev/font.cxx
index 7732b24..ee4c204 100644
--- a/vcl/source/outdev/font.cxx
+++ b/vcl/source/outdev/font.cxx
@@ -35,6 +35,7 @@
 #include "outdata.hxx"
 #include "fontinstance.hxx"
 #include "fontattributes.hxx"
+#include "impfontmetricdata.hxx"
 
 #include "outdev.h"
 #include "window.h"
@@ -190,7 +191,7 @@ FontMetric OutputDevice::GetFontMetric() const
         return aMetric;
 
     LogicalFontInstance* pFontInstance = mpFontInstance;
-    FontAttributes* pFontAttributes = &(pFontInstance->maFontAttributes);
+    ImplFontMetricData* pFontAttributes = &(pFontInstance->maFontMetric);
 
     // prepare metric
     aMetric.Font::operator=( maFont );
@@ -209,7 +210,7 @@ FontMetric OutputDevice::GetFontMetric() const
         aMetric.SetOrientation( pFontInstance->mnOwnOrientation );
     else
         aMetric.SetOrientation( pFontAttributes->GetOrientation() );
-    if( !pFontInstance->maFontAttributes.IsKernable() )
+    if( !pFontInstance->maFontMetric.IsKernable() )
          aMetric.SetKerning( maFont.GetKerning() & ~FontKerning::FontSpecific );
 
     // set remaining metric fields
@@ -486,7 +487,7 @@ FontEmphasisMark OutputDevice::ImplGetEmphasisMarkStyle( const vcl::Font& rFont
 long OutputDevice::GetFontExtLeading() const
 {
     LogicalFontInstance*      pFontInstance = mpFontInstance;
-    FontAttributes* pFontAttributes = &(pFontInstance->maFontAttributes);
+    ImplFontMetricData* pFontAttributes = &(pFontInstance->maFontMetric);
 
     return pFontAttributes->GetExternalLeading();
 }
@@ -1102,13 +1103,13 @@ bool OutputDevice::ImplNewFont() const
         {
             pFontEntry->mbInit = true;
 
-            pFontEntry->maFontAttributes.SetOrientation( sal::static_int_cast<short>(pFontEntry->maFontSelData.mnOrientation) );
-            pGraphics->GetFontAttributes( &(pFontEntry->maFontAttributes) );
+            pFontEntry->maFontMetric.SetOrientation( sal::static_int_cast<short>(pFontEntry->maFontSelData.mnOrientation) );
+            pGraphics->GetFontMetric( &(pFontEntry->maFontMetric) );
 
-            pFontEntry->maFontAttributes.ImplInitTextLineSize( this );
-            pFontEntry->maFontAttributes.ImplInitAboveTextLineSize();
+            pFontEntry->maFontMetric.ImplInitTextLineSize( this );
+            pFontEntry->maFontMetric.ImplInitAboveTextLineSize();
 
-            pFontEntry->mnLineHeight = pFontEntry->maFontAttributes.GetAscent() + pFontEntry->maFontAttributes.GetDescent();
+            pFontEntry->mnLineHeight = pFontEntry->maFontMetric.GetAscent() + pFontEntry->maFontMetric.GetDescent();
 
             SetFontOrientation( pFontEntry );
         }
@@ -1118,7 +1119,7 @@ bool OutputDevice::ImplNewFont() const
     if ( maFont.GetKerning() & FontKerning::FontSpecific )
     {
         // TODO: test if physical font supports kerning and disable if not
-        if( pFontEntry->maFontAttributes.IsKernable() )
+        if( pFontEntry->maFontMetric.IsKernable() )
             mbKerning = true;
     }
     else
@@ -1154,7 +1155,7 @@ bool OutputDevice::ImplNewFont() const
     else if ( eAlign == ALIGN_TOP )
     {
         mnTextOffX = 0;
-        mnTextOffY = +pFontEntry->maFontAttributes.GetAscent() + mnEmphasisAscent;
+        mnTextOffY = +pFontEntry->maFontMetric.GetAscent() + mnEmphasisAscent;
         if ( pFontEntry->mnOrientation )
         {
             Point aOriginPt(0, 0);
@@ -1164,7 +1165,7 @@ bool OutputDevice::ImplNewFont() const
     else // eAlign == ALIGN_BOTTOM
     {
         mnTextOffX = 0;
-        mnTextOffY = -pFontEntry->maFontAttributes.GetDescent() + mnEmphasisDescent;
+        mnTextOffY = -pFontEntry->maFontMetric.GetDescent() + mnEmphasisDescent;
         if ( pFontEntry->mnOrientation )
         {
             Point aOriginPt(0, 0);
@@ -1182,7 +1183,7 @@ bool OutputDevice::ImplNewFont() const
     // #95414# fix for OLE objects which use scale factors very creatively
     if( mbMap && !aSize.Width() )
     {
-        int nOrigWidth = pFontEntry->maFontAttributes.GetWidth();
+        int nOrigWidth = pFontEntry->maFontMetric.GetWidth();
         float fStretch = (float)maMapRes.mnMapScNumX * maMapRes.mnMapScDenomY;
         fStretch /= (float)maMapRes.mnMapScNumY * maMapRes.mnMapScDenomX;
         int nNewWidth = (int)(nOrigWidth * fStretch + 0.5);
@@ -1203,14 +1204,14 @@ bool OutputDevice::ImplNewFont() const
 
 void OutputDevice::SetFontOrientation( LogicalFontInstance* const pFontEntry ) const
 {
-    if( pFontEntry->maFontSelData.mnOrientation && !pFontEntry->maFontAttributes.GetOrientation() )
+    if( pFontEntry->maFontSelData.mnOrientation && !pFontEntry->maFontMetric.GetOrientation() )
     {
         pFontEntry->mnOwnOrientation = sal::static_int_cast<short>(pFontEntry->maFontSelData.mnOrientation);
         pFontEntry->mnOrientation = pFontEntry->mnOwnOrientation;
     }
     else
     {
-        pFontEntry->mnOrientation = pFontEntry->maFontAttributes.GetOrientation();
+        pFontEntry->mnOrientation = pFontEntry->maFontMetric.GetOrientation();
     }
 }
 
@@ -1300,9 +1301,9 @@ void OutputDevice::ImplDrawEmphasisMarks( SalLayout& rSalLayout )
     Point aOffset = Point(0,0);
 
     if ( nEmphasisMark & EMPHASISMARK_POS_BELOW )
-        aOffset.Y() += mpFontInstance->maFontAttributes.GetDescent() + nEmphasisYOff;
+        aOffset.Y() += mpFontInstance->maFontMetric.GetDescent() + nEmphasisYOff;
     else
-        aOffset.Y() -= mpFontInstance->maFontAttributes.GetAscent() + nEmphasisYOff;
+        aOffset.Y() -= mpFontInstance->maFontMetric.GetAscent() + nEmphasisYOff;
 
     long nEmphasisWidth2  = nEmphasisWidth / 2;
     long nEmphasisHeight2 = nEmphasisHeight / 2;
@@ -1464,7 +1465,7 @@ long OutputDevice::GetMinKashida() const
         return 0;
 
     LogicalFontInstance* pFontInstance = mpFontInstance;
-    FontAttributes* pFontAttributes = &(pFontInstance->maFontAttributes);
+    ImplFontMetricData* pFontAttributes = &(pFontInstance->maFontMetric);
     return ImplDevicePixelToLogicWidth( pFontAttributes->GetMinKashida() );
 }
 
diff --git a/vcl/source/outdev/text.cxx b/vcl/source/outdev/text.cxx
index e62ea7c..912249a 100644
--- a/vcl/source/outdev/text.cxx
+++ b/vcl/source/outdev/text.cxx
@@ -177,7 +177,7 @@ void OutputDevice::ImplDrawTextBackground( const SalLayout& rSalLayout )
     mpGraphics->SetFillColor( ImplColorToSal( GetTextFillColor() ) );
     mbInitFillColor = true;
 
-    ImplDrawTextRect( nX, nY, 0, -(mpFontInstance->maFontAttributes.GetAscent() + mnEmphasisAscent),
+    ImplDrawTextRect( nX, nY, 0, -(mpFontInstance->maFontMetric.GetAscent() + mnEmphasisAscent),
                       nWidth,
                       mpFontInstance->mnLineHeight+mnEmphasisAscent+mnEmphasisDescent );
 }
@@ -191,7 +191,7 @@ Rectangle OutputDevice::ImplGetTextBoundRect( const SalLayout& rSalLayout )
     long nWidth = rSalLayout.GetTextWidth();
     long nHeight = mpFontInstance->mnLineHeight + mnEmphasisAscent + mnEmphasisDescent;
 
-    nY -= mpFontInstance->maFontAttributes.GetAscent() + mnEmphasisAscent;
+    nY -= mpFontInstance->maFontMetric.GetAscent() + mnEmphasisAscent;
 
     if ( mpFontInstance->mnOrientation )
     {
@@ -232,7 +232,7 @@ bool OutputDevice::ImplDrawRotateText( SalLayout& rSalLayout )
     {
         // guess vertical text extents if GetBoundRect failed
         int nRight = rSalLayout.GetTextWidth();
-        int nTop = mpFontInstance->maFontAttributes.GetAscent() + mnEmphasisAscent;
+        int nTop = mpFontInstance->maFontMetric.GetAscent() + mnEmphasisAscent;
         long nHeight = mpFontInstance->mnLineHeight + mnEmphasisAscent + mnEmphasisDescent;
         aBoundRect = Rectangle( 0, -nTop, nRight, nHeight - nTop );
     }
@@ -2621,7 +2621,7 @@ bool OutputDevice::GetTextBoundRect( Rectangle& rRect,
         Point aTopLeft( nLeft, nTop );
         aTopLeft -= aOffset;
         // adjust to text alignment
-        aTopLeft.Y()+= mnTextOffY - (mpFontInstance->maFontAttributes.GetAscent() + mnEmphasisAscent);
+        aTopLeft.Y()+= mnTextOffY - (mpFontInstance->maFontMetric.GetAscent() + mnEmphasisAscent);
         // convert to logical coordinates
         aSize = PixelToLogic( aSize );
         aTopLeft.X() = ImplDevicePixelToLogicWidth( aTopLeft.X() );
diff --git a/vcl/source/outdev/textline.cxx b/vcl/source/outdev/textline.cxx
index 3ced7c8..7e147d8 100644
--- a/vcl/source/outdev/textline.cxx
+++ b/vcl/source/outdev/textline.cxx
@@ -56,12 +56,12 @@ bool OutputDevice::ImplIsUnderlineAbove( const vcl::Font& rFont )
 
 void OutputDevice::ImplInitTextLineSize()
 {
-    mpFontInstance->maFontAttributes.ImplInitTextLineSize( this );
+    mpFontInstance->maFontMetric.ImplInitTextLineSize( this );
 }
 
 void OutputDevice::ImplInitAboveTextLineSize()
 {
-    mpFontInstance->maFontAttributes.ImplInitAboveTextLineSize();
+    mpFontInstance->maFontMetric.ImplInitAboveTextLineSize();
 }
 
 void OutputDevice::ImplDrawWavePixel( long nOriginX, long nOriginY,
@@ -221,13 +221,13 @@ void OutputDevice::ImplDrawWaveTextLine( long nBaseX, long nBaseY,
 
     if ( bIsAbove )
     {
-        nLineHeight = pFontInstance->maFontAttributes.GetAboveWavelineUnderlineSize();
-        nLinePos = pFontInstance->maFontAttributes.GetAboveWavelineUnderlineOffset();
+        nLineHeight = pFontInstance->maFontMetric.GetAboveWavelineUnderlineSize();
+        nLinePos = pFontInstance->maFontMetric.GetAboveWavelineUnderlineOffset();
     }
     else
     {
-        nLineHeight = pFontInstance->maFontAttributes.GetWavelineUnderlineSize();
-        nLinePos = pFontInstance->maFontAttributes.GetWavelineUnderlineOffset();
+        nLineHeight = pFontInstance->maFontMetric.GetWavelineUnderlineSize();
+        nLinePos = pFontInstance->maFontMetric.GetWavelineUnderlineOffset();
     }
     if ( (eTextLine == UNDERLINE_SMALLWAVE) && (nLineHeight > 3) )
         nLineHeight = 3;
@@ -303,13 +303,13 @@ void OutputDevice::ImplDrawStraightTextLine( long nBaseX, long nBaseY,
     case UNDERLINE_DASHDOTDOT:
         if ( bIsAbove )
         {
-            nLineHeight = pFontInstance->maFontAttributes.GetAboveUnderlineSize();
-            nLinePos    = nY + pFontInstance->maFontAttributes.GetAboveUnderlineOffset();
+            nLineHeight = pFontInstance->maFontMetric.GetAboveUnderlineSize();
+            nLinePos    = nY + pFontInstance->maFontMetric.GetAboveUnderlineOffset();
         }
         else
         {
-            nLineHeight = pFontInstance->maFontAttributes.GetUnderlineSize();
-            nLinePos    = nY + pFontInstance->maFontAttributes.GetUnderlineOffset();
+            nLineHeight = pFontInstance->maFontMetric.GetUnderlineSize();
+            nLinePos    = nY + pFontInstance->maFontMetric.GetUnderlineOffset();
         }
         break;
     case UNDERLINE_BOLD:
@@ -320,27 +320,27 @@ void OutputDevice::ImplDrawStraightTextLine( long nBaseX, long nBaseY,
     case UNDERLINE_BOLDDASHDOTDOT:
         if ( bIsAbove )
         {
-            nLineHeight = pFontInstance->maFontAttributes.GetAboveBoldUnderlineSize();
-            nLinePos    = nY + pFontInstance->maFontAttributes.GetAboveBoldUnderlineOffset();
+            nLineHeight = pFontInstance->maFontMetric.GetAboveBoldUnderlineSize();
+            nLinePos    = nY + pFontInstance->maFontMetric.GetAboveBoldUnderlineOffset();
         }
         else
         {
-            nLineHeight = pFontInstance->maFontAttributes.GetBoldUnderlineSize();
-            nLinePos    = nY + pFontInstance->maFontAttributes.GetBoldUnderlineOffset();
+            nLineHeight = pFontInstance->maFontMetric.GetBoldUnderlineSize();
+            nLinePos    = nY + pFontInstance->maFontMetric.GetBoldUnderlineOffset();
         }
         break;
     case UNDERLINE_DOUBLE:
         if ( bIsAbove )
         {
-            nLineHeight = pFontInstance->maFontAttributes.GetAboveDoubleUnderlineSize();
-            nLinePos    = nY + pFontInstance->maFontAttributes.GetAboveDoubleUnderlineOffset1();
-            nLinePos2   = nY + pFontInstance->maFontAttributes.GetAboveDoubleUnderlineOffset2();
+            nLineHeight = pFontInstance->maFontMetric.GetAboveDoubleUnderlineSize();
+            nLinePos    = nY + pFontInstance->maFontMetric.GetAboveDoubleUnderlineOffset1();
+            nLinePos2   = nY + pFontInstance->maFontMetric.GetAboveDoubleUnderlineOffset2();
         }
         else
         {
-            nLineHeight = pFontInstance->maFontAttributes.GetDoubleUnderlineSize();
-            nLinePos    = nY + pFontInstance->maFontAttributes.GetDoubleUnderlineOffset1();
-            nLinePos2   = nY + pFontInstance->maFontAttributes.GetDoubleUnderlineOffset2();
+            nLineHeight = pFontInstance->maFontMetric.GetDoubleUnderlineSize();
+            nLinePos    = nY + pFontInstance->maFontMetric.GetDoubleUnderlineOffset1();
+            nLinePos2   = nY + pFontInstance->maFontMetric.GetDoubleUnderlineOffset2();
         }
         break;
     default:
@@ -538,17 +538,17 @@ void OutputDevice::ImplDrawStrikeoutLine( long nBaseX, long nBaseY,
     switch ( eStrikeout )
     {
     case STRIKEOUT_SINGLE:
-        nLineHeight = pFontInstance->maFontAttributes.GetStrikeoutSize();
-        nLinePos    = nY + pFontInstance->maFontAttributes.GetStrikeoutOffset();
+        nLineHeight = pFontInstance->maFontMetric.GetStrikeoutSize();
+        nLinePos    = nY + pFontInstance->maFontMetric.GetStrikeoutOffset();
         break;
     case STRIKEOUT_BOLD:
-        nLineHeight = pFontInstance->maFontAttributes.GetBoldStrikeoutSize();
-        nLinePos    = nY + pFontInstance->maFontAttributes.GetBoldStrikeoutOffset();
+        nLineHeight = pFontInstance->maFontMetric.GetBoldStrikeoutSize();
+        nLinePos    = nY + pFontInstance->maFontMetric.GetBoldStrikeoutOffset();
         break;
     case STRIKEOUT_DOUBLE:
-        nLineHeight = pFontInstance->maFontAttributes.GetDoubleStrikeoutSize();
-        nLinePos    = nY + pFontInstance->maFontAttributes.GetDoubleStrikeoutOffset1();
-        nLinePos2   = nY + pFontInstance->maFontAttributes.GetDoubleStrikeoutOffset2();
+        nLineHeight = pFontInstance->maFontMetric.GetDoubleStrikeoutSize();
+        nLinePos    = nY + pFontInstance->maFontMetric.GetDoubleStrikeoutOffset1();
+        nLinePos2   = nY + pFontInstance->maFontMetric.GetDoubleStrikeoutOffset2();
         break;
     default:
         break;
@@ -652,8 +652,8 @@ void OutputDevice::ImplDrawStrikeoutChar( long nBaseX, long nBaseY,
     Rectangle aPixelRect;
     aPixelRect.Left() = nBaseX+mnTextOffX;
     aPixelRect.Right() = aPixelRect.Left()+nWidth;
-    aPixelRect.Bottom() = nBaseY+mpFontInstance->maFontAttributes.GetDescent();
-    aPixelRect.Top() = nBaseY-mpFontInstance->maFontAttributes.GetAscent();
+    aPixelRect.Bottom() = nBaseY+mpFontInstance->maFontMetric.GetDescent();
+    aPixelRect.Top() = nBaseY-mpFontInstance->maFontMetric.GetAscent();
 
     if (mpFontInstance->mnOrientation)
     {
@@ -1043,9 +1043,9 @@ void OutputDevice::DrawWaveLine( const Point& rStartPos, const Point& rEndPos )
 
     // #109280# make sure the waveline does not exceed the descent to avoid paint problems
     LogicalFontInstance* pFontInstance = mpFontInstance;
-    if( nWaveHeight > pFontInstance->maFontAttributes.GetWavelineUnderlineSize() )
+    if( nWaveHeight > pFontInstance->maFontMetric.GetWavelineUnderlineSize() )
     {
-        nWaveHeight = pFontInstance->maFontAttributes.GetWavelineUnderlineSize();
+        nWaveHeight = pFontInstance->maFontMetric.GetWavelineUnderlineSize();
     }
     ImplDrawWaveLine(nStartX, nStartY, 0, 0,
                      nEndX-nStartX, nWaveHeight,
diff --git a/vcl/unx/generic/gdi/cairotextrender.cxx b/vcl/unx/generic/gdi/cairotextrender.cxx
index 6808193..398b756 100644
--- a/vcl/unx/generic/gdi/cairotextrender.cxx
+++ b/vcl/unx/generic/gdi/cairotextrender.cxx
@@ -32,6 +32,7 @@
 #include "unx/fc_fontoptions.hxx"
 #include "PhysicalFontFace.hxx"
 #include "impfont.hxx"
+#include "impfontmetricdata.hxx"
 
 #include <config_graphite.h>
 #if ENABLE_GRAPHITE
@@ -454,7 +455,7 @@ FontConfigFontOptions* GetFCFontOptions( const FontAttributes& rFontAttributes,
 }
 
 void
-CairoTextRender::GetFontAttributes( FontAttributes *pFontAttributes, int nFallbackLevel )
+CairoTextRender::GetFontMetric( ImplFontMetricData *pFontMetric, int nFallbackLevel )
 {
     if( nFallbackLevel >= MAX_FALLBACK )
         return;
@@ -462,7 +463,7 @@ CairoTextRender::GetFontAttributes( FontAttributes *pFontAttributes, int nFallba
     if( mpServerFont[nFallbackLevel] != nullptr )
     {
         long rDummyFactor;
-        mpServerFont[nFallbackLevel]->FetchFontAttributes( *pFontAttributes, rDummyFactor );
+        mpServerFont[nFallbackLevel]->FetchFontMetric( *pFontMetric, rDummyFactor );
     }
 }
 
diff --git a/vcl/unx/generic/gdi/salgdi3.cxx b/vcl/unx/generic/gdi/salgdi3.cxx
index 5112546..568695c 100644
--- a/vcl/unx/generic/gdi/salgdi3.cxx
+++ b/vcl/unx/generic/gdi/salgdi3.cxx
@@ -136,9 +136,9 @@ void X11SalGraphics::GetDevFontList( PhysicalFontCollection* pFontCollection )
 }
 
 void
-X11SalGraphics::GetFontAttributes( FontAttributes *pFontAttributes, int nFallbackLevel )
+X11SalGraphics::GetFontMetric( ImplFontMetricData *pFontMetric, int nFallbackLevel )
 {
-    mxTextRenderImpl->GetFontAttributes(pFontAttributes, nFallbackLevel);
+    mxTextRenderImpl->GetFontMetric(pFontMetric, nFallbackLevel);
 }
 
 bool X11SalGraphics::GetGlyphBoundRect( sal_GlyphId aGlyphId, Rectangle& rRect )
diff --git a/vcl/unx/generic/glyphs/freetype_glyphcache.cxx b/vcl/unx/generic/glyphs/freetype_glyphcache.cxx
index 2f539a9..a9d1287 100644
--- a/vcl/unx/generic/glyphs/freetype_glyphcache.cxx
+++ b/vcl/unx/generic/glyphs/freetype_glyphcache.cxx
@@ -614,9 +614,9 @@ ServerFont::~ServerFont()
 }
 
 
-void ServerFont::FetchFontAttributes( FontAttributes& rTo, long& rFactor ) const
+void ServerFont::FetchFontMetric( ImplFontMetricData& rTo, long& rFactor ) const
 {
-    static_cast<FontAttributes&>(rTo) = mpFontInfo->GetFontAttributes();
+    static_cast< FontAttributes& >(rTo) = mpFontInfo->GetFontAttributes();
 
     rTo.SetScalableFlag( true ); // FIXME: Shouldn't this check FT_IS_SCALABLE( maFaceFT )?
     rTo.SetTrueTypeFlag( FT_IS_SFNT( maFaceFT ) != 0 );
diff --git a/vcl/unx/generic/print/genpspgraphics.cxx b/vcl/unx/generic/print/genpspgraphics.cxx
index ef6d063..931e87e 100644
--- a/vcl/unx/generic/print/genpspgraphics.cxx
+++ b/vcl/unx/generic/print/genpspgraphics.cxx
@@ -52,6 +52,7 @@
 #include "langboost.hxx"
 #include "fontinstance.hxx"
 #include "fontattributes.hxx"
+#include "impfontmetricdata.hxx"
 #include "PhysicalFontCollection.hxx"
 #include "PhysicalFontFace.hxx"
 #include "salbmp.hxx"
@@ -913,7 +914,7 @@ void GenPspGraphics::ClearDevFontCache()
     GlyphCache::GetInstance().ClearFontCache();
 }
 
-void GenPspGraphics::GetFontAttributes( FontAttributes *pFontAttributes, int )
+void GenPspGraphics::GetFontMetric( ImplFontMetricData *pFontMetric, int )
 {
     const psp::PrintFontManager& rMgr = psp::PrintFontManager::get();
     psp::PrintFontInfo aInfo;
@@ -921,24 +922,24 @@ void GenPspGraphics::GetFontAttributes( FontAttributes *pFontAttributes, int )
     if (rMgr.getFontInfo (m_pPrinterGfx->GetFontID(), aInfo))
     {
         FontAttributes aDFA = Info2FontAttributes( aInfo );
-        *pFontAttributes = aDFA;
-        pFontAttributes->SetBuiltInFontFlag( aDFA.IsBuiltInFont() );
-        pFontAttributes->SetScalableFlag( true );
-        pFontAttributes->SetTrueTypeFlag( false ); // FIXME, needed?
+        static_cast< FontAttributes& >(*pFontMetric) = aDFA;
+        pFontMetric->SetBuiltInFontFlag( aDFA.IsBuiltInFont() );
+        pFontMetric->SetScalableFlag( true );
+        pFontMetric->SetTrueTypeFlag( false ); // FIXME, needed?
 
-        pFontAttributes->SetOrientation( m_pPrinterGfx->GetFontAngle() );
-        pFontAttributes->SetSlant( 0 );
+        pFontMetric->SetOrientation( m_pPrinterGfx->GetFontAngle() );
+        pFontMetric->SetSlant( 0 );
 
         sal_Int32 nTextHeight   = m_pPrinterGfx->GetFontHeight();
         sal_Int32 nTextWidth    = m_pPrinterGfx->GetFontWidth();
         if( ! nTextWidth )
             nTextWidth = nTextHeight;
 
-        pFontAttributes->SetWidth( nTextWidth );
-        pFontAttributes->SetAscent( ( aInfo.m_nAscend * nTextHeight + 500 ) / 1000 );
-        pFontAttributes->SetDescent( ( aInfo.m_nDescend * nTextHeight + 500 ) / 1000 );
-        pFontAttributes->SetInternalLeading( ( aInfo.m_nLeading * nTextHeight + 500 ) / 1000 );
-        pFontAttributes->SetExternalLeading( 0 );
+        pFontMetric->SetWidth( nTextWidth );
+        pFontMetric->SetAscent( ( aInfo.m_nAscend * nTextHeight + 500 ) / 1000 );
+        pFontMetric->SetDescent( ( aInfo.m_nDescend * nTextHeight + 500 ) / 1000 );
+        pFontMetric->SetInternalLeading( ( aInfo.m_nLeading * nTextHeight + 500 ) / 1000 );
+        pFontMetric->SetExternalLeading( 0 );
     }
 }
 
diff --git a/vcl/win/gdi/salfont.cxx b/vcl/win/gdi/salfont.cxx
index 4781b14..674eeaf 100644
--- a/vcl/win/gdi/salfont.cxx
+++ b/vcl/win/gdi/salfont.cxx
@@ -50,6 +50,7 @@
 #include "win/saldata.hxx"
 #include "win/salgdi.h"
 #include "impfontcharmap.hxx"
+#include "impfontmetricdata.hxx"
 
 using namespace vcl;
 
@@ -1478,14 +1479,14 @@ sal_uInt16 WinSalGraphics::SetFont( FontSelectPattern* pFont, int nFallbackLevel
         return 0;
 }
 
-void WinSalGraphics::GetFontAttributes( FontAttributes* pFontAttributes, int nFallbackLevel )
+void WinSalGraphics::GetFontMetric( ImplFontMetricData* pFontMetric, int nFallbackLevel )
 {
     // temporarily change the HDC to the font in the fallback level
     HFONT hOldFont = SelectFont( getHDC(), mhFonts[nFallbackLevel] );
 
     wchar_t aFaceName[LF_FACESIZE+60];
     if( ::GetTextFaceW( getHDC(), sizeof(aFaceName)/sizeof(wchar_t), aFaceName ) )
-        pFontAttributes->SetFamilyName(OUString(reinterpret_cast<const sal_Unicode*>(aFaceName)));
+        pFontMetric->SetFamilyName(OUString(reinterpret_cast<const sal_Unicode*>(aFaceName)));
 
     // get the font metric
     TEXTMETRICA aWinMetric;
@@ -1496,63 +1497,63 @@ void WinSalGraphics::GetFontAttributes( FontAttributes* pFontAttributes, int nFa
         return;
 
     // device independent font attributes
-    pFontAttributes->SetFamilyType(ImplFamilyToSal( aWinMetric.tmPitchAndFamily ));
-    pFontAttributes->SetSymbolFlag(aWinMetric.tmCharSet == SYMBOL_CHARSET);
-    pFontAttributes->SetWeight(ImplWeightToSal( aWinMetric.tmWeight ));
-    pFontAttributes->SetPitch(ImplMetricPitchToSal( aWinMetric.tmPitchAndFamily ));
-    pFontAttributes->SetItalic(aWinMetric.tmItalic ? ITALIC_NORMAL : ITALIC_NONE);
-    pFontAttributes->SetSlant( 0 );
+    pFontMetric->SetFamilyType(ImplFamilyToSal( aWinMetric.tmPitchAndFamily ));
+    pFontMetric->SetSymbolFlag(aWinMetric.tmCharSet == SYMBOL_CHARSET);
+    pFontMetric->SetWeight(ImplWeightToSal( aWinMetric.tmWeight ));
+    pFontMetric->SetPitch(ImplMetricPitchToSal( aWinMetric.tmPitchAndFamily ));
+    pFontMetric->SetItalic(aWinMetric.tmItalic ? ITALIC_NORMAL : ITALIC_NONE);
+    pFontMetric->SetSlant( 0 );
 
     // device dependent font attributes
-    pFontAttributes->SetBuiltInFontFlag( (aWinMetric.tmPitchAndFamily & TMPF_DEVICE) != 0 );
-    pFontAttributes->SetScalableFlag( (aWinMetric.tmPitchAndFamily & (TMPF_VECTOR|TMPF_TRUETYPE)) != 0 );
-    pFontAttributes->SetTrueTypeFlag( (aWinMetric.tmPitchAndFamily & TMPF_TRUETYPE) != 0 );
-    if( pFontAttributes->IsScalable() )
+    pFontMetric->SetBuiltInFontFlag( (aWinMetric.tmPitchAndFamily & TMPF_DEVICE) != 0 );
+    pFontMetric->SetScalableFlag( (aWinMetric.tmPitchAndFamily & (TMPF_VECTOR|TMPF_TRUETYPE)) != 0 );
+    pFontMetric->SetTrueTypeFlag( (aWinMetric.tmPitchAndFamily & TMPF_TRUETYPE) != 0 );
+    if( pFontMetric->IsScalable() )
     {
         // check if there are kern pairs
         // TODO: does this work with GPOS kerning?
         DWORD nKernPairs = ::GetKerningPairsA( getHDC(), 0, NULL );
-        pFontAttributes->SetKernableFlag( (nKernPairs > 0) );
+        pFontMetric->SetKernableFlag( (nKernPairs > 0) );
     }
     else
     {
         // bitmap fonts cannot be rotated directly
-        pFontAttributes->SetOrientation( 0 );
+        pFontMetric->SetOrientation( 0 );
         // bitmap fonts have no kerning
-        pFontAttributes->SetKernableFlag( false );
+        pFontMetric->SetKernableFlag( false );
     }
 
     // transformation dependent font metrics
-    pFontAttributes->SetWidth( static_cast<int>( mfFontScale[nFallbackLevel] * aWinMetric.tmAveCharWidth ) );
-    pFontAttributes->SetInternalLeading( static_cast<int>( mfFontScale[nFallbackLevel] * aWinMetric.tmInternalLeading ) );

... etc. - the rest is truncated


More information about the Libreoffice-commits mailing list