Browse Source

Draw glyphs one by one to position them correctly and remove all the scaling hack

Vivien Nicolas 14 years ago
parent
commit
13bf137220
  1. 61
      fonts.js
  2. 55
      pdf.js

61
fonts.js

@ -114,60 +114,6 @@ var serifFonts = { @@ -114,60 +114,6 @@ var serifFonts = {
'Wide Latin': true, 'Windsor': true, 'XITS': true
};
var FontMeasure = (function FontMeasure() {
var kScalePrecision = 30;
var ctx = document.createElement('canvas').getContext('2d');
ctx.scale(1 / kScalePrecision, 1);
var current;
var measureCache;
return {
setActive: function fonts_setActive(font, size) {
if (current == font) {
var sizes = current.sizes;
if (!(measureCache = sizes[size]))
measureCache = sizes[size] = Object.create(null);
} else {
measureCache = null;
}
var name = font.loadedName;
var bold = font.bold ? 'bold' : 'normal';
var italic = font.italic ? 'italic' : 'normal';
size *= kScalePrecision;
var rule = italic + ' ' + bold + ' ' + size + 'px "' + name + '"';
ctx.font = rule;
current = font;
},
measureText: function fonts_measureText(text, font, size) {
var width;
if (measureCache && (width = measureCache[text]))
return width;
try {
width = 0.0;
var composite = font.composite;
for (var i = 0; i < text.length; i++) {
var charcode = composite ?
((text.charCodeAt(i++) << 8) + text.charCodeAt(i)) :
text.charCodeAt(i);
var charWidth = parseFloat(font.encoding[charcode].width);
width += charWidth;
}
// XXX should use the unit-per-em value from the embedded font
var unitsPerEm = 1000;
width = width * size / unitsPerEm;
} catch(e) {
width = ctx.measureText(text).width / kScalePrecision;
}
if (measureCache)
measureCache[text] = width;
return width;
}
};
})();
var FontLoader = {
listeningForFontLoad: false,
@ -1142,9 +1088,10 @@ var Font = (function Font() { @@ -1142,9 +1088,10 @@ var Font = (function Font() {
// so create an identity encoding
var widths = properties.widths;
for (i = 0; i < numGlyphs; i++) {
var width = widths[i];
encoding[i] = {
unicode: i + kCmapGlyphOffset,
width: widths[i] || properties.defaultWidth
width: IsNum(width) ? width : properties.defaultWidth
};
}
} else {
@ -2360,13 +2307,13 @@ var Type2CFF = (function() { @@ -2360,13 +2307,13 @@ var Type2CFF = (function() {
if (code == -1)
index = code = mapping.unicode || index;
var width = mapping.width || defaultWidth;
if (code <= 0x1f || (code >= 127 && code <= 255))
code += kCmapGlyphOffset;
var width = mapping.width;
properties.glyphs[glyph] = properties.encoding[index] = {
unicode: code,
width: width
width: IsNum(width) ? width : defaultWidth
};
charstrings.push({

55
pdf.js

@ -4242,9 +4242,10 @@ var PartialEvaluator = (function() { @@ -4242,9 +4242,10 @@ var PartialEvaluator = (function() {
continue;
var code = j >> 1;
var width = glyphsWidths[code];
encoding[code] = {
unicode: glyphID,
width: glyphsWidths[code] || defaultWidth
width: IsNum(width) ? width : defaultWidth
};
}
} else if (type == 'CIDFontType0') {
@ -4316,7 +4317,7 @@ var PartialEvaluator = (function() { @@ -4316,7 +4317,7 @@ var PartialEvaluator = (function() {
var width = properties.widths[i] || properties.widths[glyph];
map[i] = {
unicode: index,
width: width || properties.defaultWidth
width: IsNum(width) ? width : properties.defaultWidth
};
if (glyph)
@ -4615,9 +4616,6 @@ function ScratchCanvas(width, height) { @@ -4615,9 +4616,6 @@ function ScratchCanvas(width, height) {
}
var CanvasGraphics = (function() {
var kScalePrecision = 50.0;
var kRasterizerMin = 14;
function constructor(canvasCtx, imageCanvas) {
this.ctx = canvasCtx;
this.current = new CanvasExtraState();
@ -4878,22 +4876,13 @@ var CanvasGraphics = (function() { @@ -4878,22 +4876,13 @@ var CanvasGraphics = (function() {
return;
var fontObj = font.fontObj;
var name = fontObj.loadedName;
if (!name) {
// TODO: fontDescriptor is not available, fallback to default font
name = 'sans-serif';
}
this.current.font = fontObj;
this.current.fontSize = size;
var name = fontObj.loadedName || 'sans-serif';
if (this.ctx.$setFont) {
this.ctx.$setFont(name, size);
} else {
FontMeasure.setActive(fontObj, size);
size = (size <= kRasterizerMin) ? size * kScalePrecision : size;
var bold = fontObj.black ? (fontObj.bold ? 'bolder' : 'bold') :
(fontObj.bold ? 'bold' : 'normal');
@ -4944,42 +4933,40 @@ var CanvasGraphics = (function() { @@ -4944,42 +4933,40 @@ var CanvasGraphics = (function() {
ctx.translate(current.x, -1 * current.y);
var scaleFactorX = 1, scaleFactorY = 1;
var font = current.font;
if (font) {
if (current.fontSize <= kRasterizerMin) {
scaleFactorX = scaleFactorY = kScalePrecision;
ctx.scale(1 / scaleFactorX, 1 / scaleFactorY);
}
ctx.transform.apply(ctx, font.textMatrix || IDENTITY_MATRIX);
text = font.charsToUnicode(text);
}
var size = current.fontSize;
var composite = font.composite;
var encoding = font.encoding;
var fontSize = current.fontSize;
var charSpacing = current.charSpacing;
var wordSpacing = current.wordSpacing;
var textHScale = current.textHScale;
if (charSpacing != 0 || wordSpacing != 0 || textHScale != 1) {
scaleFactorX *= textHScale;
ctx.scale(1 / textHScale, 1);
var width = 0;
for (var i = 0; i < text.length; i++) {
if (composite) {
var position = i * 2 + 1;
var charcode = (originalText.charCodeAt(position - 1) << 8) +
originalText.charCodeAt(position);
} else {
var charcode = originalText.charCodeAt(i);
}
for (var i = 0, ii = text.length; i < ii; ++i) {
ctx.fillText(text.charAt(i), 0, 0);
var c = originalText.charAt(i);
var charWidth = FontMeasure.measureText(c, font, size);
var charWidth = font.encoding[charcode].width * fontSize * 0.001;
charWidth += charSpacing;
if (c.charCodeAt(0) == 32)
if (charcode == 32)
charWidth += wordSpacing;
ctx.translate(charWidth * scaleFactorX, 0);
ctx.fillText(text.charAt(i), 0, 0);
ctx.translate(charWidth, 0);
width += charWidth;
}
current.x += width;
} else {
ctx.fillText(text, 0, 0);
current.x += FontMeasure.measureText(originalText, font, size);
}
this.ctx.restore();
},

Loading…
Cancel
Save