Search in sources :

Example 6 with TIFFTag

use of it.geosolutions.imageio.plugins.tiff.TIFFTag in project imageio-ext by geosolutions-it.

the class TIFFField method createFromMetadataNode.

/**
 * Creates a <code>TIFFField</code> from a TIFF native image
 * metadata node. If the value of the <tt>"tagNumber"</tt> attribute
 * of the node is not found in <code>tagSet</code> then a new
 * <code>TIFFTag</code> with name <code>"unknown"</code> will be
 * created and assigned to the field.
 *
 * @param tagSet The <code>TIFFTagSet</code> to which the
 * <code>TIFFTag</code> of the field belongs.
 * @param node A native TIFF image metadata <code>TIFFField</code> node.
 * @throws IllegalArgumentException if <code>node</code> is
 * <code>null</code>.
 * @throws IllegalArgumentException if the name of the node is not
 * <code>"TIFFField"</code>.
 */
public static TIFFField createFromMetadataNode(TIFFTagSet tagSet, Node node) {
    if (node == null) {
        throw new IllegalArgumentException("node == null!");
    }
    String name = node.getNodeName();
    if (!name.equals("TIFFField")) {
        throw new IllegalArgumentException("!name.equals(\"TIFFField\")");
    }
    int tagNumber = Integer.parseInt(getAttribute(node, "number"));
    TIFFTag tag;
    if (tagSet != null) {
        tag = tagSet.getTag(tagNumber);
    } else {
        tag = new TIFFTag("unknown", tagNumber, 0, null);
    }
    int type = TIFFTag.TIFF_UNDEFINED;
    int count = 0;
    Object data = null;
    Node child = node.getFirstChild();
    if (child != null) {
        String typeName = child.getNodeName();
        if (typeName.equals("TIFFUndefined")) {
            String values = getAttribute(child, "value");
            StringTokenizer st = new StringTokenizer(values, ",");
            count = st.countTokens();
            byte[] bdata = new byte[count];
            for (int i = 0; i < count; i++) {
                bdata[i] = (byte) Integer.parseInt(st.nextToken());
            }
            type = TIFFTag.TIFF_UNDEFINED;
            data = bdata;
        } else {
            int[] otype = new int[1];
            int[] ocount = new int[1];
            Object[] odata = new Object[1];
            initData(node.getFirstChild(), otype, ocount, odata);
            type = otype[0];
            count = ocount[0];
            data = odata[0];
        }
    } else {
        int t = TIFFTag.MAX_DATATYPE;
        while (t >= TIFFTag.MIN_DATATYPE && !tag.isDataTypeOK(t)) {
            t--;
        }
        type = t;
    }
    return new TIFFField(tag, type, count, data);
}
Also used : StringTokenizer(java.util.StringTokenizer) TIFFFieldNode(it.geosolutions.imageioimpl.plugins.tiff.TIFFFieldNode) Node(org.w3c.dom.Node) IIOMetadataNode(javax.imageio.metadata.IIOMetadataNode) TIFFTag(it.geosolutions.imageio.plugins.tiff.TIFFTag)

Example 7 with TIFFTag

use of it.geosolutions.imageio.plugins.tiff.TIFFTag in project imageio-ext by geosolutions-it.

the class TIFFIFD method initialize.

public void initialize(ImageInputStream stream, boolean ignoreUnknownFields, final boolean isBTIFF) throws IOException {
    removeTIFFFields();
    List tagSetList = getTagSetList();
    final long numEntries;
    if (isBTIFF)
        numEntries = stream.readLong();
    else
        numEntries = stream.readUnsignedShort();
    for (int i = 0; i < numEntries; i++) {
        // Read tag number, value type, and value count.
        int tag = stream.readUnsignedShort();
        int type = stream.readUnsignedShort();
        int count;
        if (isBTIFF) {
            long count_ = stream.readLong();
            count = (int) count_;
            if (count != count_)
                throw new IllegalArgumentException("unable to use long number of values");
        } else
            count = (int) stream.readUnsignedInt();
        // Get the associated TIFFTag.
        TIFFTag tiffTag = getTag(tag, tagSetList);
        // Ignore unknown fields.
        if (ignoreUnknownFields && tiffTag == null) {
            if (isBTIFF)
                stream.skipBytes(8);
            else
                stream.skipBytes(4);
            // Continue with the next IFD entry.
            continue;
        }
        long nextTagOffset;
        if (isBTIFF) {
            nextTagOffset = stream.getStreamPosition() + 8;
            int sizeOfType = TIFFTag.getSizeOfType(type);
            if (count * sizeOfType > 8) {
                long value = stream.readLong();
                stream.seek(value);
            }
        } else {
            nextTagOffset = stream.getStreamPosition() + 4;
            int sizeOfType = TIFFTag.getSizeOfType(type);
            if (count * sizeOfType > 4) {
                long value = stream.readUnsignedInt();
                stream.seek(value);
            }
        }
        if (tag == BaselineTIFFTagSet.TAG_STRIP_BYTE_COUNTS || tag == BaselineTIFFTagSet.TAG_TILE_BYTE_COUNTS || tag == BaselineTIFFTagSet.TAG_JPEG_INTERCHANGE_FORMAT_LENGTH) {
            this.stripOrTileByteCountsPosition = stream.getStreamPosition();
            if (LAZY_LOADING) {
                type = type == TIFFTag.TIFF_LONG ? TIFFTag.TIFF_LAZY_LONG : TIFFTag.TIFF_LAZY_LONG8;
            }
        } else if (tag == BaselineTIFFTagSet.TAG_STRIP_OFFSETS || tag == BaselineTIFFTagSet.TAG_TILE_OFFSETS || tag == BaselineTIFFTagSet.TAG_JPEG_INTERCHANGE_FORMAT) {
            this.stripOrTileOffsetsPosition = stream.getStreamPosition();
            if (LAZY_LOADING) {
                type = type == TIFFTag.TIFF_LONG ? TIFFTag.TIFF_LAZY_LONG : TIFFTag.TIFF_LAZY_LONG8;
            }
        }
        Object obj = null;
        try {
            switch(type) {
                case TIFFTag.TIFF_BYTE:
                case TIFFTag.TIFF_SBYTE:
                case TIFFTag.TIFF_UNDEFINED:
                case TIFFTag.TIFF_ASCII:
                    byte[] bvalues = new byte[count];
                    stream.readFully(bvalues, 0, count);
                    if (type == TIFFTag.TIFF_ASCII) {
                        // Can be multiple strings
                        final List<String> v = new ArrayList<String>();
                        boolean inString = false;
                        int prevIndex = 0;
                        for (int index = 0; index <= count; index++) {
                            if (index < count && bvalues[index] != 0) {
                                if (!inString) {
                                    // start of string
                                    prevIndex = index;
                                    inString = true;
                                }
                            } else {
                                // null or special case at end of string
                                if (inString) {
                                    // end of string
                                    final String s = new String(bvalues, prevIndex, index - prevIndex);
                                    v.add(s);
                                    inString = false;
                                }
                            }
                        }
                        count = v.size();
                        String[] strings;
                        if (count != 0) {
                            strings = new String[count];
                            for (int c = 0; c < count; c++) {
                                strings[c] = v.get(c);
                            }
                        } else {
                            // This case has been observed when the value of
                            // 'count' recorded in the field is non-zero but
                            // the value portion contains all nulls.
                            count = 1;
                            strings = new String[] { "" };
                        }
                        obj = strings;
                    } else {
                        obj = bvalues;
                    }
                    break;
                case TIFFTag.TIFF_SHORT:
                    char[] cvalues = new char[count];
                    for (int j = 0; j < count; j++) {
                        cvalues[j] = (char) (stream.readUnsignedShort());
                    }
                    obj = cvalues;
                    break;
                case TIFFTag.TIFF_LONG:
                case TIFFTag.TIFF_IFD_POINTER:
                    long[] lvalues = new long[count];
                    for (int j = 0; j < count; j++) {
                        lvalues[j] = stream.readUnsignedInt();
                    }
                    obj = lvalues;
                    break;
                case TIFFTag.TIFF_RATIONAL:
                    long[][] llvalues = new long[count][2];
                    for (int j = 0; j < count; j++) {
                        llvalues[j][0] = stream.readUnsignedInt();
                        llvalues[j][1] = stream.readUnsignedInt();
                    }
                    obj = llvalues;
                    break;
                case TIFFTag.TIFF_SSHORT:
                    short[] svalues = new short[count];
                    for (int j = 0; j < count; j++) {
                        svalues[j] = stream.readShort();
                    }
                    obj = svalues;
                    break;
                case TIFFTag.TIFF_SLONG:
                    int[] ivalues = new int[count];
                    for (int j = 0; j < count; j++) {
                        ivalues[j] = stream.readInt();
                    }
                    obj = ivalues;
                    break;
                case TIFFTag.TIFF_SRATIONAL:
                    int[][] iivalues = new int[count][2];
                    for (int j = 0; j < count; j++) {
                        iivalues[j][0] = stream.readInt();
                        iivalues[j][1] = stream.readInt();
                    }
                    obj = iivalues;
                    break;
                case TIFFTag.TIFF_FLOAT:
                    float[] fvalues = new float[count];
                    for (int j = 0; j < count; j++) {
                        fvalues[j] = stream.readFloat();
                    }
                    obj = fvalues;
                    break;
                case TIFFTag.TIFF_DOUBLE:
                    double[] dvalues = new double[count];
                    for (int j = 0; j < count; j++) {
                        dvalues[j] = stream.readDouble();
                    }
                    obj = dvalues;
                    break;
                case TIFFTag.TIFF_LONG8:
                case TIFFTag.TIFF_SLONG8:
                case TIFFTag.TIFF_IFD8:
                    long[] lBvalues = new long[count];
                    for (int j = 0; j < count; j++) {
                        lBvalues[j] = stream.readLong();
                    }
                    obj = lBvalues;
                    break;
                case TIFFTag.TIFF_LAZY_LONG8:
                case TIFFTag.TIFF_LAZY_LONG:
                    obj = new TIFFLazyData(stream, type, count);
                    break;
                default:
                    // XXX Warning
                    break;
            }
        } catch (EOFException eofe) {
            // field.
            if (BaselineTIFFTagSet.getInstance().getTag(tag) == null) {
                throw eofe;
            }
        }
        if (tiffTag == null) {
        // XXX Warning: unknown tag
        } else if (!tiffTag.isDataTypeOK(type)) {
        // XXX Warning: bad data type
        } else if (tiffTag.isIFDPointer() && obj != null) {
            stream.mark();
            stream.seek(((long[]) obj)[0]);
            List tagSets = new ArrayList(1);
            tagSets.add(tiffTag.getTagSet());
            TIFFIFD subIFD = new TIFFIFD(tagSets);
            // XXX Use same ignore policy for sub-IFD fields?
            subIFD.initialize(stream, ignoreUnknownFields);
            obj = subIFD;
            stream.reset();
        }
        if (tiffTag == null) {
            tiffTag = new TIFFTag(null, tag, 1 << type, null);
        }
        // will not be the case if an EOF was ignored above.
        if (obj != null) {
            TIFFField f = new TIFFField(tiffTag, type, count, obj);
            addTIFFField(f);
        }
        stream.seek(nextTagOffset);
    }
    this.lastPosition = stream.getStreamPosition();
}
Also used : ArrayList(java.util.ArrayList) EOFException(java.io.EOFException) TIFFField(it.geosolutions.imageio.plugins.tiff.TIFFField) ArrayList(java.util.ArrayList) List(java.util.List) TIFFTag(it.geosolutions.imageio.plugins.tiff.TIFFTag)

Example 8 with TIFFTag

use of it.geosolutions.imageio.plugins.tiff.TIFFTag in project imageio-ext by geosolutions-it.

the class TIFFIFD method writeToStream.

public void writeToStream(ImageOutputStream stream, final boolean isBTIFF) throws IOException {
    long nextSpace;
    if (!isBTIFF) {
        int numFields = getNumTIFFFields();
        stream.writeShort(numFields);
        nextSpace = stream.getStreamPosition() + 12 * numFields + 4;
    } else {
        long numFields = getNumTIFFFields();
        stream.writeLong(numFields);
        nextSpace = stream.getStreamPosition() + 20 * numFields + 8;
    }
    Iterator iter = iterator();
    while (iter.hasNext()) {
        TIFFField f = (TIFFField) iter.next();
        TIFFTag tag = f.getTag();
        int type = f.getType();
        int count = f.getCount();
        // Hack to deal with unknown tags
        if (type == 0) {
            type = TIFFTag.TIFF_UNDEFINED;
        }
        int size = count * TIFFTag.getSizeOfType(type);
        if (type == TIFFTag.TIFF_ASCII) {
            int chars = 0;
            for (int i = 0; i < count; i++) {
                chars += f.getAsString(i).length() + 1;
            }
            count = chars;
            size = count;
        }
        int tagNumber = f.getTagNumber();
        stream.writeShort(tagNumber);
        stream.writeShort(type);
        if (isBTIFF) {
            stream.writeLong(count);
            stream.writeLong(0);
            // Mark beginning of next field
            stream.mark();
            stream.skipBytes(-8);
        } else {
            stream.writeInt(count);
            stream.writeInt(0);
            // Mark beginning of next field
            stream.mark();
            stream.skipBytes(-4);
        }
        long pos;
        if (!isBTIFF) {
            if (size > 4 || tag.isIFDPointer()) {
                // Ensure IFD or value is written on a word boundary
                nextSpace = (nextSpace + 3) & ~0x3;
                stream.writeInt((int) nextSpace);
                stream.seek(nextSpace);
                pos = nextSpace;
                if (tag.isIFDPointer()) {
                    TIFFIFD subIFD = (TIFFIFD) f.getData();
                    subIFD.writeToStream(stream, isBTIFF);
                    nextSpace = subIFD.lastPosition;
                } else {
                    writeTIFFFieldToStream(f, stream);
                    nextSpace = stream.getStreamPosition();
                }
            } else {
                pos = stream.getStreamPosition();
                writeTIFFFieldToStream(f, stream);
            }
        } else {
            if (size > 8 || tag.isIFDPointer()) {
                // Ensure IFD or value is written on a Long boundary
                nextSpace = (nextSpace + 7) & ~0x7;
                stream.writeLong(nextSpace);
                stream.seek(nextSpace);
                pos = nextSpace;
                if (tag.isIFDPointer()) {
                    TIFFIFD subIFD = (TIFFIFD) f.getData();
                    subIFD.writeToStream(stream, isBTIFF);
                    nextSpace = subIFD.lastPosition;
                } else {
                    writeTIFFFieldToStream(f, stream);
                    nextSpace = stream.getStreamPosition();
                }
            } else {
                pos = stream.getStreamPosition();
                writeTIFFFieldToStream(f, stream);
            }
        }
        // position for backpatching
        if (tagNumber == BaselineTIFFTagSet.TAG_STRIP_BYTE_COUNTS || tagNumber == BaselineTIFFTagSet.TAG_TILE_BYTE_COUNTS || tagNumber == BaselineTIFFTagSet.TAG_JPEG_INTERCHANGE_FORMAT_LENGTH) {
            this.stripOrTileByteCountsPosition = pos;
        } else if (tagNumber == BaselineTIFFTagSet.TAG_STRIP_OFFSETS || tagNumber == BaselineTIFFTagSet.TAG_TILE_OFFSETS || tagNumber == BaselineTIFFTagSet.TAG_JPEG_INTERCHANGE_FORMAT) {
            this.stripOrTileOffsetsPosition = pos;
        }
        // Go to marked position of next field
        stream.reset();
    }
    this.lastPosition = nextSpace;
}
Also used : Iterator(java.util.Iterator) TIFFField(it.geosolutions.imageio.plugins.tiff.TIFFField) TIFFTag(it.geosolutions.imageio.plugins.tiff.TIFFTag)

Example 9 with TIFFTag

use of it.geosolutions.imageio.plugins.tiff.TIFFTag in project imageio-ext by geosolutions-it.

the class TIFFIFD method getTag.

public static TIFFTag getTag(String tagName, List tagSets) {
    Iterator iter = tagSets.iterator();
    while (iter.hasNext()) {
        TIFFTagSet tagSet = (TIFFTagSet) iter.next();
        TIFFTag tag = tagSet.getTag(tagName);
        if (tag != null) {
            return tag;
        }
    }
    return null;
}
Also used : Iterator(java.util.Iterator) BaselineTIFFTagSet(it.geosolutions.imageio.plugins.tiff.BaselineTIFFTagSet) TIFFTagSet(it.geosolutions.imageio.plugins.tiff.TIFFTagSet) TIFFTag(it.geosolutions.imageio.plugins.tiff.TIFFTag)

Example 10 with TIFFTag

use of it.geosolutions.imageio.plugins.tiff.TIFFTag in project imageio-ext by geosolutions-it.

the class TIFFFieldNode method initialize.

private synchronized void initialize() {
    if (isInitialized == Boolean.TRUE)
        return;
    if (isIFD) {
        TIFFDirectory dir = (TIFFDirectory) field.getData();
        TIFFField[] fields = dir.getTIFFFields();
        if (fields != null) {
            TIFFTagSet[] tagSets = dir.getTagSets();
            List tagSetList = Arrays.asList(tagSets);
            int numFields = fields.length;
            for (int i = 0; i < numFields; i++) {
                TIFFField f = fields[i];
                int tagNumber = f.getTagNumber();
                TIFFTag tag = TIFFIFD.getTag(tagNumber, tagSetList);
                Node node = f.getAsNativeNode();
                if (node != null) {
                    appendChild(node);
                }
            }
        }
    } else {
        IIOMetadataNode child;
        int count = field.getCount();
        if (field.getType() == TIFFTag.TIFF_UNDEFINED) {
            child = new IIOMetadataNode("TIFFUndefined");
            byte[] data = field.getAsBytes();
            StringBuilder sb = new StringBuilder();
            for (int i = 0; i < count; i++) {
                sb.append(Integer.toString(data[i] & 0xff));
                if (i < count - 1) {
                    sb.append(",");
                }
            }
            child.setAttribute("value", sb.toString());
        } else {
            child = new IIOMetadataNode("TIFF" + field.getTypeName(field.getType()) + "s");
            TIFFTag tag = field.getTag();
            String tName = tag.getName();
            boolean proceed = true;
            if (EXCLUDE_ATTRIBUTES && tName != null && ATTRIBUTES_EXCLUSION_SET.contains(tName)) {
                proceed = false;
            }
            for (int i = 0; i < count && proceed; i++) {
                IIOMetadataNode cchild = new IIOMetadataNode("TIFF" + field.getTypeName(field.getType()));
                cchild.setAttribute("value", field.getValueAsString(i));
                if (tag.hasValueNames() && field.isIntegral()) {
                    int value = field.getAsInt(i);
                    String name = tag.getValueName(value);
                    if (name != null) {
                        cchild.setAttribute("description", name);
                    }
                }
                child.appendChild(cchild);
            }
        }
        appendChild(child);
    }
    isInitialized = Boolean.TRUE;
}
Also used : Node(org.w3c.dom.Node) IIOMetadataNode(javax.imageio.metadata.IIOMetadataNode) TIFFDirectory(it.geosolutions.imageio.plugins.tiff.TIFFDirectory) TIFFField(it.geosolutions.imageio.plugins.tiff.TIFFField) List(java.util.List) TIFFTagSet(it.geosolutions.imageio.plugins.tiff.TIFFTagSet) TIFFTag(it.geosolutions.imageio.plugins.tiff.TIFFTag) IIOMetadataNode(javax.imageio.metadata.IIOMetadataNode)

Aggregations

TIFFTag (it.geosolutions.imageio.plugins.tiff.TIFFTag)10 TIFFField (it.geosolutions.imageio.plugins.tiff.TIFFField)7 TIFFTagSet (it.geosolutions.imageio.plugins.tiff.TIFFTagSet)6 Iterator (java.util.Iterator)6 BaselineTIFFTagSet (it.geosolutions.imageio.plugins.tiff.BaselineTIFFTagSet)5 List (java.util.List)5 ArrayList (java.util.ArrayList)4 IIOMetadataNode (javax.imageio.metadata.IIOMetadataNode)4 Node (org.w3c.dom.Node)4 EXIFParentTIFFTagSet (it.geosolutions.imageio.plugins.tiff.EXIFParentTIFFTagSet)3 NodeList (org.w3c.dom.NodeList)3 StringTokenizer (java.util.StringTokenizer)2 EXIFTIFFTagSet (it.geosolutions.imageio.plugins.tiff.EXIFTIFFTagSet)1 TIFFDirectory (it.geosolutions.imageio.plugins.tiff.TIFFDirectory)1 TIFFImageWriteParam (it.geosolutions.imageio.plugins.tiff.TIFFImageWriteParam)1 TIFFFieldNode (it.geosolutions.imageioimpl.plugins.tiff.TIFFFieldNode)1 Point (java.awt.Point)1 ICC_ColorSpace (java.awt.color.ICC_ColorSpace)1 IndexColorModel (java.awt.image.IndexColorModel)1 EOFException (java.io.EOFException)1