1 /* 2 * 3 * (C) Copyright IBM Corp. 1998-2007 - All Rights Reserved 4 * 5 */ 6 7 #ifndef __GLYPHPOSITIONADJUSTMENTS_H 8 #define __GLYPHPOSITIONADJUSTMENTS_H 9 10 /** 11 * \file 12 * \internal 13 */ 14 15 #include "LETypes.h" 16 #include "OpenTypeTables.h" 17 18 U_NAMESPACE_BEGIN 19 20 class LEGlyphStorage; 21 class LEFontInstance; 22 23 class GlyphPositionAdjustments : public UMemory 24 { 25 private: 26 class Adjustment : public UMemory { 27 public: 28 29 inline Adjustment(); 30 inline Adjustment(float xPlace, float yPlace, float xAdv, float yAdv, le_int32 baseOff = -1); 31 inline ~Adjustment(); 32 33 inline float getXPlacement() const; 34 inline float getYPlacement() const; 35 inline float getXAdvance() const; 36 inline float getYAdvance() const; 37 38 inline le_int32 getBaseOffset() const; 39 40 inline void setXPlacement(float newXPlacement); 41 inline void setYPlacement(float newYPlacement); 42 inline void setXAdvance(float newXAdvance); 43 inline void setYAdvance(float newYAdvance); 44 45 inline void setBaseOffset(le_int32 newBaseOffset); 46 47 inline void adjustXPlacement(float xAdjustment); 48 inline void adjustYPlacement(float yAdjustment); 49 inline void adjustXAdvance(float xAdjustment); 50 inline void adjustYAdvance(float yAdjustment); 51 52 private: 53 float xPlacement; 54 float yPlacement; 55 float xAdvance; 56 float yAdvance; 57 58 le_int32 baseOffset; 59 60 // allow copying of this class because all of its fields are simple types 61 }; 62 63 class EntryExitPoint : public UMemory 64 { 65 public: 66 inline EntryExitPoint(); 67 inline ~EntryExitPoint(); 68 69 inline le_bool isCursiveGlyph() const; 70 inline le_bool baselineIsLogicalEnd() const; 71 72 LEPoint *getEntryPoint(LEPoint &entryPoint) const; 73 LEPoint *getExitPoint(LEPoint &exitPoint) const; 74 75 inline void clearEntryPoint(); 76 inline void clearExitPoint(); 77 inline void setEntryPoint(LEPoint &newEntryPoint, le_bool baselineIsLogicalEnd); 78 inline void setExitPoint(LEPoint &newExitPoint, le_bool baselineIsLogicalEnd); 79 inline void setCursiveGlyph(le_bool baselineIsLogicalEnd); 80 81 private: 82 enum EntryExitFlags 83 { 84 EEF_HAS_ENTRY_POINT = 0x80000000L, 85 EEF_HAS_EXIT_POINT = 0x40000000L, 86 EEF_IS_CURSIVE_GLYPH = 0x20000000L, 87 EEF_BASELINE_IS_LOGICAL_END = 0x10000000L 88 }; 89 90 le_uint32 fFlags; 91 LEPoint fEntryPoint; 92 LEPoint fExitPoint; 93 }; 94 95 le_int32 fGlyphCount; 96 EntryExitPoint *fEntryExitPoints; 97 Adjustment *fAdjustments; 98 99 GlyphPositionAdjustments(); 100 101 public: 102 GlyphPositionAdjustments(le_int32 glyphCount); 103 ~GlyphPositionAdjustments(); 104 105 inline le_bool hasCursiveGlyphs() const; 106 inline le_bool isCursiveGlyph(le_int32 index) const; 107 inline le_bool baselineIsLogicalEnd(le_int32 index) const; 108 109 const LEPoint *getEntryPoint(le_int32 index, LEPoint &entryPoint) const; 110 const LEPoint *getExitPoint(le_int32 index, LEPoint &exitPoint) const; 111 112 inline float getXPlacement(le_int32 index) const; 113 inline float getYPlacement(le_int32 index) const; 114 inline float getXAdvance(le_int32 index) const; 115 inline float getYAdvance(le_int32 index) const; 116 117 inline le_int32 getBaseOffset(le_int32 index) const; 118 119 inline void setXPlacement(le_int32 index, float newXPlacement); 120 inline void setYPlacement(le_int32 index, float newYPlacement); 121 inline void setXAdvance(le_int32 index, float newXAdvance); 122 inline void setYAdvance(le_int32 index, float newYAdvance); 123 124 inline void setBaseOffset(le_int32 index, le_int32 newBaseOffset); 125 126 inline void adjustXPlacement(le_int32 index, float xAdjustment); 127 inline void adjustYPlacement(le_int32 index, float yAdjustment); 128 inline void adjustXAdvance(le_int32 index, float xAdjustment); 129 inline void adjustYAdvance(le_int32 index, float yAdjustment); 130 131 void clearEntryPoint(le_int32 index); 132 void clearExitPoint(le_int32 index); 133 void setEntryPoint(le_int32 index, LEPoint &newEntryPoint, le_bool baselineIsLogicalEnd); 134 void setExitPoint(le_int32 index, LEPoint &newExitPoint, le_bool baselineIsLogicalEnd); 135 void setCursiveGlyph(le_int32 index, le_bool baselineIsLogicalEnd); 136 137 void applyCursiveAdjustments(LEGlyphStorage &glyphStorage, le_bool rightToLeft, const LEFontInstance *fontInstance); 138 }; 139 140 inline GlyphPositionAdjustments::Adjustment::Adjustment() 141 : xPlacement(0), yPlacement(0), xAdvance(0), yAdvance(0), baseOffset(-1) 142 { 143 // nothing else to do! 144 } 145 146 inline GlyphPositionAdjustments::Adjustment::Adjustment(float xPlace, float yPlace, float xAdv, float yAdv, le_int32 baseOff) 147 : xPlacement(xPlace), yPlacement(yPlace), xAdvance(xAdv), yAdvance(yAdv), baseOffset(baseOff) 148 { 149 // nothing else to do! 150 } 151 152 inline GlyphPositionAdjustments::Adjustment::~Adjustment() 153 { 154 // nothing to do! 155 } 156 157 inline float GlyphPositionAdjustments::Adjustment::getXPlacement() const 158 { 159 return xPlacement; 160 } 161 162 inline float GlyphPositionAdjustments::Adjustment::getYPlacement() const 163 { 164 return yPlacement; 165 } 166 167 inline float GlyphPositionAdjustments::Adjustment::getXAdvance() const 168 { 169 return xAdvance; 170 } 171 172 inline float GlyphPositionAdjustments::Adjustment::getYAdvance() const 173 { 174 return yAdvance; 175 } 176 177 inline le_int32 GlyphPositionAdjustments::Adjustment::getBaseOffset() const 178 { 179 return baseOffset; 180 } 181 182 inline void GlyphPositionAdjustments::Adjustment::setXPlacement(float newXPlacement) 183 { 184 xPlacement = newXPlacement; 185 } 186 187 inline void GlyphPositionAdjustments::Adjustment::setYPlacement(float newYPlacement) 188 { 189 yPlacement = newYPlacement; 190 } 191 192 inline void GlyphPositionAdjustments::Adjustment::setXAdvance(float newXAdvance) 193 { 194 xAdvance = newXAdvance; 195 } 196 197 inline void GlyphPositionAdjustments::Adjustment::setYAdvance(float newYAdvance) 198 { 199 yAdvance = newYAdvance; 200 } 201 202 inline void GlyphPositionAdjustments::Adjustment::setBaseOffset(le_int32 newBaseOffset) 203 { 204 baseOffset = newBaseOffset; 205 } 206 207 inline void GlyphPositionAdjustments::Adjustment::adjustXPlacement(float xAdjustment) 208 { 209 xPlacement += xAdjustment; 210 } 211 212 inline void GlyphPositionAdjustments::Adjustment::adjustYPlacement(float yAdjustment) 213 { 214 yPlacement += yAdjustment; 215 } 216 217 inline void GlyphPositionAdjustments::Adjustment::adjustXAdvance(float xAdjustment) 218 { 219 xAdvance += xAdjustment; 220 } 221 222 inline void GlyphPositionAdjustments::Adjustment::adjustYAdvance(float yAdjustment) 223 { 224 yAdvance += yAdjustment; 225 } 226 227 inline GlyphPositionAdjustments::EntryExitPoint::EntryExitPoint() 228 : fFlags(0) 229 { 230 fEntryPoint.fX = fEntryPoint.fY = fExitPoint.fX = fExitPoint.fY = 0; 231 } 232 233 inline GlyphPositionAdjustments::EntryExitPoint::~EntryExitPoint() 234 { 235 // nothing special to do 236 } 237 238 inline le_bool GlyphPositionAdjustments::EntryExitPoint::isCursiveGlyph() const 239 { 240 return (fFlags & EEF_IS_CURSIVE_GLYPH) != 0; 241 } 242 243 inline le_bool GlyphPositionAdjustments::EntryExitPoint::baselineIsLogicalEnd() const 244 { 245 return (fFlags & EEF_BASELINE_IS_LOGICAL_END) != 0; 246 } 247 248 inline void GlyphPositionAdjustments::EntryExitPoint::clearEntryPoint() 249 { 250 fFlags &= ~EEF_HAS_ENTRY_POINT; 251 } 252 253 inline void GlyphPositionAdjustments::EntryExitPoint::clearExitPoint() 254 { 255 fFlags &= ~EEF_HAS_EXIT_POINT; 256 } 257 258 inline void GlyphPositionAdjustments::EntryExitPoint::setEntryPoint(LEPoint &newEntryPoint, le_bool baselineIsLogicalEnd) 259 { 260 if (baselineIsLogicalEnd) { 261 fFlags |= (EEF_HAS_ENTRY_POINT | EEF_IS_CURSIVE_GLYPH | EEF_BASELINE_IS_LOGICAL_END); 262 } else { 263 fFlags |= (EEF_HAS_ENTRY_POINT | EEF_IS_CURSIVE_GLYPH); 264 } 265 266 fEntryPoint = newEntryPoint; 267 } 268 269 inline void GlyphPositionAdjustments::EntryExitPoint::setExitPoint(LEPoint &newExitPoint, le_bool baselineIsLogicalEnd) 270 { 271 if (baselineIsLogicalEnd) { 272 fFlags |= (EEF_HAS_EXIT_POINT | EEF_IS_CURSIVE_GLYPH | EEF_BASELINE_IS_LOGICAL_END); 273 } else { 274 fFlags |= (EEF_HAS_EXIT_POINT | EEF_IS_CURSIVE_GLYPH); 275 } 276 277 fExitPoint = newExitPoint; 278 } 279 280 inline void GlyphPositionAdjustments::EntryExitPoint::setCursiveGlyph(le_bool baselineIsLogicalEnd) 281 { 282 if (baselineIsLogicalEnd) { 283 fFlags |= (EEF_IS_CURSIVE_GLYPH | EEF_BASELINE_IS_LOGICAL_END); 284 } else { 285 fFlags |= EEF_IS_CURSIVE_GLYPH; 286 } 287 } 288 289 inline le_bool GlyphPositionAdjustments::isCursiveGlyph(le_int32 index) const 290 { 291 return fEntryExitPoints != NULL && fEntryExitPoints[index].isCursiveGlyph(); 292 } 293 294 inline le_bool GlyphPositionAdjustments::baselineIsLogicalEnd(le_int32 index) const 295 { 296 return fEntryExitPoints != NULL && fEntryExitPoints[index].baselineIsLogicalEnd(); 297 } 298 299 inline float GlyphPositionAdjustments::getXPlacement(le_int32 index) const 300 { 301 return fAdjustments[index].getXPlacement(); 302 } 303 304 inline float GlyphPositionAdjustments::getYPlacement(le_int32 index) const 305 { 306 return fAdjustments[index].getYPlacement(); 307 } 308 309 inline float GlyphPositionAdjustments::getXAdvance(le_int32 index) const 310 { 311 return fAdjustments[index].getXAdvance(); 312 } 313 314 inline float GlyphPositionAdjustments::getYAdvance(le_int32 index) const 315 { 316 return fAdjustments[index].getYAdvance(); 317 } 318 319 320 inline le_int32 GlyphPositionAdjustments::getBaseOffset(le_int32 index) const 321 { 322 return fAdjustments[index].getBaseOffset(); 323 } 324 325 inline void GlyphPositionAdjustments::setXPlacement(le_int32 index, float newXPlacement) 326 { 327 fAdjustments[index].setXPlacement(newXPlacement); 328 } 329 330 inline void GlyphPositionAdjustments::setYPlacement(le_int32 index, float newYPlacement) 331 { 332 fAdjustments[index].setYPlacement(newYPlacement); 333 } 334 335 inline void GlyphPositionAdjustments::setXAdvance(le_int32 index, float newXAdvance) 336 { 337 fAdjustments[index].setXAdvance(newXAdvance); 338 } 339 340 inline void GlyphPositionAdjustments::setYAdvance(le_int32 index, float newYAdvance) 341 { 342 fAdjustments[index].setYAdvance(newYAdvance); 343 } 344 345 inline void GlyphPositionAdjustments::setBaseOffset(le_int32 index, le_int32 newBaseOffset) 346 { 347 fAdjustments[index].setBaseOffset(newBaseOffset); 348 } 349 350 inline void GlyphPositionAdjustments::adjustXPlacement(le_int32 index, float xAdjustment) 351 { 352 fAdjustments[index].adjustXPlacement(xAdjustment); 353 } 354 355 inline void GlyphPositionAdjustments::adjustYPlacement(le_int32 index, float yAdjustment) 356 { 357 fAdjustments[index].adjustYPlacement(yAdjustment); 358 } 359 360 inline void GlyphPositionAdjustments::adjustXAdvance(le_int32 index, float xAdjustment) 361 { 362 fAdjustments[index].adjustXAdvance(xAdjustment); 363 } 364 365 inline void GlyphPositionAdjustments::adjustYAdvance(le_int32 index, float yAdjustment) 366 { 367 fAdjustments[index].adjustYAdvance(yAdjustment); 368 } 369 370 inline le_bool GlyphPositionAdjustments::hasCursiveGlyphs() const 371 { 372 return fEntryExitPoints != NULL; 373 } 374 375 U_NAMESPACE_END 376 #endif 377