Как сжать JPEG-файл до ограниченного размера (например, 200 КБ) без потери качества изображения
Я хочу уменьшить размер изображения около 200 КБ, прежде чем сохранить в базу данных. Допустим, у меня есть файл растрового изображения около 39 МБ, мне нужно преобразовать растровое изображение в формат Jpeg, а затем уменьшить файл Jpeg <= 200 КБ (можно конвертировать все типы графических файлов (например, BMP, JPG, PNG), но окончательный тип графики будет быть Jpeg меньше чем 200KB). Я пишу следующий код, чтобы попытаться преобразовать (в этом случае я установил качество jpg равным 10, поскольку я хочу, чтобы размер файла составлял 200 КБ):
function BMPtoJPG(var BMPpic, JPGpic: string):boolean;
var Bitmap: TBitmap;
JpegImg: TJpegImage;
begin
Result:= False;
Bitmap := TBitmap.Create;
try
Bitmap.LoadFromFile(BMPpic) ;
JpegImg := TJpegImage.Create;
try
JpegImg.CompressionQuality := 10; //in this case i set the quality to 10 so the file size will be around 200KB)
JpegImg.Assign(Bitmap);
JpegImg.Compress;
JpegImg.SaveToFile(JPGpic) ;
Result:=True;
finally
JpegImg.Free
end;
finally
Bitmap.Free;
end;
end;
Я использую тот же файл изображения для преобразования в программе Adobe Lightroom в диалоговом окне экспорта, ограничив размер до 200 КБ, и сравниваю с изображением, преобразованным вышеуказанной функцией BMPtoJPG. Качество изображения от Adobe Lightroom намного лучше, чем у метода функции (размер файла около 200 КБ)
Может кто-нибудь показать мне, как писать код уменьшить размер изображения (ограничить размер до 200 КБ), в то время как качество не сильно падает.
Спасибо и признателен за ваш ответ.
2 ответа
Если ваша цель состоит в том, чтобы иметь меньший размер файла, вы можете сначала изменить размер растрового изображения, а затем применить лучший CompressionQuality
темп.
В результате глобальное качество изображения, вероятно, будет лучше.
TJpegImage
опирается на стандартную библиотеку libjpeg, в то время как я полагаю, что у Adobe есть собственная настроенная реализация. Вы можете попробовать другие реализации, например, включенную в GDI +, или чисто паскальскую реализацию, или даже старую библиотеку Intel.
Посмотрите, поддерживает ли ваш кодировщик выборку. Если вы отбираете компоненты Cb и Cr с более низкой скоростью, чем компонент Y, вы часто можете получить лучшее сжатие без значительной потери качества. Если вы делаете 4:1:1, вы сокращаете объем данных для сжатия почти на треть. 2:1:1 разрезает его пополам.
Этот метод называется подвыборкой цветности. К сожалению, акции Delphi TJpegImage
обертка вокруг реализации IJG вер. 6b не предоставляет эту возможность и инициализирует контекст кодера значениями по умолчанию, которые соответствуют 4:2:0. Ссылаться на TJPEGImage.Compress
код метода, libjpeg
документация и jpeglib.h
или же JPEGLIB.PAS
от pasjpeg
пакет, если вы предпочитаете (последний - просто прямой перевод IJG-версии ver 6a на Pascal).
Также вы можете перейти на другую реализацию. В дополнение к списку @Arnaud Bouchez стоит упомянуть еще одну реализацию Pascal, доступную для повторного использования: http://www.colosseumbuilders.com/sourcecode