Inject the text from the text layer in the MathML tags when they're in the struct tree (bug 1998046)

This way, the screen readers can read the math content properly.
The elements in the text layer will also have aria-hidden="true"
to avoid duplication.
This commit is contained in:
calixteman 2025-11-30 23:11:15 +01:00
parent 8435e8f4bb
commit 79c72f2c9a
No known key found for this signature in database
GPG Key ID: 0C5442631EE0691F
2 changed files with 25 additions and 4 deletions

View File

@ -420,8 +420,12 @@ describe("accessibility", () => {
expect(mathML)
.withContext(`In ${browserName}`)
.toEqual(
`<mi aria-owns="p76R_mc16"></mi><mo aria-owns="p76R_mc17"></mo><msqrt><mrow><msup><mi aria-owns="p76R_mc18"></mi><mn aria-owns="p76R_mc19"></mn></msup><mo aria-owns="p76R_mc20"></mo><msup><mi aria-owns="p76R_mc21"></mi><mn aria-owns="p76R_mc22"></mn></msup></mrow></msqrt>`
`<mi aria-owns="p76R_mc16">𝑐</mi><mo aria-owns="p76R_mc17">=</mo><msqrt><mrow><msup><mi aria-owns="p76R_mc18">𝑎</mi><mn aria-owns="p76R_mc19">2</mn></msup><mo aria-owns="p76R_mc20">+</mo><msup><mi aria-owns="p76R_mc21">𝑏</mi><mn aria-owns="p76R_mc22">2</mn></msup></mrow></msqrt>`
);
const ariaHidden = await page.$eval("span#p76R_mc16", el =>
el.getAttribute("aria-hidden")
);
expect(ariaHidden).withContext(`In ${browserName}`).toEqual("true");
})
);
});

View File

@ -323,9 +323,26 @@ class StructTreeLayerBuilder {
let element;
if ("role" in node) {
const { role } = node;
element = MathMLElements.has(role)
? document.createElementNS(MathMLNamespace, role)
: document.createElement("span");
if (MathMLElements.has(role)) {
element = document.createElementNS(MathMLNamespace, role);
let text = "";
for (const { type, id } of node.children || []) {
if (type !== "content" || !id) {
continue;
}
const elem = document.getElementById(id);
if (!elem) {
continue;
}
text += elem.textContent.trim() || "";
// Aria-hide the element in order to avoid duplicate reading of the
// math content by screen readers.
elem.ariaHidden = "true";
}
element.textContent = text;
} else {
element = document.createElement("span");
}
const match = role.match(HEADING_PATTERN);
if (match) {
element.setAttribute("role", "heading");