Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Browser Canvas CORS Support for Cross Domain Loaded Image Manipulation

Tags:

QUESTION: What browser versions support CORS (Cross-Origin Resource Sharing) headers for Cross Domain Images used in Canvas?

CORS can apply to both cross domain XMLHttpRequests and to image requests. This question is about image requests My normal go to for browser version compatibility http://caniuse.com/cors is unclear on the issue and google search yields no good results.

I did find a recent chrome development blog implying that CORS support was wide spread in modern browsers but might break because of WebGL security problems.
http://blog.chromium.org/2011/07/using-cross-domain-images-in-webgl-and.html

More detail on CORS:

We're considering the viability of using canvas & CORS with cross domain image requests as described in the W3C Working Draft http://www.w3.org/TR/cors/#use-cases. CORS is used by html canvas to allow cross domain resource usage in a fashion similar to the way flash uses crossdomain.xml. Basically, we want to read/edit the image data pixels and we don't want to use a same origin proxy server.

Normally, if are images loaded cross domain and used with html canvas, accessing pixels using functions like canvas.toDataURL() will throw a security error. However, If the server delivering the image adds a header like this, the cross domain usage should be allowed.

access-control-allow-origin: * 

Browsers We Care Most About:

We are planning to work around IE's lack of canvas support using flash, so for desktop browsers with a CORS problem we can do that as well, but on mobile flash is not an option, and using a proxy to make the requests same origin is not an option in our use case. So, I'm particularly interested in Andriod, Iphone, IPAD browser support for CORS.

like image 545
Glenn Avatar asked Aug 20 '11 02:08

Glenn


People also ask

How do you allow cross-origin use of images and canvas?

HTML provides a crossorigin attribute for images that, in combination with an appropriate CORS header, allows images defined by the <img> element that are loaded from foreign origins to be used in a <canvas> as if they had been loaded from the current origin.

Does CORS apply to IMG?

The crossorigin attribute specifies that the img element supports CORS. CORS stands for Cross Origin Resource Sharing. CORS is a standard mechanism to retrieve files from a third party domain or server. If specified, the image file request will be sent with or without credentials.

How do I enable CORS on my browser?

To enable cross-origin access go to Tools->Internet Options->Security tab, click on “Custom Level” button. Find the Miscellaneous -> Access data sources across domains setting and select “Enable” option.


2 Answers

Test Results: Bad News, it appears to only work in Chrome. All other browsers (including Android Mobile) give an error like this:

Failed: DOM Exception: SECURITY_ERR (18) 

Mobile Devices I tested Android (samsung galaxy kernel version 2.6.32.9), Iphone and IPAD V1 and it failed in all three.

You can test your own mobile device with this URL: http://maplarge.com/CrossOriginImageTest.html

The Test Script:

  <!DOCTYPE html> <html> <head> <title>Canvas Cross Origin Image Test: Testing for Canvas Cross Domain Image CORS Support</title> <script type="text/javascript">     function initialize() {          //will fail here if no canvas support         try {             var can = document.getElementById('mycanvas');             var ctx = can.getContext('2d');             var img = new Image();             img.crossOrigin = '';             //domain needs to be different from html page domain to test cross origin security             img.src = 'http://lobbydata.com/Content/images/bg_price2.gif';         } catch (ex) {             document.getElementById("results").innerHTML = "<span style='color:Red;'>Failed: " + ex.Message + "</span>";         }          //will fail here if security error         img.onload = function () {             try {                 var start = new Date().getTime();                 can.width = img.width;                 can.height = img.height;                 ctx.drawImage(img, 0, 0, img.width, img.height);                 var url = can.toDataURL(); // if read succeeds, canvas isn't dirty.                 //get pixels                 var imgd = ctx.getImageData(0, 0, img.width, img.width);                 var pix = imgd.data;                 var len = pix.length;                 var argb = []; //pixels as int                 for (var i = 0; i < len; i += 4) {                     argb.push((pix[i + 3] << 24) + (pix[i] << 16) + (pix[i + 1] << 8) + pix[i + 2]);                 }                 var end = new Date().getTime();                 var time = end - start;                 document.getElementById("results").innerHTML = "<span style='color:Green;'>" +                 "Success: Your browser supports CORS for cross domain images in Canvas <br>"+                 "Read " + argb.length+ " pixels in "+ time+"ms</span>";             } catch (ex) {                 document.getElementById("results").innerHTML = "<span style='color:Red;'>Failed: " + ex + "</span>";             }          }      } </script> </head> <body onload="initialize()"> <h2>Canvas Cross Origin Image Test: Testing for Canvas Cross Domain Image CORS Support</h2> <h2><a href="http://blog.chromium.org/2011/07/using-cross-domain-images-in-webgl-and.html">What is CORS Image Security?</a></h2> <h1 id="results" style="color:Orange;">Testing...</h1> <canvas id="mycanvas"></canvas> <br /> <a href="/Example/List">More Examples</a> </body> </html> 
like image 134
Glenn Avatar answered Nov 25 '22 14:11

Glenn


I just tested this on my iPhone running iOS 6 in both Safari and in Chrome and your test page passes the test. I would have posted this as a comment but I am not given the option to post a comment to your answer.

like image 30
bfcoder Avatar answered Nov 25 '22 14:11

bfcoder