Skip to content

Commit 4ee9c39

Browse files
Prevent inherited spacing from affecting text layer
Fixes #21259. Reset letter-spacing and word-spacing on the text layer and hidden measurement canvas so inherited page styles do not affect text layer alignment. Add an integration regression test for inherited spacing.
1 parent ea18e73 commit 4ee9c39

3 files changed

Lines changed: 59 additions & 1 deletion

File tree

src/display/text_layer.js

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -473,7 +473,8 @@ class TextLayer {
473473
// OffscreenCanvas.
474474
const canvas = document.createElement("canvas");
475475
canvas.style.cssText =
476-
"position:absolute;top:0;left:0;width:0;height:0;display:none";
476+
"position:absolute;top:0;left:0;width:0;height:0;display:none;" +
477+
"letter-spacing:normal;word-spacing:normal";
477478
canvas.lang = lang;
478479
document.body.append(canvas);
479480
ctx = canvas.getContext("2d", {

test/integration/text_layer_spec.mjs

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,61 @@ import { startBrowser } from "../test.mjs";
4949
*/
5050

5151
describe("Text layer", () => {
52+
describe("Text layout", () => {
53+
let pages;
54+
55+
beforeEach(async () => {
56+
pages = await loadAndWait(
57+
"tracemonkey.pdf",
58+
".textLayer .endOfContent",
59+
100,
60+
{
61+
postPageSetup: async page => {
62+
await page.evaluate(() => {
63+
const style = document.createElement("style");
64+
style.textContent = `
65+
body,
66+
#mainContainer {
67+
letter-spacing: 5px;
68+
word-spacing: 5px;
69+
}
70+
`;
71+
document.documentElement.append(style);
72+
});
73+
},
74+
}
75+
);
76+
});
77+
78+
afterEach(async () => {
79+
await closePages(pages);
80+
});
81+
82+
it("must ignore inherited text spacing styles", async () => {
83+
await Promise.all(
84+
pages.map(async ([_, page]) => {
85+
const spacing = await page.evaluate(() => {
86+
const textLayer = document.querySelector(".textLayer");
87+
const span = textLayer.querySelector("span");
88+
const textLayerStyle = getComputedStyle(textLayer);
89+
const spanStyle = getComputedStyle(span);
90+
return {
91+
textLayerLetterSpacing: textLayerStyle.letterSpacing,
92+
textLayerWordSpacing: textLayerStyle.wordSpacing,
93+
spanLetterSpacing: spanStyle.letterSpacing,
94+
spanWordSpacing: spanStyle.wordSpacing,
95+
};
96+
});
97+
98+
expect(spacing.textLayerLetterSpacing).toEqual("normal");
99+
expect(spacing.spanLetterSpacing).toEqual("normal");
100+
expect(["0px", "normal"]).toContain(spacing.textLayerWordSpacing);
101+
expect(["0px", "normal"]).toContain(spacing.spanWordSpacing);
102+
})
103+
);
104+
});
105+
});
106+
52107
describe("Text selection", () => {
53108
// page.mouse.move(x, y, { steps: ... }) doesn't work in Firefox, because
54109
// puppeteer will send fractional intermediate positions and Firefox doesn't

web/text_layer_builder.css

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@
2222
overflow: clip;
2323
opacity: 1;
2424
line-height: 1;
25+
letter-spacing: normal;
26+
word-spacing: normal;
2527
text-size-adjust: none;
2628
forced-color-adjust: none;
2729
transform-origin: 0 0;

0 commit comments

Comments
 (0)