GithubHelp home page GithubHelp logo

Comments (7)

haraldk avatar haraldk commented on June 16, 2024 1

Hi Ben,

Thanks for reporting! I think I understand the issue.

Unfortunately, it's not as easy as just "allow ... explicit photometric interpretation", as that photometric may not be compatible with the actual image data. We could make an illegal combination of photometric and actual image data throw an exception, but that would make the library harder to use in some cases. Or we could automatically convert, but that's quite hard to implement robustly, and may make some writes surprisingly slow due to the implicit conversion. So I tried to keep things simple by just going with whatever the input was.

For the logic you mention, I use the following, to avoid the fixed color model, but instead use the color model supplied in the image:

// Can't use createFromRenderedImage in this case, as it does not consider palette for TYPE_BYTE_BINARY...
// TODO: Consider writing workaround in ImageTypeSpecifiers
ImageTypeSpecifier spec = new ImageTypeSpecifier(renderedImage);

So I think you should be able to get WHITE_IS_ZERO, if the IndexColorModel really has white at index 0 (which is opposite of the default BufferedImage.TYPE_BYTE_BINARY color model). From your test code, I see you use com.twelvemonkeys.image.MonochromeColorModel. This model has black in index 0. Try instead to use a color model like this:

new IndexColorModel(1, 2, new int[] {0xFFFFFFFF, 0xFF000000}, 0, false, -1, DataBuffer.TYPE_BYTE);

I'll create a test case to verify this (I thought I had that already), but feel free to try it out and report back in the mean time! 😀

from twelvemonkeys.

ben-manes avatar ben-manes commented on June 16, 2024 1

Thank you, @haraldk! I had seen your similar comment in #533 (comment). Unfortunately it didn't work for me because the color model was inferred from ImageTypeSpecifier.createFromRenderedImage, which always selects createGrayscale, and that ignores the image's to use instead a hard coded color model (see ImageTypeSpecifier.Grayscale). I hadn't realized that there was a constructor, new ImageTypeSpecifier(renderedImage), which then lets me pass through the image's original color model. That magical line fixes it and the output becomes WhiteIsZero! Thank you!!! 😃

from twelvemonkeys.

ben-manes avatar ben-manes commented on June 16, 2024 1

That didn't work when using a jpeg output. I forget why, but those two lines resolves that issue.

Caused by: javax.imageio.IIOException: Metadata components != number of destination bands
	at java.desktop/com.sun.imageio.plugins.jpeg.JPEGImageWriter.checkSOFBands(JPEGImageWriter.java:1337)
	at java.desktop/com.sun.imageio.plugins.jpeg.JPEGImageWriter.writeOnThread(JPEGImageWriter.java:739)
	at java.desktop/com.sun.imageio.plugins.jpeg.JPEGImageWriter.write(JPEGImageWriter.java:384)
	at com.twelvemonkeys.imageio.plugins.jpeg.JPEGImageWriter.write(JPEGImageWriter.java:173)
	at com.twelvemonkeys.imageio.plugins.tiff.TIFFImageWriter.writePage(TIFFImageWriter.java:252)
	at com.twelvemonkeys.imageio.plugins.tiff.TIFFImageWriter.writeToSequence(TIFFImageWriter.java:964)

from twelvemonkeys.

haraldk avatar haraldk commented on June 16, 2024 1

Thanks for reporting!
Pushed a fix for that, should be in the latest snapshot and a proper release soon. 😀

from twelvemonkeys.

haraldk avatar haraldk commented on June 16, 2024

Excellent!

There's actually two constructors you can use:

  • public ImageTypeSpecifier(ColorModel colorModel, SampleModel sampleModel) which is kind of the "canonical" constructor
  • public ImageTypeSpecifier(RenderedImage image) (basically the same as ImageTypeSpecifier(image.getColorModel(), image.getSampleModel()))

But yes, it unfortunate that the many factory methods don't just do the right thing from the start. I've made my own ImageTypeSepcifiers class with factory methods for these situations. I'm also adding special handling for createFromRenderedImage now, to preservere palette/LUT for IndexColorModel.

PS: Studying your sample code some more, I don't think you actually need the lines:

var type = ImageTypeSpecifier.createFromRenderedImage(image); // ..or new ImageTypeSpecifier(image)
var tiffMetadata = new TIFFImageMetadata(List.of(
            new TIFFEntry(TAG_X_RESOLUTION, new Rational(settings.xResolution())),
            new TIFFEntry(TAG_Y_RESOLUTION, new Rational(settings.yResolution()))));
var metadata = writer.convertImageMetadata(tiffMetadata, type, params);
writer.writeToSequence(new IIOImage(image, /* thumbnails */ null, metadata), params);

It should be enough to just do:

var tiffMetadata = new TIFFImageMetadata(List.of(
            new TIFFEntry(TAG_X_RESOLUTION, new Rational(settings.xResolution())),
            new TIFFEntry(TAG_Y_RESOLUTION, new Rational(settings.yResolution()))));
writer.writeToSequence(new IIOImage(image, /* thumbnails */ null, tiffMetadata), params);

...as the writer will merge ("convert") the metadata and fill in/overwrite any necessary values in the write methods anyway.

from twelvemonkeys.

ben-manes avatar ben-manes commented on June 16, 2024

Thanks, I’ll give that a shot. Less code for me to screw up! 🙂

from twelvemonkeys.

haraldk avatar haraldk commented on June 16, 2024

Interesting... I need to investigate a little, but I don't think we should pass the TIFF image metadata to the JPEG writer, when writing a JPEG compressed TIFF. That's probably an oversight...

from twelvemonkeys.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.