2 * Copyright (C) 2000, Matias Atria
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
28 static int tfm_load_font __PROTO((DviParams *, DviFont *));
29 static int tfm_font_get_glyph __PROTO((DviParams *, DviFont *, int));
31 DviFontInfo tfm_font_info = {
33 0, /* scaling not supported by format */
45 DviFontInfo ofm_font_info = {
47 0, /* scaling not supported by format */
59 DviFontInfo afm_font_info = {
61 0, /* scaling not supported by format */
73 #define TYPENAME(font) \
74 ((font)->search.info ? (font)->search.info : "none")
77 * Although it does not seem that way, this conversion is independent of the
78 * shrinking factors, within roundoff (that's because `conv' and `vconv'
79 * have already been scaled by hshrink and vshrink, repsectively). We
80 * should really use `dviconv' and `dvivconv', but I'm not so sure those
81 * should be moved to the DviParams structure.
83 #define XCONV(x) FROUND(params->conv * (x) * params->hshrink)
84 #define YCONV(y) FROUND(params->vconv * (y) * params->vshrink)
86 /* this is used quite often in several places, so I made it standalone */
87 int get_tfm_chars(DviParams *params, DviFont *font, TFMInfo *info, int loaded)
94 n = info->hic - info->loc + 1;
95 if(n != FONT_GLYPH_COUNT(font)) {
96 font->chars = mdvi_realloc(font->chars,
97 n * sizeof(DviFontChar));
99 font->loc = info->loc;
100 font->hic = info->hic;
104 /* Prepare z, alpha and beta for TFM width computation */
105 TFMPREPARE(font->scale, z, alpha, beta);
107 /* get the character metrics */
108 for(n = info->loc; n <= info->hic; ch++, ptr++, n++) {
111 ch->offset = ptr->present;
114 /* this is what we came here for */
115 ch->tfmwidth = TFMSCALE(z, ptr->advance, alpha, beta);
116 /* scale all other TFM units (so they are in DVI units) */
117 a = TFMSCALE(z, ptr->left, alpha, beta);
118 b = TFMSCALE(z, ptr->right, alpha, beta);
119 c = TFMSCALE(z, ptr->height, alpha, beta);
120 d = TFMSCALE(z, ptr->depth, alpha, beta);
122 /* now convert to unscaled pixels */
123 ch->width = XCONV(b - a);
124 ch->height = YCONV(c - d);
125 if(ch->height < 0) ch->height = -ch->height;
129 * the offset is not used, but we might as well set it to
130 * something meaningful (and it MUST be non-zero)
134 ch->glyph.data = NULL;
135 ch->grey.data = NULL;
136 ch->shrunk.data = NULL;
144 * We use this function as a last resort to find the character widths in a
145 * font The DVI rendering code can correctly skip over a glyph if it knows
146 * its TFM width, which is what we try to find here.
148 static int tfm_load_font(DviParams *params, DviFont *font)
153 switch(font->search.info->kpse_type) {
154 case kpse_tfm_format:
157 case kpse_afm_format:
160 case kpse_ofm_format:
167 /* we don't need this */
172 tfm = get_font_metrics(font->fontname, type, font->filename);
176 if(tfm->checksum && font->checksum && tfm->checksum != font->checksum) {
177 warning(_("%s: Checksum mismatch (got %u, expected %u)\n"),
178 font->fontname, (unsigned)tfm->checksum,
179 (unsigned)font->checksum);
181 font->checksum = tfm->checksum;
182 font->design = tfm->design;
186 get_tfm_chars(params, font, tfm, 1);
188 /* free everything */
189 free_font_metrics(tfm);
194 static int tfm_font_get_glyph(DviParams *params, DviFont *font, int code)
198 ch = FONTCHAR(font, code);
199 if(!glyph_present(ch))
203 ch->glyph.w = ch->width;
204 ch->glyph.h = ch->height;
206 * This has two purposes: (1) avoid unnecessary calls to this function,
207 * and (2) detect when the glyph data for a TFM font is actually used
208 * (we'll get a SEGV). Any occurrence of that is a bug.
210 ch->glyph.data = MDVI_GLYPH_EMPTY;