Recommended Free Tools
Some links on this page are affiliate links: if you buy through them we may earn a commission, at no extra cost to you.
Short answer: there is no currently documented, supported Chrome screenshot API for legacy packaged apps that this guide can recommend as a universal recipe. Chrome Apps are deprecated. For a maintained replacement, use a web app with the Screen Capture API when a user should choose a screen, window, or tab, or build a Chrome extension when the task needs extension capabilities. Those capture APIs provide a media stream, not a PNG or JPEG; making a still image requires extracting a video frame and encoding it.
If you are maintaining a packaged app that must keep working, first establish its runtime and Chrome version, then validate any existing capture mechanism there. The extension and web examples below are alternatives for migration, not drop-in code for a packaged app.
Why a packaged-app screenshot recipe needs a platform caveat
Chrome Apps, including packaged apps, are deprecated. Chrome’s migration guidance favors web applications for most use cases and extensions when the required capability is not available to a web application. The current Chrome capture references relevant here describe extension capture APIs and the web Screen Capture API; they do not establish a currently supported screenshot API for legacy packaged apps.
That distinction matters because code that worked in a particular old app environment is not automatically a reliable choice for a maintained deployment. Before changing code, identify how the app is installed and launched, which Chrome version and platform it targets, and whether it is actually a Chrome App or an extension. Do not assume that extension permissions or web APIs can simply be added to a packaged app.
#1 Best Overall
- COMPACT SIZE, COMPACT FUN – The Lenovo Tab One is compact, efficient, and provides non-stop entertainment everywhere you go. It’s lightweight and has a long-lasting battery life so the fun never stops.
- SIMPLICITY IN HAND - Add a touch of style with a modern design that’s tailor-made to fit in your hand. It weighs less than a pound and has an 8.7” display that’s easy to tuck in a purse or backpack.
- NON-STOPPABLE FUN – Freedom never felt so sweet with all-day battery life and up to 12.5 hours of unplugged YouTube streaming. It’s designed to charge 15W faster than previous models so you can spend less time tethered to a power cable.
- PORTABLE MEDIA CENTER - Enjoy vibrant visuals, immersive sound, and endless entertainment anywhere you go. The HD display has 480 nits of brightness for realistic graphics and dual Dolby Atmos speakers that provide impressive sound depth.
- ELEVATED EFFICIENCY - Experience the MediaTek Helio G85 processor and 60Hz refresh rate that ensure fluid browsing, responsive gaming, and lag-free streaming.
For an app that must remain packaged, consult the documentation and compatibility details for its actual runtime and test there. For a new or migrated implementation, choose among the currently documented routes below based on what needs to be captured and what interaction is acceptable.
Choose the capture route by target and app type
| Need | Documented route | What it does |
|---|---|---|
| A user chooses a screen, window, or tab from an extension | chrome.desktopCapture |
Opens a browser picker and provides a short-lived, one-use stream ID to exchange for a media stream. |
| An invoked extension captures its tab | chrome.tabCapture |
Provides tab media capture following user invocation, subject to the API’s permission and execution-context restrictions. |
| A web application asks a user to choose a display surface | getDisplayMedia() |
Shows the browser’s display-selection dialog and returns a media stream. |
| A still screenshot from any of these streams | Video element plus canvas | Extracts and encodes a frame; this is stream processing, not a screenshot-file response from the capture API. |
All three capture routes involve a user-facing choice or invocation. They are not silent, arbitrary screenshot facilities. If the requirement is ongoing capture or background recording rather than one still image, treat that as a different lifecycle and architecture question; Chrome’s extension guidance describes offscreen documents in current extension patterns for background recording.
Capture a user-selected surface in a Chrome extension
For a user-selected screen, window, or tab, the extension API is chrome.desktopCapture.chooseDesktopMedia(). The extension needs the desktopCapture permission. The picker returns a short-lived stream ID that is intended to be used once, and the extension passes it into navigator.mediaDevices.getUserMedia() with Chrome’s documented desktop-media constraints.
Quick wins for a faster PC:
Repair Windows errors before they cause bigger problemsFix Now →Fix the driver behind crashes, sound loss and screen glitchesFind Drivers →Clear out junk files and repair common Windows errorsFree Scan →The API returns media, not an image file. The stream must then be attached to a video element, and a frame drawn into a canvas if the output should be a still. Use Chrome’s official desktop-capture documentation for the exact constraints and extension setup supported by your target version; the following describes the handoff, not a universally validated packaged-app implementation.
Implementation sequence
- Request a surface. Invoke
chooseDesktopMedia()in response to the extension workflow that should show the picker. Offer only the surface types your feature needs. - Handle cancellation. If the user dismisses the picker or no stream ID is returned, stop the workflow and show an appropriate message. Do not try to bypass the selection step.
- Exchange the ID. Use the returned ID with the documented Chrome desktop-media constraints in
getUserMedia(). The stream ID is short-lived and one-use, so do not treat it as a reusable authorization token. - Extract a still. Once a video frame is available, draw it to a canvas sized to the video frame, then encode the canvas to the image type your application needs.
- Release capture. Stop the media tracks when the still is obtained or the user ends the operation. This prevents an unnecessary live capture session from remaining active.
Frame-to-image code pattern
The generic still-frame step can be expressed with browser APIs. This snippet assumes that stream is already the valid MediaStream obtained from the Chrome API, and that the browser allows the canvas export. It does not create the picker, declare a manifest, or supply Chrome’s desktop constraints; verify those parts against the Chrome version and extension architecture you support.
Rank #2
- A VIBRANT, SLIMMER BUILD FOR SHARPER MINDS – Engage in AI-powered smart learning on the stylish Lenovo Idea Tab Plus. The svelte tablet packs a powerful punch with quad speakers, sharp graphics, and all-day battery life.
- CARRY LIGHT, FEEL BRIGHT – Weighing just over a pound, the Idea Tab Plus is light enough to carry from morning to night and thin enough to easily slip between your notebooks. The Luna Grey color is soft, fresh, and designed to feel just right anywhere.
- CIRCLE TO SEARCH – Stay focused and use your Lenovo Tab Pen or fingertip to circle items for instant search results or to translate other languages without switching apps. Circle to Search is powered by Google.
- LET YOUR LEARNING CLICK – Write, organize, sketch, and calculate with four learning apps built to match your flow. Lenovo Notepad, Squid, Nebo, and MyScript Calculator help you stay clear, focused, and ready for every study session.
- MORE TO SEE, MORE TO ENJOY – The 12.1″ 2.5K display delivers rich color and sharp detail. With TÜV Rheinland Low Blue Light and up to 800 nits brightness, the display keeps every frame clear in any light.
async function streamFrameToPngBlob(stream) {
const video = document.createElement('video');
video.muted = true;
video.playsInline = true;
video.srcObject = stream;
await video.play();
await new Promise((resolve) => {
if (video.videoWidth && video.videoHeight) return resolve();
video.addEventListener('loadedmetadata', resolve, { once: true });
});
const canvas = document.createElement('canvas');
canvas.width = video.videoWidth;
canvas.height = video.videoHeight;
canvas.getContext('2d').drawImage(video, 0, 0);
const blob = await new Promise((resolve, reject) => {
canvas.toBlob((result) => result ? resolve(result) : reject(new Error('PNG encoding failed')), 'image/png');
});
stream.getTracks().forEach((track) => track.stop());
video.srcObject = null;
return blob;
}
Call the function only after a valid stream has been acquired. In production code, also stop tracks if playback, metadata, or encoding fails; otherwise an error path can leave capture active. Check for a missing 2D context, an empty video dimension, and a null result from toBlob(). This is a general stream-processing pattern, not a tested recipe asserted for every Chrome release or legacy app environment.
Capture the invoked tab with chrome.tabCapture
When the intended source is the tab on which the user invoked an extension, use chrome.tabCapture rather than asking the user to select among desktop surfaces. The API requires the tabCapture permission and user invocation. Its getMediaStreamId() method returns an opaque, short-lived ID that is exchanged for a stream.
What’s actually slowing this PC down?
Pick the symptom - the matching free tool is one click away.
There are restrictions on the origin and execution context of the frame consuming that ID. In particular, do not assume that an ID obtained in one extension context can be consumed from any other frame or origin. Design the capture handoff around the current Chrome reference for the exact extension setup you use, then pass the acquired stream into the same video-and-canvas still-image step described above.
This route is appropriate when the extension’s target is a tab and the user has initiated the capture. It is not evidence of a supported API for a legacy packaged app, and it does not return a PNG or JPEG on its own.
Capture from a web application with getDisplayMedia()
For a web application that needs a user-selected display surface, use navigator.mediaDevices.getDisplayMedia(). The browser displays a selection dialog; after the user chooses a surface, the call resolves to a MediaStream. As with the extension APIs, the result is a stream rather than an encoded still image. Attach it to a video element, wait until frame dimensions are available, and use canvas to draw and encode the frame.
Rank #3
- LIFE TRANSFORMING – The Lenovo Chromebook Duet is where power meets portability. Amazingly durable, the 2-in-1 convertible laptop is your perfect companion for life on-the-go.
- ALWAYS READY TO GO – With its perfectly portable size, folio keyboard, and all-day battery life, the lightweight Lenovo Chromebook Duet is ready for anything you throw at it.
- ADAPTS TO YOUR EVERY MOVE – Impressively versatile, crafted to impress. The durable design is encased in a full-metal chassis, fortified with tough Corning glass, and supported by a soft folio stand.
- SMILE, SNAP, SHARE - Get ready to take phenomenal photos, even in low light thanks to cutting-edge image processing technology. The front camera comes with a physical shutter to ensure your video calls capture every detail, while keeping your privacy at your fingertips.
- NOT SHORT ON PORTS - Plug into unlimited functionality with two USB Type-C connections. They ensure you can transfer large pictures and videos quickly, enjoy smooth video chats, and connect to external displays.
Use this route only when its user-selection behavior fits the product. A web app cannot silently select an arbitrary display through this flow. Handle the user’s cancellation and stream ending as normal outcomes, and stop tracks once the still has been captured. Check current browser support and the security requirements in the official web API and Chrome guidance before deploying; compatibility can change.
Make the still image useful and reliable
Wait for a real frame
A video element may not have usable dimensions as soon as its source is assigned. Wait for playback and metadata, and confirm that videoWidth and videoHeight are nonzero before sizing the canvas. A zero-sized canvas can produce a blank result even though the stream was acquired successfully.
Choose the output deliberately
Use canvas.toBlob() when you want a binary image object for upload or storage, and handle the possibility that it returns no blob. A data URL may be convenient for small previews, but it encodes the image into a string; choose based on how the result will be consumed. Set the canvas dimensions to the actual video frame dimensions if you want to preserve the captured frame’s pixel size.
Stop tracks on every exit path
When the frame is captured, or when the user cancels or an operation fails, release the stream tracks. Keep cleanup in a finally path in a complete application. For a longer-running recording workflow, define explicit start, stop, navigation, and permission-loss behavior rather than reusing a one-frame routine.
Troubleshooting common failures
- No picker or permission error: confirm you are implementing an extension route, have the required
desktopCaptureortabCapturepermission, and invoke capture through the expected user-facing flow. Packaged-app code is not interchangeable with extension code. - The user closes the picker: treat the missing or rejected capture result as cancellation. Return to the app without attempting to reuse an old stream ID.
- Stream acquisition fails: check that the ID is fresh, used once, and passed with the documented constraints. For
tabCapture, check the consuming frame’s origin and execution context against the API’s restrictions. - Canvas is blank or tiny: wait for video playback and metadata, then verify nonzero
videoWidthandvideoHeightbefore drawing. - Image encoding fails: check that the 2D context exists and that
toBlob()returned a blob. Avoid assuming success merely because the stream is active. - Capture indicator or stream remains active: stop every track after capture and also in error/cancellation cleanup. Clear the video element’s
srcObjectafter release. - Works in an extension but not a packaged app: that mismatch is expected to require investigation. The documented extension APIs do not establish packaged-app support; identify a migration path or verify the legacy runtime’s own capabilities.
Or skip the browser setup
If what you need is a screenshot of a public webpage by URL—not a screenshot of the user’s desktop, a local app, or an extension tab—you can use ScreenshotNeo, a website screenshot API and MCP server. Its endpoint returns a screenshot or PDF from one GET request; it is not a replacement for user-authorized screen capture.
Rank #4
- POWER YOUR STUDY, FUEL YOUR PLAY – Discover smarter learning with the Lenovo Idea Tab. Stay campus-ready with all-day battery life, AI-powered apps to enhance your work, and sharp graphics for tv marathons with friends.
- SMOOTH, POWERFUL, IMMERSIVE – The MediaTek Dimensity 6300 processor is more powerful than ever, with the AI-enhanced multitasking you need to stay ahead.
- CIRCLE IT, SEARCH IT – Use your Lenovo Tab Pen or fingertip to circle items for instant search results or to translate other languages without switching apps. Circle to Search with Google ensures answers are only a circle away.
- SHARP VIEW, CLEAR SOUND – Experience sharp visuals and immersive sound for study sessions and streaming breaks. With 72% NTSC and quad Dolby Atmos-tuned speakers you can enjoy your study breaks with vivid videos and crystal-clear sound.
- LEVEL UP YOUR STUDY – Write, organize, sketch, and calculate with four learning apps built to match your flow. Lenovo AI Note, Squid, Nebo, and MyScript Calculator help you stay clear, focused, and ready for every study session.
For example, this saves a PNG capture of a webpage URL. See the ScreenshotNeo API documentation for options and response details.
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://example.com -o shot.png
ScreenshotNeo accepts cookie/consent banners like a visitor and removes more than 60 known consent platforms, newsletter popups, and chat widgets before capture; each step can be turned off. Bot checks/CAPTCHAs, blank pages, timeouts, failed loads, and cache hits are not billed, and responses identify the page verdict and billing status in headers. Its MCP server provides take_screenshot, get_page_info, and capture_pdf tools for AI agents. The Free plan includes 1,000 shots per month with no card; paid plans start at $5 for 3,000 shots. Every feature is on every plan.
Sign up for ScreenshotNeo’s free plan to get 1,000 screenshots a month with no card.
Frequently Asked Questions
Does canvas code by itself take a screenshot of a Chrome window?
No. The canvas step only turns a frame from an already acquired video stream into an image. A capture API or another authorized stream source must supply that frame.
Free tools Windows power users keep installed
One-click scans. No signup required.
Can ScreenshotNeo capture my desktop or a packaged app window?
No. ScreenshotNeo captures webpages from a URL. It does not provide the user-selected screen, window, or extension-tab capture described in this guide.
Quick Recap
Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.

