Преоразмеряване на Java изображение - най-близък съсед

Опитвам се да преоразмеря изображение с Java и трябва да получа точния ефект, който се получава, когато преоразмерите с Photoshop Nearest Neighbor (Запазване на твърдите ръбове).

Работата е там, че никога не получавам точно същия ефект...

Опитах следните методи:

1) java-image-scale от mortennobel lib

resampleOp.setFilter(ResampleFilters.getBoxFilter());

това се представя чудесно, но оставя някои артефакти в изображението, които не са там, когато го прави Photoshop.

2) Библиотека TwelveMonkeys за манипулиране на изображения. (ето връзката към github) Не работи добре, PointFilter напълно унищожава градиента вътре и Box filter прави същото като mortennobel getBoxFilter.

3) AWT AffineTransform, това беше най-лошият, напълно нереалистично преоразмеряване.

Сега съм объркан дали най-близкият съсед на photoshop преоразмерява по различен начин от това, което означава името, или всички други библиотеки го правят погрешно (във втория случай коя е библиотеката, която ще го направи правилно?)

Ето изображенията преди и след, генерирани от Photoshop

въведете описание на изображението туквъведете описание на изображението тук

И ето изображението, генерирано от get BoxFilter от mortennobel lib.

въведете описание на изображението тук

Увеличих малко изображенията, за да можете да видите детайлите, в действителност те са по-малки. Всяка помощ наистина се оценява :) Наистина съм заседнал в това.


person Avetis Zakharyan    schedule 21.09.2014    source източник
comment
Библиотеката mortennobel използва филтър за кутии и като такъв не е това, което искате - най-близкият съсед. Мислили ли сте сами да напишете кода? Итерирането върху необработени пиксели на изображението, без никакво филтриране, не е толкова трудно.   -  person Jongware    schedule 21.09.2014
comment
Хм.. Мислех, че филтърът на кутията и най-близкият съсед са едни и същи. Е, обмислих това, но си помислих, че може да е бавно и освен това трябва да има lib, който прави това, нали? Вместо луксозен филтър използвайте простия, това е всичко, което искам. Имам чувството, че има друго име за това, което Photoshop прави, и ако го знаех, щях да намеря правилната библиотека.   -  person Avetis Zakharyan    schedule 21.09.2014
comment
Може да искате да обясните доколко резултатите от използването на RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR се различават от това, което искате да постигнете (вижте също today.java.net/pub/a/today/2007/04/03/ )   -  person Marco13    schedule 21.09.2014
comment
@Marco13, всъщност това току-що реши проблема!!! Благодаря ти! Искате ли да публикувате примерен код като отговор, за да мога да гласувам за? или мога да го направя сам, ако искаш :)   -  person Avetis Zakharyan    schedule 21.09.2014
comment
Бих могъл само да създам фрагмент, до голяма степен базиран на кода от свързания сайт, и да позная подробностите, които помогнаха за разрешаването на проблема във вашия случай. Можете да отговорите на собствения си въпрос (в противен случай ще се опитам да създам подходящ отговор, но мисля, че вашият ще бъде по-актуален)   -  person Marco13    schedule 21.09.2014
comment
Странно... Използването на ResampleOp (от TwelveMonkeys/метод 2) с PointFilter трябва да доведе до абсолютно същия резултат като AffineTransformOp с VALUE_INTERPOLATION_NEAREST_NEIGHBOR (тъй като това е, което използва вътрешно). Ако не стане, това трябва да се счита за грешка. О, не! ;-)   -  person Harald K    schedule 22.09.2014


Отговори (1)


Огромни благодарности на Marco13, че посочи това! Очевидно mortennobel lib не прави най-близкия съсед, вместо това Graphics2D на AWT може, ако се използва с подсказка за изобразяване RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR. Ето кодовия фрагмент, който работи за мен и създаде точното изображение на Photoshop.

destinationBufferedImage = new BufferedImage(newWidth, newHeight, BufferedImage.TYPE_INT_ARGB);
Graphics2D g2 = destinationBufferedImage.createGraphics();
g2.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_NEAREST_NEIGHBOR);
g2.drawImage(sourceBufferedImage, 0, 0, newWidth, newHeight, null);
g2.dispose();
person Avetis Zakharyan    schedule 22.09.2014