public ImageInfo getImageInfo()

in src/main/java/org/apache/commons/imaging/formats/tiff/TiffImageParser.java [398:579]


    public ImageInfo getImageInfo(final ByteSource byteSource, final TiffImagingParameters params) throws ImagingException, IOException {
        final FormatCompliance formatCompliance = FormatCompliance.getDefault();
        final TiffContents contents = new TiffReader(params != null && params.isStrict()).readDirectories(byteSource, false, formatCompliance);
        final TiffDirectory directory = contents.directories.get(0);

        final TiffField widthField = directory.findField(TiffTagConstants.TIFF_TAG_IMAGE_WIDTH, true);
        final TiffField heightField = directory.findField(TiffTagConstants.TIFF_TAG_IMAGE_LENGTH, true);

        if (widthField == null || heightField == null) {
            throw new ImagingException("TIFF image missing size info.");
        }

        final int height = heightField.getIntValue();
        final int width = widthField.getIntValue();

        final TiffField resolutionUnitField = directory.findField(TiffTagConstants.TIFF_TAG_RESOLUTION_UNIT);
        int resolutionUnit = 2; // Inch
        if (resolutionUnitField != null && resolutionUnitField.getValue() != null) {
            resolutionUnit = resolutionUnitField.getIntValue();
        }

        double unitsPerInch = -1;
        switch (resolutionUnit) {
        case 1:
            break;
        case 2: // Inch
            unitsPerInch = 1.0;
            break;
        case 3: // Centimeter
            unitsPerInch = 2.54;
            break;
        default:
            break;

        }

        int physicalWidthDpi = -1;
        float physicalWidthInch = -1;
        int physicalHeightDpi = -1;
        float physicalHeightInch = -1;

        if (unitsPerInch > 0) {
            final TiffField xResolutionField = directory.findField(TiffTagConstants.TIFF_TAG_XRESOLUTION);
            final TiffField yResolutionField = directory.findField(TiffTagConstants.TIFF_TAG_YRESOLUTION);

            if (xResolutionField != null && xResolutionField.getValue() != null) {
                final double xResolutionPixelsPerUnit = xResolutionField.getDoubleValue();
                physicalWidthDpi = (int) Math.round(xResolutionPixelsPerUnit * unitsPerInch);
                physicalWidthInch = (float) (width / (xResolutionPixelsPerUnit * unitsPerInch));
            }
            if (yResolutionField != null && yResolutionField.getValue() != null) {
                final double yResolutionPixelsPerUnit = yResolutionField.getDoubleValue();
                physicalHeightDpi = (int) Math.round(yResolutionPixelsPerUnit * unitsPerInch);
                physicalHeightInch = (float) (height / (yResolutionPixelsPerUnit * unitsPerInch));
            }
        }

        final TiffField bitsPerSampleField = directory.findField(TiffTagConstants.TIFF_TAG_BITS_PER_SAMPLE);

        int bitsPerSample = 1;
        if (bitsPerSampleField != null && bitsPerSampleField.getValue() != null) {
            bitsPerSample = bitsPerSampleField.getIntValueOrArraySum();
        }

        final int bitsPerPixel = bitsPerSample; // assume grayscale;
        // dunno if this handles colormapped images correctly.

        final List<String> comments = Allocator.arrayList(directory.size());
        for (final TiffField field : directory) {
            comments.add(field.toString());
        }

        final ImageFormat format = ImageFormats.TIFF;
        final String formatName = "TIFF Tag-based Image File Format";
        final String mimeType = "image/tiff";
        final int numberOfImages = contents.directories.size();
        // not accurate ... only reflects first
        final boolean progressive = false;
        // is TIFF ever interlaced/progressive?

        final String formatDetails = "TIFF v." + contents.header.tiffVersion;

        boolean transparent = false; // TODO: wrong
        boolean usesPalette = false;
        final TiffField colorMapField = directory.findField(TiffTagConstants.TIFF_TAG_COLOR_MAP);
        if (colorMapField != null) {
            usesPalette = true;
        }

        final int photoInterp = 0xffff & directory.getFieldValue(TiffTagConstants.TIFF_TAG_PHOTOMETRIC_INTERPRETATION);
        final TiffField extraSamplesField = directory.findField(TiffTagConstants.TIFF_TAG_EXTRA_SAMPLES);
        final int extraSamples;
        if (extraSamplesField == null) {
            extraSamples = 0; // no extra samples value
        } else {
            extraSamples = extraSamplesField.getIntValue();
        }
        final TiffField samplesPerPixelField = directory.findField(TiffTagConstants.TIFF_TAG_SAMPLES_PER_PIXEL);
        final int samplesPerPixel;
        if (samplesPerPixelField == null) {
            samplesPerPixel = 1;
        } else {
            samplesPerPixel = samplesPerPixelField.getIntValue();
        }

        final ImageInfo.ColorType colorType;
        switch (photoInterp) {
        case TiffTagConstants.PHOTOMETRIC_INTERPRETATION_VALUE_BLACK_IS_ZERO:
        case TiffTagConstants.PHOTOMETRIC_INTERPRETATION_VALUE_WHITE_IS_ZERO:
            // the ImageInfo.ColorType enumeration does not distinguish
            // between monotone white is zero or black is zero
            colorType = ImageInfo.ColorType.BW;
            break;
        case TiffTagConstants.PHOTOMETRIC_INTERPRETATION_VALUE_RGB:
            colorType = ImageInfo.ColorType.RGB;
            // even if 4 samples per pixel are included, TIFF
            // doesn't specify transparent unless the optional "extra samples"
            // field is supplied with a non-zero value
            transparent = samplesPerPixel == 4 && extraSamples != 0;
            break;
        case TiffTagConstants.PHOTOMETRIC_INTERPRETATION_VALUE_RGB_PALETTE:
            colorType = ImageInfo.ColorType.RGB;
            usesPalette = true;
            break;
        case TiffTagConstants.PHOTOMETRIC_INTERPRETATION_VALUE_CMYK:
            colorType = ImageInfo.ColorType.CMYK;
            break;
        case TiffTagConstants.PHOTOMETRIC_INTERPRETATION_VALUE_YCB_CR:
            colorType = ImageInfo.ColorType.YCbCr;
            break;
        default:
            colorType = ImageInfo.ColorType.UNKNOWN;
        }

        final short compressionFieldValue;
        if (directory.findField(TiffTagConstants.TIFF_TAG_COMPRESSION) != null) {
            compressionFieldValue = directory.getFieldValue(TiffTagConstants.TIFF_TAG_COMPRESSION);
        } else {
            compressionFieldValue = TiffConstants.COMPRESSION_UNCOMPRESSED_1;
        }
        final int compression = 0xffff & compressionFieldValue;
        final ImageInfo.CompressionAlgorithm compressionAlgorithm;

        switch (compression) {
        case TiffConstants.COMPRESSION_UNCOMPRESSED_1:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.NONE;
            break;
        case TiffConstants.COMPRESSION_CCITT_1D:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.CCITT_1D;
            break;
        case TiffConstants.COMPRESSION_CCITT_GROUP_3:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.CCITT_GROUP_3;
            break;
        case TiffConstants.COMPRESSION_CCITT_GROUP_4:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.CCITT_GROUP_4;
            break;
        case TiffConstants.COMPRESSION_LZW:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.LZW;
            break;
        case TiffConstants.COMPRESSION_JPEG_OBSOLETE:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.JPEG_TIFF_OBSOLETE;
            break;
        case TiffConstants.COMPRESSION_JPEG:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.JPEG;
            break;
        case TiffConstants.COMPRESSION_UNCOMPRESSED_2:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.NONE;
            break;
        case TiffConstants.COMPRESSION_PACKBITS:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.PACKBITS;
            break;
        case TiffConstants.COMPRESSION_DEFLATE_PKZIP:
        case TiffConstants.COMPRESSION_DEFLATE_ADOBE:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.DEFLATE;
            break;
        default:
            compressionAlgorithm = ImageInfo.CompressionAlgorithm.UNKNOWN;
            break;
        }
        return new ImageInfo(formatDetails, bitsPerPixel, comments, format, formatName, height, mimeType, numberOfImages, physicalHeightDpi, physicalHeightInch,
                physicalWidthDpi, physicalWidthInch, width, progressive, transparent, usesPalette, colorType, compressionAlgorithm);
    }