Сохранение Canvas в grayscale 8bit jpeg или png
Форум расскажи есть ли какие либо готовые библиотеки или простой способ вывода на сохранение в javascript на стороне клиента в 8 битный jpeg ? Если в двух словах я написал на яс приложение для обрезания фоток с вебкамеры и сохранением их. Собственно потребовалось их преобразовать в grayscale 256 формат. Как убрать цвет я с легкостью нашел, но таки сам сохраненный файл так и остается 32 битным (24 на цвет 8 на альфу), а есть нужда сохранять именно 8 бит т.б. 256 grayscale. Ткните носом в хорошую инфу или помогите реализовать. :help:
|
В гугле отыскалась небольшая кучка конвертеров которые способны сохранить файл в скажем gif или pdf, но вот что бы конкретно как сделать вывод файла jpeg с параметрами мне пока не удалось найти.
|
Цитата:
https://habrahabr.ru/post/173773/ |
Я знаю. Мне не требуется индексированная палитра. Мне нужен файл в таком вот формате.
![]() |
Цитата:
|
Цитата:
|
PNG бывает двух форматов - PNG24 и PNG8. Canvas не работает с индексированной палитрой, вы не сможете получить такую палитру на выходе. Нужна индексированная, значит конвертируйте. Если же ограничить количество оттенков серого в JPEG или PNH24 до 256, то файл при этом как был 24-битным так им и останется.
|
Цитата:
Цитата:
|
Цитата:
Я о том, что задача редкая и найти готовое решение будет проблематично. Так что рекомендую отговорить заказчика от использования компактного формата или выпросить у него дополнительно пару недель рабочего времени чтобы запилить свой конвертор. |
Цитата:
|
Цитата:
![]() Мне не нужна четкая палитра. Я понимаю что реальных цветов там 16 за глаза. Можно палитру эту топором рубить. Всяк в оставшихся 256 хватит оттенков что бы изображение не пострадало. Я делаю изображение серым с помощью кода var imageData = context.getImageData(0, 0, 320, 400); var data = imageData.data; //alert("Hello gray!.2"); for(var i = 0; i < data.length; i +=4) { var brightness = 0.25 * data[i] + 0.70 * data[i + 1] + 0.09 * data[i + 2] ; // red data[i] = brightness; // green data[i + 1] = brightness; // blue data[i + 2] = brightness; data[i + 3] = 255; } context.putImageData(imageData, 0, 0); И теперь есть необходимость сохранить файл в 8 бит. Цитата:
Время есть. Но пару недель на это тратить просто не разумно. Задача редкая, поэтому я и не смог нагуглить библиотеку. Просто какая есть возможность именно для формирования сохраненного файла в 8бит. |
Цитата:
Цитата:
Вы хотя бы на Вики почитайте что такое 8-битная палитра и в каких форматах изображения ее можно сохранить (если ориентироваться на веб), и что такое HighColor и TrueColor изображения. |
Цитата:
//alert("Hello save!."); canvas.toDataURL('image/jpg'); var gh = canvas.toDataURL('image/jpg', 1.0); var a = document.createElement('a'); a.href = gh; a.download = 'photo.jpg'; Вы знаете как это сделать ? Я нет. И где узнать не знаю. |
Цитата:
|
Цитата:
Math.floor((data[0]*11+data[1]*16+data[2]*5)/32) Это разные особенности восприятия яркости в разных условиях? Свои цифры взял из кода Qt. А относительно оптимизации размера, можно взять исходник библиотеки для работы с подходящим форматом и тупо перевести с C/С++ или другого языка на JS. Я даже уверен что полученный код будет компактней раз так в 3. Можно так же поискать компилятор из C/C++ в JS, или интерпретатор, но тогда будет проигрыш по размеру кода и по быстродействию. Так что надо делать выбор между размерами кода и размером картинок. Я бы предоставил все оптимизации непосредственно браузеру. Тогда код процедуры сохранения данных сведётся к такому: location.href = canvas.toDataURL().replace("image/png", "image/octet-stream") |
Цитата:
которое я написал работает через костыль.. А именно после захвата и обрезки изображения его приходится открывать в доп приложении (XnView) и переводить там в глубину цвета 8. потому что 32 бита при погрузке в следующую систему искажаются кардинально. Соответственно вы говорите что сохранить в канвас в PNG8 средствами javascript нет возможности? Что тогда можно еще подключить ? Цитата:
"image/octet-stream" тоже встречал о чем то подобном инфу. Так это получается запись потока в файл? Кстати вот тут другой профессор говорил что канвас не может содержать индексированный цвет, но с другой стороны мне и ненужно его выводить перед сохранением на просмотр. Может есть возможность использовать обычный массив для индексации и перевода в 8 бит? |
Цитата:
Возьмите свое PNG-8 изображение, загрузите его в canvas, а затем сохраните. Сравните размеры первого и второго, и посмотрите свойства его, глубина цвета сохраненного будет 32 бита. |
Цитата:
|
Цитата:
|
Цитата:
Цитата:
|
Цитата:
Что и как вы там делаете, это можно опустить. Пусть вы получаете изображение после canvas, если в нем его обрезаете и т.п. Далее конвертируете его в индексированную палитру. А запись в файл, это уже согласно формата PNG в котором нужно определить параметры - палитру, указать количество цвета и т.п. |
Цитата:
|
Цитата:
Цитата:
И кстати не надо вырывать из контекста Цитата:
|
Цитата:
Цитата:
Самому писать, так это согласно формата. Поэтому и не понятно нахрена вам эти заморочки. Если все-таки предполагается веб, а значит и хранение результата на сервере, то разумнее всего отдать это серверу на растерзание. К примеру, если серверный язык, это РНР, то вашу проблему тремя строками кода решает GD. Если же на клиенте, и ваше приложение использует стороннее ПО xnview, то почему не им сразу сохранить в индексированной палитре. Есть еще один кандидат решения проблемы ImageMagick - достаточно запустить его командной строкой с параметрами и на выходе получим и обрезанное, и серое, и индексированное, и какое угодно. |
Цитата:
Собственно я рекомендую при разработке браузерного приложения переложить максимум задач на браузер. Taifune, Таки надо объяснить заказчику что экономить на размере изображений нецелесообразно. Память нынче дешевая. Кроме случая когда данные надо передать по тормознутому модему(у меня самого мобильный интернет) это не актуально. При работе на локальной машине, даже если это мобилка, это значение вообще не имеет. Выгодней в таких случаях задействовать алгоритм типа GZIP, для таких задач уже есть готовые решения под браузер. Рекомендую сосредоточится на этом. |
Цитата:
|
Цитата:
|
Цитата:
Так теперь далее.. Приложение мое не использует XnView. Это приходится пользователю делать ручками.. Фотки эти мне на сервере ненужны. Они идут для другой программы. Которая уже написана( не мной, это законченный продукт и изменить что то в нем нет возможности). Получать файл тут и далее открывать его в той программе и менять битность и сохранять. А про имадж меджик заинтересовали.. Если его запуск по отношению к файлам в папке возможно реализовать через JS может быть это бы и сошло, но вот беда JS очень параноидальный язык и чую получить доступ к командной строке если не невозможно то очень не просто... |
Я тут получил файл который выдает уже программа в которую я гружу свои фотки. И о чудо ? Что это за формат ? Что скажете профессор ?
![]() Как мне вам верить ? ) Вы же говорили 8битного джепега не бывает и это вообще чуш) |
Цитата:
|
Цитата:
Цитата:
|
Цитата:
Этот формат используется и видео даже, если вы не знали. JPEG в графике, это 24 бита на цвет (нет альфа канала). Как я и ранее предлагал с PNG-8, загрузите свой рисунок 8-битый и сохраните в JPEG, получите 24-биное изображение. Но если работать в редакторе умеющем не просто сохранять, но и оптимизировать, то можно выбрать сохранение "только оттенки серого". Так понятно? То есть "по умолчанию" как вы желаете вам никто не сделает. Цитата:
|
Цитата:
Даже JS но не из под веб страницы... Ну еперный театр )) Серьезно ?) Я об это им написал вроде как. Если бы вы знали способ как запустить коммандную строку со страницы ( То писали бы вирусы :D ). З.Ы. Написать то код кто нибудь поможет ? |
Цитата:
Забейте на JS в данном случае, используйте иное, исходя из OS. |
Цитата:
|
Тогда я этого не понимаю Даже JS но не из под веб страницы.... Если все это не из под веб страницы будет использоваться, то можно даже и JS. Например в среде Windows, это может быть HTA. Можно использовать VBS, он без проблем запустит из под командной строки ImageMagick. В чем проблема?
Не забывайте, что это форум в первую очередь освещает веб приложения. А JS в рамках веб страницы имеет ограничения. |
Цитата:
|
Ну тогда только преобразование в серое в canvas, затем получить данные изображения как getImageData(...).data, затем используя Uint8ClampedArray/blob упаковать согласно формата JPEG нужного и записать в файл.
|
А вот это уже интересно. По идее в этот массив можно записать из любой даты[0][1][2] инфу т.к. кодом что я выше кидал он усредняется и во всех 3 каналах одинаковые значения. А вот как потом через блоб собирать джепег ?
|
У вас уже будут готовые бинарные данные. Например, здесь посмотрите пример Grayscaling and inverting colors. А вообще, вроде бы речь была о том, что изображение уже в градациях серого после ПО, тогда и canvas не нужен.
А далее изучать описание формата, и упаковать в бинарник заголовок файла, который и описывает формат. Если покопаться, то браузеры могут кое что, например тут пример записи в файл Save toBlob to disk, лиса записывает в файл PNG конвертируемый в BMP. Все бы хорошо, но почитайте о поддержке, а ведь в рамках веб нужна кроссбраузерность. И у каждого из них будет свое, если только оно есть. Там же найдете описание и Uint8ClampedArray, можно и ArrayBuffer использовать. Так что "безопасно", это самому ручками, изучайте формат, пакуйте, сохраняйте. |
Часовой пояс GMT +3, время: 09:58. |