Рейтинг:1

Как преобразовать 32 МБ файла PNG в 200 КБ без потери цветов

флаг us

У меня есть пара изображений размером 32 МБ, и я хочу изменить их размер с 32 МБ до 100 КБ или любого размера КБ, не затрагивая его цвета.

Команды, которые я пытаюсь:

muhammad@muhammad-mohsin:~/scans$ найти . -iname '*.png' -exec mogrify -format jpg "*.png" {} +


мухаммад@мухаммад-мохсин:~/$ найти . -тип f -имя \*.png -удалить


мухаммад@мухаммад-мохсин:~/$ найти . -iname '*.jpg' -exec mogrify -define jpeg:extent=300kb -strip -качество 90 -масштаб 90% *.jpg {} +

Здесь сначала я конвертирую PNG в JPG, который уменьшает его размер с 32 МБ до 5,8 МБ, и все остается прежним, но когда я использую 3-ю команду, она удаляет цвет фона в изображении и делает его в оттенках серого размытым.

Тем не менее, текст по-прежнему читается, а цвета и фоновый логотип — нет.

Как я могу добиться этого с помощью convert, mogrify или любого другого инструмента? Я пробовал все возможные вещи до сих пор.

Это часть исходного изображения

Это часть измененного изображения после команды

Knud Larsen avatar
флаг by
30MB png в 300kb jpg • Пример: `convert Sample.png -resize 22% S300.jpg` .... тогда у вас очень хорошее качество, но изображение меньшего размера.
LearningROR avatar
флаг us
@KnudLarsen Спасибо за это. Действительно помог мне. Можем ли мы добавить какую-то другую функцию, чтобы сделать цвета изображения четкими/яркими и т. д.? Я использую: «convert image.png -resize 35% S300.jpg», и он возвращает размер «763 КБ». Мы близко!
LearningROR avatar
флаг us
@KnudLarsen Можем ли мы выполнить пакетный процесс для этой команды, чтобы все изображения в папке и подпапках получили эту команду? Я пытаюсь найти . -iname '*.png' -exec convert -resize 60% -quality 60 "*.jpg" {} +`, но это не работает.
Рейтинг:4
флаг om

Это из-за того, как работает сжатие JPEG. Он пытается округлить соседние пиксели, которые похожи друг на друга, до аналогичных значений. Это приводит к потере деталей и блочности.

Это становится более заметным при увеличении уровня сжатия, т.е. точно что ты делаешь. Кроме того, вы делаете это в два этапа:

  1. Сжатие без потерь (PNG) в формат с потерями (JPEG).
  2. Сжатие с потерями в сжатие с потерями.

Ты будешь наверное получить лучший результат, перейдя от без потерь к сжатию с потерями в конечном качестве, таким образом применяя сжатие с потерями только один раз, например. с использованием jpeg:extent=300kb -полоса -качество 90 -масштаб 90% в первой конверсии.

Кроме того, вы ничего не говорите о размере изображения и уровне детализации. Возможно, будет невозможно уменьшить его до 300 КБ и сохранить желаемое качество.

Чтобы избавиться от фоновых пятен, вы можете попробовать применить к документу пороговые значения в каком-либо программном обеспечении для редактирования изображений, заставив, например, все, что меньше определенного оттенка серого, быть белым.

Однако, независимо от того, что вы делаете, сжатие из формата без потерь 30 МБ в формат с потерями 300 КБ будет привести к заметному снижению качества.

LearningROR avatar
флаг us
Большое спасибо за подробный ответ. Что вы скажете в этом случае после 5,8 МБ размера файла с JPG. Можем ли мы использовать какой-либо инструмент сжатия, чтобы сделать размер немного меньше?
LearningROR avatar
флаг us
У меня все файлы в PNG. Как я могу использовать `jpeg:extent=300kb -strip -quality 90 -scale 90%` только один раз в этом случае?
vidarlo avatar
флаг om
Вы можете использовать его в своей первой конверсии. И да; вы можете попробовать, например. 2 МБ, и это приведет к лучшему результату, чем цель 300 КБ.
LearningROR avatar
флаг us
Спасибо. Имеет смысл. +1 за хороший ответ. :)
Peter Cordes avatar
флаг fr
*кодирует их как копии друг друга.* - JPEG *только* выполняет квантование DCT, без внутреннего предсказания типа "копировать блок из 29 пикселей в этом направлении". Может быть, вы думаете о кадрах H.264/h.265 I (https://en.wikipedia.org/wiki/High_Efficiency_Image_File_Format)? Я предполагаю, что кодировщик JPEG, выполняющий решетчатое квантование, может попытаться кодировать близлежащие блоки таким же образом, чтобы последний шаг сжатия без потерь мог сохранить больше битов?
Peter Cordes avatar
флаг fr
Или, может быть, вы имеете в виду в очень локальном масштабе, желая округлить высокочастотные компоненты DCT до нуля, сделав соседние пиксели более похожими друг на друга. Этот эффект похожих пикселей является *не* результатом их буквального кодирования как копий друг друга, а на самом деле является результатом кодирования в основном с низкими коэффициентами пространственной частоты.
vidarlo avatar
флаг om
@PeterCordes Спасибо за исправление :)
Peter Cordes avatar
флаг fr
«*попытки округлить соседние пиксели, похожие друг на друга, до похожих значений*» по-прежнему не работают. Это может быть частью результата, но все не так просто. Сжатие JPEG с потерями происходит в частотной области после [DCT 8x8] (https://en.wikipedia.org/wiki/Discrete_cosine_transform#Compression_artifacts), а не с точки зрения фактических соседних пикселей. Таким образом, вы можете получить ["звенящие" артефакты](https://en.wikipedia.org/wiki/Ringing_artifacts) вокруг острых краев, а отдельная обработка блоков 8x8 является причиной того, что JPEG низкого качества становятся блочными.
Peter Cordes avatar
флаг fr
См. также [Два ТОЧНО одинаковых изображения .jpg, одно из которых более чем в два раза превышает размер файла другого — Почему?] (https://photo.stackexchange.com/a/125291) для получения дополнительной информации о сжатии JPEG и что затрудняет или упрощает сжатие некоторых изображений без значительных искажений. (Я написал этот ответ с техническими подробностями, но нацелен на аудиторию, которая еще не знала, как работает сжатие изображений.)
Рейтинг:2
флаг by

я стараюсь найти . -iname '*.png' -exec convert -resize 60% -quality 60 "*.jpg" {} + но это не работает.

Ссылка https://superuser.com/questions/71028/batch-converting-png-to-jpg-in-linux

$ ls -1 *.png | xargs -n 1 bash -c 'convert -quality 60 "$0" "${0%.*}.jpg"'

Преобразует мой пример 31MB.png в 1,4MB.jpg . ... Возможно, вам придется повторить, например. $ ls -1 *.PNG | ... и т.д.

Ссылка комментарий @steeldriver : «немного лучше xargs -d '\n' -n 1 "

LearningROR avatar
флаг us
Спасибо, мистер Кнуд. Я уже сделал это с помощью `find . -iname '*.png' -exec mogrify -resize 60% -quality 60 -format jpg *.png {} +`, но принимая и поддерживая ваш ответ за то, что он направил меня в правильном направлении.
флаг hr
Обратите внимание, что `ls -1 | xargs -n 1` сломается, если какое-либо из имен файлов содержит пробелы. Вы можете сделать это *немного* лучше, используя `xargs -d '\n' -n 1`, который будет работать, за исключением имен файлов, содержащих символы новой строки - вы также можете обрабатывать их, используя нулевые разделители, например. `printf '%s\0' *.png | xargs -0 -n 1 ... `. Однако, поскольку вы создаете новую оболочку bash для каждого файла, мне интересно, будет ли все это так же легко выполняться с помощью цикла оболочки `for f in *.png; сделать ... "$f" "${f%.*}.jpg"; сделано`
Knud Larsen avatar
флаг by
@steeldriver: хорошо, `ls -1` и т. д. и т. д. — это всего лишь один из возможных наборов параметров. Я могу добавить ваше предложение к ответу.

Ответить или комментировать

Большинство людей не понимают, что склонность к познанию нового открывает путь к обучению и улучшает межличностные связи. В исследованиях Элисон, например, хотя люди могли точно вспомнить, сколько вопросов было задано в их разговорах, они не чувствовали интуитивно связи между вопросами и симпатиями. В четырех исследованиях, в которых участники сами участвовали в разговорах или читали стенограммы чужих разговоров, люди, как правило, не осознавали, что задаваемый вопрос повлияет — или повлиял — на уровень дружбы между собеседниками.