2 /* This file is part of
3 * ======================================================
5 * LyX, The Document Processor
7 * Copyright 1997 Asger Alstrup
10 * ====================================================== */
13 #include <cmath> // fabs()
16 #pragma implementation "FontLoader.h"
20 #include "FontLoader.h"
23 #include "lyxrc.h" // lyxrc.font_*
24 #include "BufferView.h"
30 extern BufferView * current_view;
33 // The global fontloader
34 FontLoader fontloader;
37 // Initialize font loader
38 FontLoader::FontLoader()
43 // Destroy font loader
44 FontLoader::~FontLoader()
49 // Update fonts after zoom, dpi, font names, or norm change
50 // For now, we just ditch all fonts we have. Later, we should
51 // reuse the ones that are already loaded.
52 void FontLoader::update()
58 void FontLoader::reset()
60 // Clear font infos, font structs and font metrics
61 for (int i1 = 0; i1 < 4; ++i1)
62 for (int i2 = 0; i2 < 2; ++i2)
63 for (int i3 = 0; i3 < 4; ++i3) {
64 fontinfo[i1][i2][i3] = 0;
65 for (int i4 = 0; i4<10; ++i4) {
66 fontstruct[i1][i2][i3][i4] = 0;
72 void FontLoader::unload()
75 for (int i1 = 0; i1 < 4; ++i1)
76 for (int i2 = 0; i2 < 2; ++i2)
77 for (int i3 = 0; i3 < 4; ++i3) {
78 if (fontinfo[i1][i2][i3]) {
79 delete fontinfo[i1][i2][i3];
80 fontinfo[i1][i2][i3] = 0;
82 for (int i4 = 0; i4 < 10; ++i4) {
83 if (fontstruct[i1][i2][i3][i4]) {
84 XFreeFont(fl_get_display(), fontstruct[i1][i2][i3][i4]);
85 fontstruct[i1][i2][i3][i4] = 0;
92 /* Takes care of finding which font that can match the given request. Tries
93 different alternatives. */
94 void FontLoader::getFontinfo(LyXFont::FONT_FAMILY family,
95 LyXFont::FONT_SERIES series,
96 LyXFont::FONT_SHAPE shape)
98 // Do we have the font info already?
99 if (fontinfo[family][series][shape] != 0)
102 // Special code for the symbol family
103 if (family == LyXFont::SYMBOL_FAMILY){
104 fontinfo[family][series][shape] = new FontInfo("-*-symbol-*");
108 // Normal font. Let's search for an existing name that matches.
112 string norm = lyxrc.font_norm;
115 FontInfo * fi = new FontInfo();
116 fontinfo[family][series][shape] = fi;
118 for (int cfam = 0; cfam < 2; ++cfam) {
119 // Determine family name
121 case LyXFont::ROMAN_FAMILY:
123 case 0: ffamily = lyxrc.roman_font_name; break;
124 case 1: ffamily = "-*-times";
128 case LyXFont::SANS_FAMILY:
130 case 0: ffamily = lyxrc.sans_font_name; break;
131 case 1: ffamily = "-*-helvetica";
135 case LyXFont::TYPEWRITER_FAMILY:
137 case 0: ffamily = lyxrc.typewriter_font_name; break;
138 case 1: ffamily = "-*-courier";
145 for (int cser = 0; cser < 4; ++cser) {
146 // Determine series name
148 case LyXFont::MEDIUM_SERIES:
150 case 0: fseries = "-medium"; break;
151 case 1: fseries = "-book"; break;
152 case 2: fseries = "-light";
156 case LyXFont::BOLD_SERIES:
158 case 0: fseries = "-bold"; break;
159 case 1: fseries = "-black"; break;
160 case 2: fseries = "-demi"; break;
161 case 3: fseries = "-demibold";
168 for (int csha = 0; csha < 2; ++csha) {
169 // Determine shape name
171 case LyXFont::UP_SHAPE:
172 case LyXFont::SMALLCAPS_SHAPE:
174 case 0: fshape = "-r";
178 case LyXFont::ITALIC_SHAPE:
180 case 0: fshape = "-i"; break;
181 case 1: fshape = "-o";
185 case LyXFont::SLANTED_SHAPE:
187 case 0: fshape = "-o"; break;
188 case 1: fshape = "-i";
195 fontname = ffamily + fseries + fshape +
196 "-normal-*-*-*-*-*-*-*-" + norm;
197 fi->setPattern(fontname);
207 // A dummy fontstruct used when there is no gui.
210 XFontStruct dummyXFontStruct;
211 bool dummyXFontStructisGood = false;
216 XFontStruct * FontLoader::doLoad(LyXFont::FONT_FAMILY family,
217 LyXFont::FONT_SERIES series,
218 LyXFont::FONT_SHAPE shape,
219 LyXFont::FONT_SIZE size)
221 if (!lyxrc.use_gui) {
222 if (!dummyXFontStructisGood) {
223 // no character specific info
224 dummyXFontStruct.per_char = 0;
225 // unit ascent on character displays
226 dummyXFontStruct.ascent = 1;
227 // no descent on character displays
228 dummyXFontStruct.descent = 0;
229 dummyXFontStructisGood = true;
232 return &dummyXFontStruct;
235 getFontinfo(family, series, shape);
236 int fsize = int( (lyxrc.font_sizes[size] * lyxrc.dpi *
237 (lyxrc.zoom/100.0) ) / 72.27 + 0.5 );
239 string font = fontinfo[family][series][shape]->getFontname(fsize);
242 lyxerr << "No font matches request. Using 'fixed'." << endl;
243 lyxerr << "Start LyX as 'lyx -dbg 515' to get more information." << endl;
247 XFontStruct * fs = 0;
249 current_view->owner()->getLyXFunc()
250 ->Dispatch(LFUN_MESSAGE_PUSH,
251 _("Loading font into X-Server..."));
253 fs = XLoadQueryFont(fl_get_display(), font.c_str());
256 if (font == "fixed") {
257 lyxerr << "We're doomed. Can't get 'fixed' font." << endl;
259 lyxerr << "Could not get font. Using 'fixed'." << endl;
260 fs = XLoadQueryFont(fl_get_display(), "fixed");
262 } else if (lyxerr.debugging(Debug::FONT)) {
263 // Tell user the font matching
269 // The rest of the attributes are not interesting
270 f.setEmph(LyXFont::INHERIT);
271 f.setUnderbar(LyXFont::INHERIT);
272 f.setNoun(LyXFont::INHERIT);
273 f.setLatex(LyXFont::INHERIT);
274 f.setColor(LColor::inherit);
275 lyxerr << "Font '" << f.stateText(0)
276 << "' matched by\n" << font << endl;
279 current_view->owner()->getLyXFunc()->Dispatch(LFUN_MESSAGE_POP);
281 fontstruct[family][series][shape][size] = fs;