Windows Errors? Fix Them Before They Spread
Repair common Windows errors and clear accumulated junk for a smoother, more stable PC - no reinstall needed.Free scan · no reinstallOutdated Drivers Are Slowing You Down
One free scan finds every outdated or missing driver and matches the right update for your exact hardware.Free scan · exact hardware matchSet crossOrigin on the image before assigning its src; setting it on the canvas does not grant permission. Then configure the image server to return an Access-Control-Allow-Origin header matching your page. With both sides configured, you can draw a cross-origin image and read or export its pixels. Without successful CORS, the browser taints the canvas and protected read/export methods fail with SecurityError.
The correct pattern
Use the image element’s CORS mode before the network request starts. In markup:
<img crossorigin="anonymous" src="https://cdn.example.com/photo.jpg" alt="">
In JavaScript, assign crossOrigin first, attach handlers, and only then set src:
const img = new Image();
img.crossOrigin = "anonymous";
img.onload = () => {
const canvas = document.querySelector("canvas");
const ctx = canvas.getContext("2d");
ctx.drawImage(img, 0, 0);
const pixels = ctx.getImageData(0, 0, canvas.width, canvas.height);
console.log(pixels.data.length);
};
img.onerror = (event) => {
console.error("Image failed to load", event);
};
img.src = "https://cdn.example.com/photo.jpg";
The order matters. Changing crossOrigin after src has started a request cannot change that request; create or reload the image instead.
#1 Best Overall
What crossOrigin controls
HTMLImageElement.crossOrigin is a string property that reflects the image’s crossorigin content attribute. Its meaningful states are anonymous and use-credentials.
anonymous: cross-origin without credentials
This requests the image with CORS while omitting cookies and other credentials for a cross-origin load. It is the appropriate default when the image is public and does not require a logged-in session.
const img = new Image();
img.crossOrigin = "anonymous";
img.src = "https://images.example.com/public/banner.webp";
use-credentials: include credentials
This uses a credentialed CORS request. Cookies, client certificates, and authorization credentials may be included. The server must explicitly allow credentials with Access-Control-Allow-Credentials: true and return an origin-specific Access-Control-Allow-Origin value.
const privateImage = new Image();
privateImage.crossOrigin = "use-credentials";
privateImage.onload = () => draw(privateImage);
privateImage.src = "https://account.example.com/avatar.jpg";
A wildcard response such as Access-Control-Allow-Origin: * is incompatible with credentialed sharing. Use the requesting origin instead, and configure the server to vary the response by origin when necessary.
Missing, empty, or invalid values
If the attribute is missing, the image uses the No CORS state. An empty or invalid value uses the anonymous state. Do not rely on an empty attribute as a substitute for deliberately setting anonymous; being explicit makes the request and server configuration easier to audit.
Server headers are required
The browser-side property does not grant access by itself. The image response must opt in with an appropriate Access-Control-Allow-Origin header.
Public image example
For a page at https://app.example.com, a response can include:
Access-Control-Allow-Origin: https://app.example.com
For a genuinely public, non-credentialed asset, a wildcard may be suitable:
Access-Control-Allow-Origin: *
Do not use the wildcard when the image is loaded with use-credentials.
Credentialed image example
A credentialed response needs both an origin-specific allow header and:
Access-Control-Allow-Origin: https://app.example.com
Access-Control-Allow-Credentials: true
The server must send these headers on the actual image response, including responses served through a CDN or object-storage layer. A header on an HTML page, redirect, or unrelated API response does not authorize the image.
Why a canvas becomes tainted
When a foreign-origin image is drawn without successful CORS approval, the canvas becomes origin-tainted. This protects pixels that the page is not authorized to read. A tainted canvas can still be displayed, but script cannot extract its protected pixel data.
Recommended Free Tools
Operations blocked by tainting
getImageData()toDataURL()toBlob()captureStream()
These calls throw a SecurityError (or otherwise fail according to the API) once the canvas contains unauthorized foreign-origin data. Drawing a same-origin image generally avoids this path. If any tainted source is drawn, later clearing or drawing another image does not make the existing canvas trustworthy; use a new canvas and redraw only approved sources.
Markup, JavaScript, and canvas examples
Markup-only image
<canvas id="preview" width="800" height="450"></canvas>
<img id="hero" crossorigin="anonymous"
src="https://cdn.example.com/hero.jpg" alt="Product preview">
<script>
const canvas = document.getElementById("preview");
const ctx = canvas.getContext("2d");
const hero = document.getElementById("hero");
hero.addEventListener("load", () => ctx.drawImage(hero, 0, 0));
hero.addEventListener("error", () => console.error("CORS image load failed"));
</script>
Exporting a permitted image
const canvas = document.querySelector("canvas");
const ctx = canvas.getContext("2d");
const img = new Image();
img.crossOrigin = "anonymous";
img.onload = () => {
canvas.width = img.naturalWidth;
canvas.height = img.naturalHeight;
ctx.drawImage(img, 0, 0);
try {
const dataUrl = canvas.toDataURL("image/png");
document.querySelector("#result").src = dataUrl;
} catch (error) {
if (error.name === "SecurityError") {
console.error("Canvas is tainted; check image CORS headers", error);
} else {
throw error;
}
}
};
img.src = "https://cdn.example.com/photo.png";
Drawing a selected region
function drawCrop(url, sx, sy, sw, sh) {
return new Promise((resolve, reject) => {
const image = new Image();
image.crossOrigin = "anonymous";
image.onload = () => {
const canvas = document.createElement("canvas");
canvas.width = sw;
canvas.height = sh;
canvas.getContext("2d").drawImage(image, sx, sy, sw, sh, 0, 0, sw, sh);
resolve(canvas);
};
image.onerror = reject;
image.src = url;
});
}
A reliable debugging checklist
- Verify ordering. Confirm
img.crossOriginor the markup attribute appears beforesrcis assigned. - Inspect the actual response. In browser developer tools, open Network, select the image request, and check the response headers for
Access-Control-Allow-Origin. - Match the origin exactly. Scheme, hostname, and port all matter.
https://app.example.comis different fromhttp://app.example.comand from another port. - Check credentials. For
use-credentials, requireAccess-Control-Allow-Credentials: trueand an origin-specific allow header, not a wildcard. - Reload after changing settings. Create a new
Imageor assignsrcagain after changing the mode; a completed request cannot be retrofitted. - Test the read operation. A visible image does not prove that pixels are readable. Call
getImageData()or an export method and inspect the exact exception. - Check redirects and CDNs. Every redirect and the final image response must preserve a compatible CORS policy. Configure the cache to vary by
Originwhen responses differ per origin.
Common errors and fixes
“The image displays, but toDataURL throws SecurityError”
The image loaded without an acceptable CORS response or another source already tainted the canvas. Add the correct image-server header, set the mode before src, reload, and draw onto a fresh canvas.
“No ‘Access-Control-Allow-Origin’ header”
The server did not authorize your page. This cannot be fixed solely in front-end JavaScript. Change the CDN or object-storage CORS configuration, proxy the asset through a server you control, or use a same-origin copy where you have the rights to do so.
Rank #4
“Credential is not supported if the CORS header is ‘*’”
You used use-credentials while the response used a wildcard origin. Return the exact requesting origin and Access-Control-Allow-Credentials: true, or switch to anonymous if credentials are unnecessary.
“Setting crossOrigin did nothing”
Usually the property was set after src, the image was cached from an earlier mode, or the server header is absent. Set the property first, create a new image, and inspect the network response rather than relying on the visual result.
Canvas is tainted after drawing several images
One unauthorized image is enough. Audit every drawImage source, including canvases, video frames, SVG images, and composited assets. Ensure each foreign-origin source is CORS-authorized before it is drawn.
Choosing the right mode
| Situation | Image setting | Server requirement | Typical result |
|---|---|---|---|
| Public image; pixels must be readable | anonymous |
Matching Access-Control-Allow-Origin |
Canvas can be read if all sources pass |
| Private image requiring cookies or credentials | use-credentials |
Specific origin plus Access-Control-Allow-Credentials: true |
Credentialed CORS load and readable pixels |
| Image does not need pixel access | Omit CORS mode | No CORS authorization needed for display alone | May display, but drawing can taint the canvas |
| Same-origin image | Either explicit mode or default, as appropriate | Same-origin policy applies | Normally avoids cross-origin tainting |
Performance and operational considerations
CORS does not change the image’s intrinsic size or decoding cost. Large images still consume memory when decoded and copied into a canvas. Set the canvas dimensions deliberately, draw at the required resolution, and avoid repeatedly creating large temporary canvases. If you control the CDN, configure cache behavior carefully: an origin-reflecting policy generally requires the cache to vary on Origin so one site’s authorization is not served to another.
Use anonymous whenever credentials are not needed. It reduces exposure of cookies and avoids the stricter credentialed-header requirements. Use use-credentials only when the image service genuinely depends on an authenticated session.
Or skip the browser setup
If your goal is to obtain a clean screenshot rather than manipulate browser pixels yourself, ScreenshotNeo provides a website screenshot API and MCP server. It accepts consent banners before capture and removes more than 60 known consent platforms, newsletter popups, and chat widgets; each step can be disabled. Bot checks, CAPTCHAs, blank pages, timeouts, failed loads, and cache hits are not billed, and responses identify the page verdict and billing status in X-Page-Verdict and X-Billed headers.
One request returns PNG, JPEG, WebP, or PDF. The API supports full-page captures with lazy images loaded, CSS-selector element captures, dark mode, device presets and custom viewports, retina scale, PDF paper and page controls, custom CSS and JavaScript, clicks, selector or network-idle waits, request blocking, headers, cookies, user agents, authorization, timezone, geolocation, transparent backgrounds, resizing, configurable cache TTLs, signed links, asynchronous jobs with signed webhooks, bulk capture of up to 100 URLs per call, usage reporting, and an OpenAPI specification. Parameter names used by other screenshot APIs also work, easing migration.
cURL
curl -G "https://api.screenshotneo.com/v1/shot" -d access_key=YOUR_API_KEY --data-urlencode url=https://stripe.com -o shot.webp
Python
import requests
r = requests.get("https://api.screenshotneo.com/v1/shot", params={"access_key": "YOUR_API_KEY", "url": "https://stripe.com"}, timeout=90)
open("shot.webp", "wb").write(r.content)
Node.js
const q = new URLSearchParams({ access_key: 'YOUR_API_KEY', url: 'https://stripe.com' });
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);
See the ScreenshotNeo API documentation for parameters and response details. The Free plan includes 1,000 screenshots per month with no card; paid plans start at $5 for 3,000 shots. An MCP server exposes take_screenshot, get_page_info, and capture_pdf to Claude, Cursor, and other MCP clients. Create a free ScreenshotNeo account to start.
Frequently Asked Questions
Can I set crossOrigin on a canvas element?
No. Set the CORS mode on each HTMLImageElement before its request begins; the canvas has no setting that authorizes a foreign image.
What’s actually slowing this PC down?
Pick the symptom - the matching free tool is one click away.
Does crossOrigin fix CORS when I do not control the image server?
No. The server must return a compatible Access-Control-Allow-Origin response. If it cannot, use a permitted same-origin or server-side copy instead.
Which mode should I use for a public CDN image?
Use anonymous when you need readable canvas pixels and the CDN can authorize your page. Use use-credentials only when authentication is required.
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.

