LibreOffice Module vcl (master)  1
impglyphitem.hxx
Go to the documentation of this file.
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
5  * This Source Code Form is subject to the terms of the Mozilla Public
6  * License, v. 2.0. If a copy of the MPL was not distributed with this
7  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
11  * Licensed to the Apache Software Foundation (ASF) under one or more
12  * contributor license agreements. See the NOTICE file distributed
13  * with this work for additional information regarding copyright
14  * ownership. The ASF licenses this file to you under the Apache
15  * License, Version 2.0 (the "License"); you may not use this file
16  * except in compliance with the License. You may obtain a copy of
17  * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18  */
19 
20 #ifndef INCLUDED_VCL_IMPGLYPHITEM_HXX
21 #define INCLUDED_VCL_IMPGLYPHITEM_HXX
22 
23 #include <o3tl/typed_flags_set.hxx>
24 #include <tools/gen.hxx>
25 #include <vcl/dllapi.h>
26 #include <vcl/outdev.hxx>
27 #include <vector>
28 
29 #include "fontinstance.hxx"
30 #include "glyphid.hxx"
31 
32 enum class GlyphItemFlags : sal_uInt16
33 {
34  NONE = 0,
35  IS_IN_CLUSTER = 0x01,
36  IS_RTL_GLYPH = 0x02,
37  IS_DIACRITIC = 0x04,
38  IS_VERTICAL = 0x08,
39  IS_SPACING = 0x10,
40  ALLOW_KASHIDA = 0x20,
41  IS_DROPPED = 0x40,
42  IS_CLUSTER_START = 0x80,
43  IS_UNSAFE_TO_BREAK = 0x100 // HB_GLYPH_FLAG_UNSAFE_TO_BREAK from harfbuzz
44 };
45 namespace o3tl
46 {
47 template <> struct typed_flags<GlyphItemFlags> : is_typed_flags<GlyphItemFlags, 0x1ff>
48 {
49 };
50 };
51 
53 {
54  DevicePoint m_aLinearPos; // absolute position of non rotated string
55  DeviceCoordinate m_nOrigWidth; // original glyph width
56  sal_Int32 m_nCharPos; // index in string
57  sal_Int32 m_nXOffset;
58  sal_Int32 m_nYOffset;
59  DeviceCoordinate m_nNewWidth; // width after adjustments
62  sal_Int8 m_nCharCount; // number of characters making up this glyph
63 
64 public:
65  GlyphItem(int nCharPos, int nCharCount, sal_GlyphId aGlyphId, const DevicePoint& rLinearPos,
66  GlyphItemFlags nFlags, DeviceCoordinate nOrigWidth, int nXOffset, int nYOffset)
67  : m_aLinearPos(rLinearPos)
68  , m_nOrigWidth(nOrigWidth)
69  , m_nCharPos(nCharPos)
70  , m_nXOffset(nXOffset)
71  , m_nYOffset(nYOffset)
72  , m_nNewWidth(nOrigWidth)
73  , m_aGlyphId(aGlyphId)
74  , m_nFlags(nFlags)
75  , m_nCharCount(nCharCount)
76  {
77  }
78 
79  bool IsInCluster() const { return bool(m_nFlags & GlyphItemFlags::IS_IN_CLUSTER); }
80  bool IsRTLGlyph() const { return bool(m_nFlags & GlyphItemFlags::IS_RTL_GLYPH); }
81  bool IsDiacritic() const { return bool(m_nFlags & GlyphItemFlags::IS_DIACRITIC); }
82  bool IsVertical() const { return bool(m_nFlags & GlyphItemFlags::IS_VERTICAL); }
83  bool IsSpacing() const { return bool(m_nFlags & GlyphItemFlags::IS_SPACING); }
84  bool AllowKashida() const { return bool(m_nFlags & GlyphItemFlags::ALLOW_KASHIDA); }
85  bool IsDropped() const { return bool(m_nFlags & GlyphItemFlags::IS_DROPPED); }
86  bool IsClusterStart() const { return bool(m_nFlags & GlyphItemFlags::IS_CLUSTER_START); }
87  bool IsUnsafeToBreak() const { return bool(m_nFlags & GlyphItemFlags::IS_UNSAFE_TO_BREAK); }
88 
89  inline bool GetGlyphBoundRect(const LogicalFontInstance*, tools::Rectangle&) const;
90  inline bool GetGlyphOutline(const LogicalFontInstance*, basegfx::B2DPolyPolygon&) const;
91  inline void dropGlyph();
92 
93  sal_GlyphId glyphId() const { return m_aGlyphId; }
94  int charCount() const { return m_nCharCount; }
95  DeviceCoordinate origWidth() const { return m_nOrigWidth; }
96  int charPos() const { return m_nCharPos; }
97  int xOffset() const { return m_nXOffset; }
98  int yOffset() const { return m_nYOffset; }
99  DeviceCoordinate newWidth() const { return m_nNewWidth; }
100  const DevicePoint& linearPos() const { return m_aLinearPos; }
101 
102  void setNewWidth(DeviceCoordinate width) { m_nNewWidth = width; }
103  void addNewWidth(DeviceCoordinate width) { m_nNewWidth += width; }
104  void setLinearPos(const DevicePoint& point) { m_aLinearPos = point; }
105  void setLinearPosX(double x) { m_aLinearPos.setX(x); }
106  void adjustLinearPosX(double diff) { m_aLinearPos.adjustX(diff); }
107 #ifdef DBG_UTIL
108  bool operator==(const GlyphItem& other) const
109  {
110  return m_aLinearPos == other.m_aLinearPos && m_nOrigWidth == other.m_nOrigWidth
111  && m_nCharPos == other.m_nCharPos && m_nXOffset == other.m_nXOffset
112  && m_nYOffset == other.m_nYOffset && m_nNewWidth == other.m_nNewWidth
113  && m_aGlyphId == other.m_aGlyphId && m_nCharCount == other.m_nCharCount
114  && m_nFlags == other.m_nFlags;
115  }
116  bool operator!=(const GlyphItem& other) const { return !(*this == other); }
117 #endif
118 };
119 
121  tools::Rectangle& rRect) const
122 {
123  return pFontInstance->GetGlyphBoundRect(m_aGlyphId, rRect, IsVertical());
124 }
125 
127  basegfx::B2DPolyPolygon& rPoly) const
128 {
129  return pFontInstance->GetGlyphOutline(m_aGlyphId, rPoly, IsVertical());
130 }
131 
133 {
134  m_nCharPos = -1;
136 }
137 
138 class SalLayoutGlyphsImpl : public std::vector<GlyphItem>
139 {
140 public:
142  : m_rFontInstance(&rFontInstance)
143  {
144  }
145  SalLayoutGlyphsImpl* clone() const;
146  SalLayoutGlyphsImpl* cloneCharRange(sal_Int32 index, sal_Int32 length) const;
148  bool IsValid() const;
149  void SetFlags(SalLayoutFlags flags) { mnFlags = flags; }
150  SalLayoutFlags GetFlags() const { return mnFlags; }
151 #ifdef DBG_UTIL
152  bool isEqual(const SalLayoutGlyphsImpl* other) const;
153 #endif
154 
155 private:
156  bool isSafeToBreak(const_iterator pos, bool rtl) const;
159 };
160 
161 #endif // INCLUDED_VCL_IMPGLYPHITEM_HXX
162 
163 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
bool GetGlyphBoundRect(sal_GlyphId, tools::Rectangle &, bool) const
bool AllowKashida() const
bool IsDiacritic() const
signed char sal_Int8
SalLayoutGlyphsImpl * cloneCharRange(sal_Int32 index, sal_Int32 length) const
bool operator!=(const GlyphItem &other) const
#define VCL_DLLPUBLIC
Definition: dllapi.h:29
void setLinearPosX(double x)
bool isEqual(const SalLayoutGlyphsImpl *other) const
void SetFlags(SalLayoutFlags flags)
bool IsSpacing() const
sal_Int32 DeviceCoordinate
bool IsValid() const
void adjustLinearPosX(double diff)
bool IsUnsafeToBreak() const
void setX(double fX)
sal_uInt16 sal_GlyphId
Definition: glyphid.hxx:24
SalLayoutFlags mnFlags
void dropGlyph()
sal_GlyphId glyphId() const
GlyphItemFlags
DeviceCoordinate m_nOrigWidth
const DevicePoint & linearPos() const
bool isSafeToBreak(const_iterator pos, bool rtl) const
bool GetGlyphOutline(const LogicalFontInstance *, basegfx::B2DPolyPolygon &) const
DeviceCoordinate m_nNewWidth
GlyphItemFlags m_nFlags
void setNewWidth(DeviceCoordinate width)
SalLayoutFlags GetFlags() const
bool IsVertical() const
sal_Int8 m_nCharCount
bool IsInCluster() const
bool IsDropped() const
SalLayoutGlyphsImpl(LogicalFontInstance &rFontInstance)
bool IsRTLGlyph() const
sal_Int32 m_nCharPos
DevicePoint m_aLinearPos
rtl::Reference< LogicalFontInstance > m_rFontInstance
const rtl::Reference< LogicalFontInstance > & GetFont() const
int charCount() const
GlyphItem(int nCharPos, int nCharCount, sal_GlyphId aGlyphId, const DevicePoint &rLinearPos, GlyphItemFlags nFlags, DeviceCoordinate nOrigWidth, int nXOffset, int nYOffset)
int charPos() const
sal_Int32 m_nYOffset
DeviceCoordinate newWidth() const
void addNewWidth(DeviceCoordinate width)
bool IsClusterStart() const
sal_GlyphId m_aGlyphId
int yOffset() const
virtual bool GetGlyphOutline(sal_GlyphId, basegfx::B2DPolyPolygon &, bool) const =0
bool GetGlyphBoundRect(const LogicalFontInstance *, tools::Rectangle &) const
void setLinearPos(const DevicePoint &point)
int xOffset() const
DeviceCoordinate origWidth() const
sal_Int32 m_nXOffset
SalLayoutGlyphsImpl * clone() const
bool operator==(const GlyphItem &other) const
void adjustX(double fX)
SalLayoutFlags