00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034 #ifndef MWAW_FONT
00035 # define MWAW_FONT
00036
00037 #include <assert.h>
00038 #include <string>
00039 #include <vector>
00040
00041 #include "libmwaw_internal.hxx"
00042
00044 class MWAWFont
00045 {
00046 public:
00048 struct Line {
00050 enum Style { None, Simple, Dot, LargeDot, Dash, Wave };
00052 enum Type { Single, Double, Triple };
00054 Line(Style style=None, Type type=Single, bool wordFlag=false, float w=1.0) :
00055 m_style(style), m_type(type), m_word(wordFlag), m_width(w), m_color(MWAWColor::black()) { }
00057 bool isSet() const
00058 {
00059 return m_style != None && m_width>0;
00060 }
00062 void addTo(librevenge::RVNGPropertyList &propList, std::string const &type) const;
00064 friend std::ostream &operator<<(std::ostream &o, Line const &line);
00066 bool operator==(Line const &oth) const
00067 {
00068 return cmp(oth)==0;
00069 }
00071 bool operator!=(Line const &oth) const
00072 {
00073 return cmp(oth)!=0;
00074 }
00076 int cmp(Line const &oth) const
00077 {
00078 if (m_style != oth.m_style) return int(m_style)-int(oth.m_style);
00079 if (m_type != oth.m_type) return int(m_type)-int(oth.m_type);
00080 if (m_word != oth.m_word) return m_word ? -1 : 1;
00081 if (m_width < oth.m_width) return -1;
00082 if (m_width > oth.m_width) return 1;
00083 if (m_color.isSet() != oth.m_color.isSet())
00084 return m_color.isSet();
00085 if (m_color.get() < oth.m_color.get()) return -1;
00086 if (m_color.get() > oth.m_color.get()) return 1;
00087 return 0;
00088 }
00090 Style m_style;
00092 Type m_type;
00094 bool m_word;
00096 float m_width;
00098 MWAWVariable<MWAWColor> m_color;
00099 };
00101 struct Script {
00103 Script(float delta=0, librevenge::RVNGUnit deltaUnit=librevenge::RVNG_PERCENT, int scale=100) :
00104 m_delta(delta), m_deltaUnit(deltaUnit), m_scale(scale)
00105 {
00106 }
00108 bool isSet() const
00109 {
00110 return *this != Script();
00111 }
00113 static Script sub()
00114 {
00115 return Script(-33,librevenge::RVNG_PERCENT,58);
00116 }
00118 static Script sub100()
00119 {
00120 return Script(-20);
00121 }
00123 static Script super()
00124 {
00125 return Script(33,librevenge::RVNG_PERCENT,58);
00126 }
00128 static Script super100()
00129 {
00130 return Script(20);
00131 }
00133 std::string str(float fSize) const;
00134
00136 bool operator==(Script const &oth) const
00137 {
00138 return cmp(oth)==0;
00139 }
00141 bool operator!=(Script const &oth) const
00142 {
00143 return cmp(oth)!=0;
00144 }
00146 bool operator<(Script const &oth) const
00147 {
00148 return cmp(oth)<0;
00149 }
00151 bool operator<=(Script const &oth) const
00152 {
00153 return cmp(oth)<=0;
00154 }
00156 bool operator>(Script const &oth) const
00157 {
00158 return cmp(oth)>0;
00159 }
00161 bool operator>=(Script const &oth) const
00162 {
00163 return cmp(oth)>=0;
00164 }
00166 int cmp(Script const &oth) const
00167 {
00168 if (m_delta > oth.m_delta) return -1;
00169 if (m_delta < oth.m_delta) return 1;
00170 if (m_deltaUnit != oth.m_deltaUnit) return int(m_deltaUnit)-int(oth.m_deltaUnit);
00171 if (m_scale != oth.m_scale) return m_scale-oth.m_scale;
00172 return 0;
00173 }
00175 float m_delta;
00177 librevenge::RVNGUnit m_deltaUnit;
00179 int m_scale;
00180 };
00181
00183 enum FontBits { boldBit=1, italicBit=2, blinkBit=4, embossBit=8, engraveBit=0x10,
00184 hiddenBit=0x20, outlineBit=0x40, shadowBit=0x80,
00185 reverseVideoBit=0x100, smallCapsBit=0x200, allCapsBit=0x400,
00186 lowercaseBit=0x800, boxedBit=0x1000, boxedRoundedBit=0x2000,
00187 reverseWritingBit=0x4000
00188 };
00194 MWAWFont(int newId=-1, float sz=12, uint32_t f = 0) : m_id(newId), m_size(sz), m_deltaSpacing(0), m_texteWidthScaling(1.0), m_scriptPosition(),
00195 m_flags(f), m_overline(Line::None), m_strikeoutline(Line::None), m_underline(Line::None),
00196 m_color(MWAWColor::black()), m_backgroundColor(MWAWColor::white()), m_language(""), m_extra("")
00197 {
00198 resetColor();
00199 };
00201 bool isSet() const
00202 {
00203 return m_id.isSet();
00204 }
00206 void insert(MWAWFont const &ft)
00207 {
00208 m_id.insert(ft.m_id);
00209 m_size.insert(ft.m_size);
00210 m_deltaSpacing.insert(ft.m_deltaSpacing);
00211 m_texteWidthScaling.insert(ft.m_texteWidthScaling);
00212 m_scriptPosition.insert(ft.m_scriptPosition);
00213 if (ft.m_flags.isSet()) {
00214 if (m_flags.isSet())
00215 setFlags(flags()| ft.flags());
00216 else
00217 m_flags = ft.m_flags;
00218 }
00219 m_overline.insert(ft.m_overline);
00220 m_strikeoutline.insert(ft.m_strikeoutline);
00221 m_underline.insert(ft.m_underline);
00222 m_color.insert(ft.m_color);
00223 m_extra += ft.m_extra;
00224 }
00226 void setFont(int newId)
00227 {
00228 resetColor();
00229 m_id=newId;
00230 }
00231
00233 int id() const
00234 {
00235 return m_id.get();
00236 }
00238 void setId(int newId)
00239 {
00240 m_id = newId;
00241 }
00242
00244 float size() const
00245 {
00246 return m_size.get();
00247 }
00249 void setSize(float sz)
00250 {
00251 m_size = sz;
00252 }
00253
00255 float deltaLetterSpacing() const
00256 {
00257 return m_deltaSpacing.get();
00258 }
00260 void setDeltaLetterSpacing(float d)
00261 {
00262 m_deltaSpacing=d;
00263 }
00265 float texteWidthScaling() const
00266 {
00267 return m_texteWidthScaling.get();
00268 }
00270 void setTexteWidthScaling(float scale=1.0)
00271 {
00272 m_texteWidthScaling = scale;
00273 }
00275 Script const &script() const
00276 {
00277 return m_scriptPosition.get();
00278 }
00279
00281 void set(Script const &newscript)
00282 {
00283 m_scriptPosition = newscript;
00284 }
00285
00287 uint32_t flags() const
00288 {
00289 return m_flags.get();
00290 }
00292 void setFlags(uint32_t fl)
00293 {
00294 m_flags = fl;
00295 }
00296
00298 bool hasColor() const
00299 {
00300 return m_color.isSet() && !m_color.get().isBlack();
00301 }
00303 void getColor(MWAWColor &c) const
00304 {
00305 c = m_color.get();
00306 }
00308 void setColor(MWAWColor color)
00309 {
00310 m_color = color;
00311 }
00312
00314 void getBackgroundColor(MWAWColor &c) const
00315 {
00316 c = m_backgroundColor.get();
00317 }
00319 void setBackgroundColor(MWAWColor color)
00320 {
00321 m_backgroundColor = color;
00322 }
00324 void resetColor()
00325 {
00326 m_color = MWAWColor::black();
00327 m_backgroundColor = MWAWColor::white();
00328 }
00329
00331 bool hasDecorationLines() const
00332 {
00333 return (m_overline.isSet() && m_overline->isSet()) ||
00334 (m_strikeoutline.isSet() && m_strikeoutline->isSet()) ||
00335 (m_underline.isSet() && m_underline->isSet());
00336 }
00338 void resetDecorationLines()
00339 {
00340 if (m_overline.isSet()) m_overline=Line(Line::None);
00341 if (m_strikeoutline.isSet()) m_strikeoutline=Line(Line::None);
00342 if (m_underline.isSet()) m_underline=Line(Line::None);
00343 }
00345 Line const &getOverline() const
00346 {
00347 return m_overline.get();
00348 }
00350 void setOverline(Line const &line)
00351 {
00352 m_overline = line;
00353 }
00355 void setOverlineStyle(Line::Style style=Line::None, bool doReset=true)
00356 {
00357 if (doReset)
00358 m_overline = Line(style);
00359 else
00360 m_overline->m_style = style;
00361 }
00363 void setOverlineType(Line::Type type=Line::Single)
00364 {
00365 m_overline->m_type = type;
00366 }
00368 void setOverlineWordFlag(bool wordFlag=false)
00369 {
00370 m_overline->m_word = wordFlag;
00371 }
00373 void setOverlineWidth(float w)
00374 {
00375 m_overline->m_width = w;
00376 }
00378 void setOverlineColor(MWAWColor const &color)
00379 {
00380 m_overline->m_color = color;
00381 }
00382
00384 Line const &getStrikeOut() const
00385 {
00386 return m_strikeoutline.get();
00387 }
00389 void setStrikeOut(Line const &line)
00390 {
00391 m_strikeoutline = line;
00392 }
00394 void setStrikeOutStyle(Line::Style style=Line::None, bool doReset=true)
00395 {
00396 if (doReset)
00397 m_strikeoutline = Line(style);
00398 else
00399 m_strikeoutline->m_style = style;
00400 }
00402 void setStrikeOutType(Line::Type type=Line::Single)
00403 {
00404 m_strikeoutline->m_type = type;
00405 }
00407 void setStrikeOutWordFlag(bool wordFlag=false)
00408 {
00409 m_strikeoutline->m_word = wordFlag;
00410 }
00412 void setStrikeOutWidth(float w)
00413 {
00414 m_strikeoutline->m_width = w;
00415 }
00417 void setStrikeOutColor(MWAWColor const &color)
00418 {
00419 m_strikeoutline->m_color = color;
00420 }
00421
00423 Line const &getUnderline() const
00424 {
00425 return m_underline.get();
00426 }
00428 void setUnderline(Line const &line)
00429 {
00430 m_underline = line;
00431 }
00433 void setUnderlineStyle(Line::Style style=Line::None, bool doReset=true)
00434 {
00435 if (doReset)
00436 m_underline = Line(style);
00437 else
00438 m_underline->m_style = style;
00439 }
00441 void setUnderlineType(Line::Type type=Line::Single)
00442 {
00443 m_underline->m_type = type;
00444 }
00446 void setUnderlineWordFlag(bool wordFlag=false)
00447 {
00448 m_underline->m_word = wordFlag;
00449 }
00451 void setUnderlineWidth(float w)
00452 {
00453 m_underline->m_width = w;
00454 }
00456 void setUnderlineColor(MWAWColor const &color)
00457 {
00458 m_underline->m_color = color;
00459 }
00460
00462 std::string const &language() const
00463 {
00464 return m_language.get();
00465 }
00467 void setLanguage(std::string const &lang)
00468 {
00469 m_language=lang;
00470 }
00472 void addTo(librevenge::RVNGPropertyList &propList, shared_ptr<MWAWFontConverter> fontConverter) const;
00473
00475 std::string getDebugString(shared_ptr<MWAWFontConverter> &converter) const;
00476
00478 bool operator==(MWAWFont const &f) const
00479 {
00480 return cmp(f) == 0;
00481 }
00483 bool operator!=(MWAWFont const &f) const
00484 {
00485 return cmp(f) != 0;
00486 }
00487
00489 int cmp(MWAWFont const &oth) const
00490 {
00491 int diff = id() - oth.id();
00492 if (diff != 0) return diff;
00493 if (size() < oth.size()) return -1;
00494 if (size() > oth.size()) return -1;
00495 if (flags() < oth.flags()) return -1;
00496 if (flags() > oth.flags()) return 1;
00497 if (m_deltaSpacing.get() < oth.m_deltaSpacing.get()) return -1;
00498 if (m_deltaSpacing.get() > oth.m_deltaSpacing.get()) return 1;
00499 if (m_texteWidthScaling.get() < oth.m_texteWidthScaling.get()) return -1;
00500 if (m_texteWidthScaling.get() > oth.m_texteWidthScaling.get()) return 1;
00501 diff = script().cmp(oth.script());
00502 if (diff != 0) return diff;
00503 diff = m_overline.get().cmp(oth.m_overline.get());
00504 if (diff != 0) return diff;
00505 diff = m_strikeoutline.get().cmp(oth.m_strikeoutline.get());
00506 if (diff != 0) return diff;
00507 diff = m_underline.get().cmp(oth.m_underline.get());
00508 if (diff != 0) return diff;
00509 if (m_color.get() < oth.m_color.get()) return -1;
00510 if (m_color.get() > oth.m_color.get()) return 1;
00511 if (m_backgroundColor.get() < oth.m_backgroundColor.get()) return -1;
00512 if (m_backgroundColor.get() > oth.m_backgroundColor.get()) return 1;
00513 if (m_language.get() < oth.m_language.get()) return -1;
00514 if (m_language.get() > oth.m_language.get()) return 1;
00515 return diff;
00516 }
00517
00518 protected:
00519 MWAWVariable<int> m_id ;
00520 MWAWVariable<float> m_size ;
00521 MWAWVariable<float> m_deltaSpacing ;
00522 MWAWVariable<float> m_texteWidthScaling ;
00523 MWAWVariable<Script> m_scriptPosition ;
00524 MWAWVariable<uint32_t> m_flags ;
00525 MWAWVariable<Line> m_overline ;
00526 MWAWVariable<Line> m_strikeoutline ;
00527 MWAWVariable<Line> m_underline ;
00528 MWAWVariable<MWAWColor> m_color ;
00529 MWAWVariable<MWAWColor> m_backgroundColor ;
00530 MWAWVariable<std::string> m_language ;
00531 public:
00533 std::string m_extra;
00534 };
00535
00536
00537 #endif
00538