Skip to content

Commit 4d19284

Browse files
authored
fixed canvas maxWidth resize issue (#2039)
1 parent ae9af70 commit 4d19284

2 files changed

Lines changed: 43 additions & 4 deletions

File tree

packages/dom/src/serialize-canvas.js

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,13 @@ function createAndInsertImageElement(canvas, clone, percyElementId, imageUrl) {
1313
img.setAttribute('data-percy-canvas-serialized', '');
1414
img.setAttribute('data-percy-serialized-attribute-src', imageUrl);
1515

16-
// set the maxWidth only if it was set on the canvas
17-
if (canvas.style.maxWidth) {
18-
img.style.maxWidth = canvas.style.maxWidth;
16+
// set a default max width to account for canvases that might resize with JS
17+
// Check if width is "static" (fixed pixels) vs "dynamic" (%, vw, etc.)
18+
const hasStaticWidth = canvas.style.width &&
19+
canvas.style.width.match(/^\d+px$/);
20+
21+
if (!hasStaticWidth) {
22+
img.style.maxWidth = img.style.maxWidth || '100%';
1923
}
2024

2125
// insert the image into the cloned DOM and remove the cloned canvas element

packages/dom/test/serialize-canvas.test.js

Lines changed: 36 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,12 @@ describe('serializeCanvas', () => {
2020
height="100px"
2121
style="border: 2px solid red; max-width: 150px;"
2222
></canvas>
23+
<canvas
24+
id="canvas-with-static-width"
25+
width="180px"
26+
height="120px"
27+
style="border: 1px solid green; width: 180px;"
28+
></canvas>
2329
<canvas
2430
id="empty"
2531
width="0px"
@@ -51,6 +57,14 @@ describe('serializeCanvas', () => {
5157
ctxWithMaxWidth.fillRect(10, 10, 50, 30);
5258

5359
cache[plat].dataURLWithMaxWidth = canvasWithMaxWidth.toDataURL();
60+
61+
// Draw on canvas with static width
62+
let canvasWithStaticWidth = dom.getElementById('canvas-with-static-width');
63+
let ctxWithStaticWidth = canvasWithStaticWidth.getContext('2d');
64+
ctxWithStaticWidth.fillStyle = 'green';
65+
ctxWithStaticWidth.fillRect(5, 5, 40, 25);
66+
67+
cache[plat].dataURLWithStaticWidth = canvasWithStaticWidth.toDataURL();
5468
});
5569

5670
serialized = serializeDOM();
@@ -68,8 +82,10 @@ describe('serializeCanvas', () => {
6882
expect($canvas[0].getAttribute('width')).toBe('150px');
6983
expect($canvas[0].getAttribute('height')).toBe('150px');
7084
expect($canvas[0].getAttribute('src')).toMatch('/__serialized__/\\w+\\.png');
71-
expect($canvas[0].getAttribute('style')).toBe('border: 5px solid black;');
85+
expect($canvas[0].getAttribute('style')).toBe('border: 5px solid black; max-width: 100%;');
7286
expect($canvas[0].matches('[data-percy-canvas-serialized]')).toBe(true);
87+
// Verify maxWidth is applied since canvas has no style.width (only attribute width)
88+
expect($canvas[0].style.maxWidth).toBe('100%');
7389

7490
expect(serialized.resources).toContain(jasmine.objectContaining({
7591
url: $canvas[0].getAttribute('src'),
@@ -86,6 +102,8 @@ describe('serializeCanvas', () => {
86102
expect($canvas[0].getAttribute('style')).toBe('border: 2px solid red; max-width: 150px;');
87103
expect($canvas[0].style.maxWidth).toBe('150px');
88104
expect($canvas[0].matches('[data-percy-canvas-serialized]')).toBe(true);
105+
// Verify original maxWidth is preserved (not overridden to 100%)
106+
// since canvas already has maxWidth and no static pixel width
89107

90108
expect(serialized.resources).toContain(jasmine.objectContaining({
91109
url: $canvas[0].getAttribute('src'),
@@ -94,6 +112,23 @@ describe('serializeCanvas', () => {
94112
}));
95113
});
96114

115+
it(`${platform}: does not add maxWidth when canvas has static pixel width`, () => {
116+
let $canvas = $('#canvas-with-static-width');
117+
expect($canvas[0].tagName).toBe('IMG');
118+
expect($canvas[0].getAttribute('width')).toBe('180px');
119+
expect($canvas[0].getAttribute('height')).toBe('120px');
120+
expect($canvas[0].getAttribute('style')).toBe('border: 1px solid green; width: 180px;');
121+
expect($canvas[0].matches('[data-percy-canvas-serialized]')).toBe(true);
122+
// Verify maxWidth is NOT added since canvas has static pixel width (width: 180px)
123+
expect($canvas[0].style.maxWidth).toBe('');
124+
125+
expect(serialized.resources).toContain(jasmine.objectContaining({
126+
url: $canvas[0].getAttribute('src'),
127+
content: cache[platform].dataURLWithStaticWidth.split(',')[1],
128+
mimetype: 'image/png'
129+
}));
130+
});
131+
97132
it(`${platform}: does not serialize canvas elements when JS is enabled`, () => {
98133
serialized = serializeDOM({ enableJavaScript: true });
99134
$ = parseDOM(serialized.html, platform);

0 commit comments

Comments
 (0)