Frustrated with getting blank images in Puppeteer Chrome screenshots, recently I was in a situation where I needed to migrate an existing Puppeteer project from Ubuntu over to CentOS7. When the transition to the new OS was made, I noticed an odd quirk where some of my screenshots would end up returning a blank white image.
Perplexed as to the reason why, I trolled through many of the Github issues raised in the Puppeteer project. I eventually narrowed down my issue to this specific one – the main reason being that when using the elementHandle.screenshot function, capturing an element outside of the viewport results in a blank / empty screenshot.
Debugging the URL page I was performing the screenshot on, my default viewport width and heights were 1920 x 1280. The actual width and height of the full page was 1920 x 6785.14252. I noticed the page had a height with a decimal in it.
Further down in the comment, the same issue raised mentions that others who have a height value with decimals in it, will have the same symptoms of a blank image being returned too.
I eventually solved my blank images issue after stumbling across this pull request which gave me the idea to resize the viewport before taking the screenshot.
The fix that worked for me ended up looking like this:
... const page = await chrome.newPage(); const defaultViewport = { height: 1920, width: 1280 }; await page.goto(url); await page.waitForFunction('window.ready'); // Resize the viewport to screenshot elements outside of the viewport const bodyHandle = await page.$('body'); const boundingBox = await bodyHandle.boundingBox(); const newViewport = { width: Math.max(defaultViewport.width, Math.ceil(boundingBox.width)), height: Math.max(defaultViewport.height, Math.ceil(boundingBox.height)), }; await page.setViewport(Object.assign({}, defaultViewport, newViewport)); let buffer; try { let elementHandle = await page.$('#my-target-div'); buffer = await elementHandle.screenshot(); ... } ...