简体   繁体   English

我无法使用画布从Blob URL中裁剪图像

[英]I can't crop an image from a blob URL using canvas

I'm building an application where users can upload a photo, and then that photo is resized and assigned as the src of a different image tag. 我正在构建一个应用程序,用户可以在其中上传照片,然后调整照片的大小并将其分配为其他图像标签的src。 I just can't get it to work, and I'm guessing it's because of the blob URL. 我只是无法使其正常工作,而我猜测是由于Blob URL所致。 Any help would be awesome. 任何帮助都是极好的。

Here's the live example . 这是现场示例

HTML: HTML:

<!DOCTYPE html>
<html>
    <head>
        <meta name='viewport' content='width=device-width,initial-scale=1,minimum-scale=1'>

        <title>Test</title>

        <!-- styles -->
        <link rel="stylesheet" href="http://code.jquery.com/ui/1.11.0/themes/smoothness/jquery-ui.css">

        <!-- scripts -->
        <script src="http://code.jquery.com/jquery-1.11.1.min.js"></script>
        <script src='js/script.js'></script>
    </head>

    <body>
        <label for='existing'>Choose existing photo:</label>
            <input id="existing" type="file" accept="image/*">

        <div id="photo_container">
            <img id="photo" src="" width="640">
            <img id="new">
        </div>

        <canvas width="200"></canvas>
    </body>
</html>

JS: JS:

$(document).ready(
    function()
    {   
        var showPicture = document.querySelector("#photo");
        var takePicture = document.querySelector("#existing");

        takePicture.onchange = function( event )
        {
            var files = event.target.files, file;

            if (files && files.length > 0) 
            {
                file = files[0];
            }

            try 
            {
                var URL = window.URL || window.webkitURL;
                var imgURL = URL.createObjectURL(file);

                showPicture.src = imgURL;

                var canvas = document.querySelector('canvas');
                var newImage = document.querySelector('img#new');
                var ctx = canvas.getContext('2d');
                var photoHeight = showPicture.height;
                var photoWidth = showPicture.width;

                canvas.width = photoWidth;
                canvas.height = photoHeight;

                ctx.drawImage(showPicture, photoWidth/2, photoHeight/2);

                newImage.src = canvas.toDataURL('image/jpeg');
            }

            catch(e) 
            {
                try 
                {
                    var fileReader = new FileReader();

                    fileReader.onload = function (event) 
                    {

                        showPicture.src = event.target.result;

                    };

                    fileReader.readAsDataURL(file);
                }

                catch(e) 
                {

                    var error = document.querySelector("#error");

                    if (error) 
                    {
                        error.innerHTML = "Neither createObjectURL or FileReader are supported";
                    }
                }
            }
        };
    }
);

Here's one way to load a CORS compliant image that has been selected by the user using FileReader. 这是一种加载由用户使用FileReader.选择的CORS兼容图像的方法FileReader.

BTW, remember that if the user loads an image with transparency (eg. .png) then the resulting .jpg will be black where the incoming image is transparent. 顺便说一句,请记住,如果用户加载具有透明性的图像(例如.png),则在传入图像为透明的情况下,生成的.jpg将为黑色。

Example code and a Demo: http://jsfiddle.net/m1erickson/9e9LD/ 示例代码和演示: http : //jsfiddle.net/m1erickson/9e9LD/

My example uses drag/drop but you can substitute file-browse if you prefer. 我的示例使用拖放功能,但是如果愿意,可以使用文件浏览代替。

<!doctype html>
<html>
<head>
<link rel="stylesheet" type="text/css" media="all" href="css/reset.css" /> <!-- reset css -->
<script type="text/javascript" src="http://code.jquery.com/jquery.min.js"></script>
<style>
    body{ background-color: ivory; }
    canvas{border:1px solid red;}
    #dropzone{border:1px solid blue; width:300px;height:300px;}
</style>
<script>
$(function(){

    // dropzone event handlers
    var dropzone;
    dropzone = document.getElementById("dropzone");
    dropzone.addEventListener("dragenter", dragenter, false);
    dropzone.addEventListener("dragover", dragover, false);
    dropzone.addEventListener("drop", drop, false);

    //
    function dragenter(e) {
      e.stopPropagation();
      e.preventDefault();
    }
    //

    function dragover(e) {
      e.stopPropagation();
      e.preventDefault();
    }

    //
    function drop(e) {
      e.stopPropagation();
      e.preventDefault();

      var dt = e.dataTransfer;
      var files = dt.files;

      handleFiles(files);
    }

    //
    function handleFiles(files) {

        for (var i = 0; i < files.length; i++) {

          // get the next file that the user selected
          var file = files[i];
          var imageType = /image.*/;

          // don't try to process non-images
          if (!file.type.match(imageType)) {
            continue;
          }

          // a seed img element for the FileReader
          var img = document.createElement("img");
          img.classList.add("obj");
          img.file = file;

          // get an image file from the user
          // this uses drag/drop, but you could substitute file-browsing
          var reader=new FileReader();
          reader.onload=(function(aImg){
              return function(e) {
                  aImg.onload=function(){

                      // draw the aImg onto the canvas
                      var canvas=document.createElement("canvas");
                      var ctx=canvas.getContext("2d");
                      canvas.width=aImg.width;
                      canvas.height=aImg.height;

                      // I don't know your design requirements about clipping
                      // but you can use the extended form of drawImage to crop
                      // the image as your design requires.

                      ctx.drawImage(aImg,0,0);

                      // make the jpeg image
                      var newImg=new Image();
                      newImg.onload=function(){
                          newImg.id="newest";
                          document.body.appendChild(newImg);
                      }
                      newImg.src=canvas.toDataURL('image/jpeg');
                  }
                  // e.target.result is a dataURL for the image
                  aImg.src = e.target.result;
              }; 
          })(img);
          reader.readAsDataURL(file);

        } // end for

    } // end handleFiles

}); // end $(function(){});
</script>
</head>
<body>
    <h4>Drag an image from desktop to blue dropzone.</h4>
    <div id="dropzone"></div>
    <div id="preview"></div>
</body>
</html>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM