Получить данные изображения в JavaScript?


У меня есть обычная HTML-страница с некоторыми изображениями (просто обычный <img /> HTML-теги). Я хотел бы получить их содержимое, желательно в кодировке base64, без необходимости повторно загружать изображение (т. е. он уже загружен браузером, поэтому теперь я хочу контент).

Я хотел бы достичь этого с помощью Greasemonkey и Firefox.

6 301

6 ответов:

Примечание: это работает только в том случае, если изображение из того же домена, что и страница, или имеет crossOrigin="anonymous" атрибут и сервер поддерживает CORS. Это также не даст вам исходный файл, но перекодированную версию. Если вам нужно, чтобы результат был идентичен оригиналу, см. Kaiido по.


вам нужно будет создать элемент холста с правильными размерами и скопировать данные изображения с помощью

эта функция принимает URL-адрес, а затем возвращает изображение BASE64

function getBase64FromImageUrl(url) {
    var img = new Image();

    img.setAttribute('crossOrigin', 'anonymous');

    img.onload = function () {
        var canvas = document.createElement("canvas");
        canvas.width =this.width;
        canvas.height =this.height;

        var ctx = canvas.getContext("2d");
        ctx.drawImage(this, 0, 0);

        var dataURL = canvas.toDataURL("image/png");

        alert(dataURL.replace(/^data:image\/(png|jpg);base64,/, ""));
    };

    img.src = url;
}

называйте это, как это : getBase64FromImageUrl("images/slbltxt.png")

идет долго после, но ни один из ответов здесь не является полностью правильным.

при рисовании на холсте переданное изображение не сжимается + все предварительно умножается.
При экспорте его распаковывают или повторно сжимают с помощью другого алгоритма и не умножают.

все браузеры и устройства будут иметь различные ошибки округления происходит в этом процессе
(см. холст отпечатков пальцев).

Так что если кто-то хочет base64 версию изображения файл, они должны запрос это снова (большую часть времени он будет поступать из кэша), но на этот раз как Blob.

затем вы можете использовать FileReader читать его либо как ArrayBuffer, либо как dataURL.

function toDataURL(url, callback){
    var xhr = new XMLHttpRequest();
    xhr.open('get', url);
    xhr.responseType = 'blob';
    xhr.onload = function(){
      var fr = new FileReader();
    
      fr.onload = function(){
        callback(this.result);
      };
    
      fr.readAsDataURL(xhr.response); // async call
    };
    
    xhr.send();
}

toDataURL(myImage.src, function(dataURL){
  result.src = dataURL;

  // now just to show that passing to a canvas doesn't hold the same results
  var canvas = document.createElement('canvas');
  canvas.width = myImage.naturalWidth;
  canvas.height = myImage.naturalHeight;
  canvas.getContext('2d').drawImage(myImage, 0,0);

  console.log(canvas.toDataURL() === dataURL); // false - not same data
  });
<img id="myImage" src="https://dl.dropboxusercontent.com/s/4e90e48s5vtmfbd/aaa.png" crossOrigin="anonymous">
<img id="result">

в дополнение к ответу Мэтью, я хотел бы сказать, что изображение.ширина и изображение.высота возвращает отображаемый размер изображения (и обрезать изображение при рисовании его на холсте)

используйте naturalWidth и naturalHeight вместо этого, который использует изображение реального размера.

см http://www.whatwg.org/specs/web-apps/current-work/multipage/edits.html#dom-img-naturalwidth

более современная версия ответа кайидо с помощью fetch будет:

function toDataURL(url) {
  return fetch(url)
      .then((response)=> {
        return response.blob();
      })
      .then(blob=> {
        return URL.createObjectURL(blob);
      });
}

https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API/Using_Fetch

function encodeImageFileAsURL(cb) {
    return function() {
        var file = this.files[0];
        var reader = new FileReader();
        reader.onloadend = function() {
            cb(reader.result);
        }
        reader.readAsDataURL(file);
    }
}

$('#inputFileToLoad').change(encodeImageFileAsURL(function(base64Img) {
    $('.output')
        .find('textarea')
        .val(base64Img)
        .end()
        .find('a')
        .attr('href', base64Img)
        .text(base64Img)
        .end()
        .find('img')
        .attr('src', base64Img);
}));
@import url('//netdna.bootstrapcdn.com/bootstrap/3.1.0/css/bootstrap.min.css'); body{ padding: 20px; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<h2>Input</h2>
<form class="input-group" id="img2b64">
    <input id="inputFileToLoad" type="file" onchange="encodeImageFileAsURL();" />
</form>
<hr>
Вот рабочий пример скрипки: -загрузить и получить данные изображения