сделатьраспознавание изображенийПрограммное обеспечение, применяемое для потоковой передачи изображений, предварительного просмотра, технологий Blob, Base64 и преобразования типов. Эти технологии незаменимы при разработке изображений. На этот раз давайте поиграем с «потоковой передачей изображений»!
1. Общие сценарии
Давайте сначала посмотрим на сценарий использования образа:
- Загрузить через ввод;
- загрузка файлов методом перетаскивания;
- Предварительный просмотр изображения;
- хранение данных изображения;
- Нужен сторонний интерфейс;
- …
Конечно, фактическое приложение намного сложнее, чем это, но если мы освоим основную идею, то это не что иное, как получение и преобразование «потока изображения», давайте углубимся!
Во-вторых, поговорим о потоке изображений
Упомянутый выше «поток изображений» на самом деле представляет собой двоичный поток для представления изображений, который мы часто называем «двоичными изображениями».
Хранилище компьютера физически полностью двоичное, поэтому разница между текстовыми файлами и двоичными файлами не физическая, а логическая.
Некоторые люди могут спросить, зачем использовать двоичный код для представления изображений? Давайте посмотрим на преимущества бинарника:
- Двоичные файлы более компактны и ничем не отличаются от обычного хранилища при хранении символьных данных. Но при хранении чисел, особенно вещественных, двоичный код экономит место;
- Данные, участвующие в вычислении в памяти, хранятся в бинарном формате, поэтому быстрее использовать бинарник для сохранения в файл. При сохранении в виде текстового файла требуется процесс преобразования. Когда объем данных велик, между ними будет значительная разница в скорости;
- При использовании некоторых относительно точных данных использование двоичного хранилища не приведет к потере значимых битов;
Видя это, я считаю, что у каждого есть определенное понимание потоковой передачи изображений. Теперь, когда упомянуто хранилище, добавьте описание того, как изображения хранятся в бэкэнде:
- Один: изображение может быть сохранено в указанной папке сервера как независимый файл, а затем путь может быть сохранен в поле базы данных;
- Второе: преобразовать изображение в бинарный поток и сохранить его непосредственно в базе данных.
Image
в поле типа;
3. Что такое FileReader?
FileReader
объект разрешенWeb
Приложение асинхронно считывает содержимое файла (или буфера необработанных данных), хранящегося на компьютере пользователя, используяFile
илиBlob
Объект указывает файл или данные для чтения.
вFile
Объекты могут быть от пользователя в<input>
Возвращается после выбора файла на элементеFileList
Объекты, которые также могут быть созданы с помощью операций перетаскивания.DataTransfer
объекта, а также может исходить отHTMLCanvasElement
выполнить наmozGetAsFile()
Метод возвращает результат.
Официальная много сказала, на самом деле достаточно знать только, что "используется для чтения файлов".
Описание параметра выглядит следующим образом:
-
FileReader.error
(только чтение): аDOMException
, указывая на то, что при чтении файла произошла ошибка; -
FileReader.readyState
(только для чтения): указываетFileReader
Номер состояния. Значения следующие:-
EMPTY
0 Данные еще не загружены. -
LOADING
1 данные загружаются. -
DONE
2 Выполнены все запросы на чтение.
-
-
FileReader.result
(только для чтения): содержимое файла. Это свойство действует только после завершения операции чтения, формат данных зависит от того, какой метод использовался для инициации операции чтения.
Также есть несколько обработчиков событий:
-
FileReader.onabort
:иметь дело сabort
мероприятие. Это событие запускается, когда операция чтения прерывается. -
FileReader.onerror
:иметь дело сerror
мероприятие. Это событие запускается при возникновении ошибки в операции чтения. -
FileReader.onload
:иметь дело сload
мероприятие. Это событие срабатывает после завершения операции чтения. -
FileReader.onloadstart
:иметь дело сloadstart
мероприятие. Это событие срабатывает при запуске операции чтения. -
FileReader.onloadend
:иметь дело сloadend
мероприятие. Это событие срабатывает, когда операция чтения завершается (успешно или неудачно). -
FileReader.onprogress
:иметь дело сprogress
мероприятие. Событие читаетсяBlob
срабатывает когда.
Доступны следующие методы:
-
FileReader.abort()
: Прервать операцию чтения. По возвращении,readyState
собственностьDONE
. -
FileReader.readAsArrayBuffer()
: начать чтение указанногоBlob
содержание в . Когда-то сделали,result
свойство будет содержатьArrayBuffer
представлять данные файла; -
FileReader.readAsBinaryString()
: начать чтение указанногоBlob
содержание в . Когда-то сделали,result
Свойства будут содержать необработанные двоичные данные читаемого файла. -
FileReader.readAsDataURL()
: начать чтение указанногоBlob
содержание в . Когда-то сделали,result
свойства будут содержатьdata: URL
Строка формата для представления содержимого читаемого файла. -
FileReader.readAsText()
: начать чтение указанногоBlob
содержание в . Когда-то сделали,result
Атрибут будет содержать строку, представляющую содержимое читаемого файла.
Приведенный выше документ очень понятен, но я думаю, вы не читали его по порядку, не беда, у нас еще есть примеры🙈
Конкретные сценарии применения могут быть следующими:
onDrop(files) {
files.forEach(file => {
const reader = new FileReader();
reader.onload = () => {
console.log('Jartto files logs: ', file);
const fileAsBinaryString = reader.result;
// Todo...
};
reader.onabort = () => console.log('file reading was aborted');
reader.onerror = () => console.log('file reading has failed');
reader.readAsBinaryString(file);
});
}
Использование очень простое, единственное, на что вам нужно обратить внимание, это то, что он должен быть вonload
Сделай это позже!В-четвертых, формат base64
Иногда мы видим такой код на веб-страницах:
data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAb4AAABYCAYAAACK55LCAAAgAElEQVR4Xuy9aXNc2ZEleN4e+wIgsO8ACXAnk8mUUqoqldQ9Yz3W/an/wsxvnA/TM2NWizKVmczkTgIg9h0IxL6+fez4DbCo7JQqpZLZfGBARjEJBOK95/de9+PHj3toO//7f40x/BpaYGiBoQWGFhha4BOxgDYMfJ/ISg8fc2iBoQWGFhhaQCwwDHzDjTC0wNACQwsMLfBJWWAY
...
Этоbase64
Данные в формате представляют собой данные изображения.Технический термин называется:Data URI scheme
.
Data URI scheme
Он определен в RFC2397 и предназначен для встраивания небольших данных непосредственно в веб-страницу, чтобы их не нужно было загружать из внешнего файла.
В настоящее время,Data URI scheme
Поддерживаемые типы:
data:,文本数据
data:text/plain,文本数据
data:text/html,HTML 代码
data:text/html;base64,base64 编码的 HTML 代码
data:text/css,CSS代码
data:text/css;base64,base64 编码的 CSS 代码
data:text/javascript,Javascript 代码
data:text/javascript;base64,base64 编码的 Javascript代码
data:image/gif;base64,base64 编码的 gif 图片数据
data:image/png;base64,base64 编码的 png 图片数据
data:image/jpeg;base64,base64 编码的 jpeg 图片数据
data:image/x-icon;base64,base64 编码的 icon 图片数据
Base64
кодировка называетсяBase64
, потому что он использует 64 символа для кодирования произвольных данных.Base64
Кодирование — это, по сути, схема преобразования двоичных данных в текстовые данные. Для недвоичных данных сначала преобразуйте их в двоичную форму, затем вычислите их десятичное значение для каждых 6 последовательных битов (2 в 6-й степени = 64) и найдите соответствующий символ в таблице индексов выше в соответствии с этим значением, и, наконец, получить текстовую строку.
Для более глубокого понимания, пожалуйста, обратитесь к:Принцип кодирования Base64 и применение
5. Формат BLOB-объекта
Большой двоичный объект (двоичный большой объект), большой двоичный объект, представляет собой контейнер, в котором могут храниться двоичные файлы.
Blob
это большой файл, обычноBlob
изображение или звуковой файл, с которым из-за его размера необходимо обращаться особым образом (например, загружать, скачивать или хранить в базе данных).
Вот тот, который я переделалBlob
Объект:
Blob {
name: "图片示例:jartto.png",
preview: "blob:file:///f3823a2a-2908-44cb-81e2-c19d98abc5d1",
size: 47396,
type: "image/png",
}
Обратите внимание, что здесьpreview
Атрибуты можно вынуть для предварительного просмотра изображения.Шесть, base64 в Blob
когда мы получимbase64
Представленный код изображения кажется вам недостаточно элегантным или по различным другим причинам вам может потребоваться преобразовать его вBlob
Формат, код выглядит следующим образом:
base64ToBlob(b64data, contentType, sliceSize) {
sliceSize || (sliceSize = 512);
return new Promise((resolve, reject) => {
// 使用 atob() 方法将数据解码
let byteCharacters = atob(b64data);
let byteArrays = [];
for (let offset = 0; offset < byteCharacters.length; offset += sliceSize) {
let slice = byteCharacters.slice(offset, offset + sliceSize);
let byteNumbers = [];
for (let i = 0; i < slice.length; i++) {
byteNumbers.push(slice.charCodeAt(i));
}
// 8 位无符号整数值的类型化数组。内容将初始化为 0。
// 如果无法分配请求数目的字节,则将引发异常。
byteArrays.push(new Uint8Array(byteNumbers));
}
resolve(new Blob(byteArrays, {
type: contentType
}))
})
}
Метод вызова:
// dataUri 是你的 base64 图片流
let blob = await this.base64ToBlob(dataUri.split(',')[1], 'image/png');
После обработки мы получилиBlob
объект, но, возможно, это:
Blob {
size: 47396,
type: "image/png",
}
Вот и все, план я хочу озвучить не зря? Не волнуйтесь, добавим:
Object.assign(blob,{
// jartto: 这里一定要处理一下
preview: URL.createObjectURL(blob),
name: `图片示例:${index}.png`
});
вы можете использоватьwindow.btoa()
метод кодирования данных, которые могут иметь проблемы во время передачи, и после принятия данных использоватьatob()
метод декодирования данных.оatob
а такжеUint8Array
Я не буду вдаваться в подробности здесь, вы можете взглянуть на документацию:
Семь, Blob в base64
Это еще один сценарий. Он может появиться, когда вы используете сторонний плагин, такой как плагин загрузки изображений, и он автоматически вернется к вам.Blob
объекта, но, к сожалению, вы обнаружили, что использовали сторонний сервисный интерфейс, который получает толькоbase64
Данные в формате немного похожи на плач.
Не бойтесь, у нас также есть решение, а именно:
blobToBase64(blob) {
return new Promise((resolve, reject) => {
const fileReader = new FileReader();
fileReader.onload = (e) => {
resolve(e.target.result);
};
fileReader.readAsDataURL(blob);
fileReader.onerror = () => {
reject(new Error('文件流异常'));
};
});
}
Метод вызова:
const allBase64 = await this.blobToBase64(blobObj);
Добавлю, что упомянутая выше сцена — это то, с чем я действительно столкнулся, а жизнь полна сюрпризов.
Восемь, URL-адрес base64
Что ж, самое интересное, я повысил требования, дайте только URL-адрес (локальный или онлайн-адрес) изображения, можете ли вы закодировать изображение в поток? Ответ да, здесь мы должны спроситьcanvas
сейчас:
Идея очень проста, нарисовать холст в соответствии с данными объекта изображения, а затем использовать его для эквивалентного представления потока изображения.
getDataUri(url) {
return new Promise((resolve, reject) => {
/* eslint-disable */
let image = new Image();
image.onload = function() {
let canvas = document.createElement('canvas');
canvas.width = this.naturalWidth;
canvas.height = this.naturalHeight;
canvas.getContext('2d').drawImage(this, 0, 0);
// Data URI
resolve(canvas.toDataURL('image/png'));
};
image.src = url;
// console.log(image.src);
image.onerror = () => {
reject(new Error('图片流异常'));
};
});
}
Вы можете назвать это так:
let dataUri = await this.getDataUri(`image/test/jartto.png`);
9. Часто задаваемые вопросы и дополнительные инструкции
1.Failed to execute 'readAsDataURL' on 'FileReader': parameter 1 is not of type 'Blob'.
Если возникает вышеуказанная проблема, проверьте, имеет ли ваш объект Blob правильный формат и отсутствуют ли необходимые элементы.
2. Необходимо удалить многие сторонние приложенияbase64
информация заголовка:
base64.replace(/^data:image\/(jpeg|png|gif);base64,/,'')
3.FileReader
После прочтения файла не забудьте поставитьonload
Помните, внутри функции.
4. В использованииcanvas.getContext('2d').drawImage(this, 0, 0);
В процессе обязательно обращайте внимание наthis
указать, в противном случае может возникнуть исключение.
5.base64
ПеременаBlob
,Пожалуйста, помните:
Object.assign(blob,{
// jartto: 这里一定要处理一下
preview: URL.createObjectURL(blob),
name: `图片示例:${index}.png`
});
10. Резюме
Чувствуете ли вы легкое головокружение, когда изображение перемещается? Поверьте, если вы внимательно прочитаете статью, то ваша обработка графических данных в дальнейшем будет проходить гораздо более плавно.
Мне всегда нравится писать статьи так: в свободное от проекта время записывайте проблемы, а потом разбирайтесь в них по порядку. Знание похоже на ветку: вы продолжаете учиться и размышлять, оно продолжает распространяться и делиться, и со временем оно образует сеть.
Итак, усердно учитесь, позвольте себе вырасти в высокое дерево, полное жизненной силы, и затенять небо.
11. Справочные ресурсы
Blob
MDN FileReader
бинарное изображение
Convert Image to Data URI
Отображение изображения HTML base64 img