FileDocCategorySizeDatePackage
ExifTag.javaAPI DocAndroid 5.1 API35109Thu Mar 12 22:22:42 GMT 2015com.android.gallery3d.exif

ExifTag

public class ExifTag extends Object
This class stores information of an EXIF tag. For more information about defined EXIF tags, please read the Jeita EXIF 2.2 standard. Tags should be instantiated using {@link ExifInterface#buildTag}.
see
ExifInterface

Fields Summary
public static final short
TYPE_UNSIGNED_BYTE
The BYTE type in the EXIF standard. An 8-bit unsigned integer.
public static final short
TYPE_ASCII
The ASCII type in the EXIF standard. An 8-bit byte containing one 7-bit ASCII code. The final byte is terminated with NULL.
public static final short
TYPE_UNSIGNED_SHORT
The SHORT type in the EXIF standard. A 16-bit (2-byte) unsigned integer
public static final short
TYPE_UNSIGNED_LONG
The LONG type in the EXIF standard. A 32-bit (4-byte) unsigned integer
public static final short
TYPE_UNSIGNED_RATIONAL
The RATIONAL type of EXIF standard. It consists of two LONGs. The first one is the numerator and the second one expresses the denominator.
public static final short
TYPE_UNDEFINED
The UNDEFINED type in the EXIF standard. An 8-bit byte that can take any value depending on the field definition.
public static final short
TYPE_LONG
The SLONG type in the EXIF standard. A 32-bit (4-byte) signed integer (2's complement notation).
public static final short
TYPE_RATIONAL
The SRATIONAL type of EXIF standard. It consists of two SLONGs. The first one is the numerator and the second one is the denominator.
private static Charset
US_ASCII
private static final int[]
TYPE_TO_SIZE_MAP
private static final int
UNSIGNED_SHORT_MAX
private static final long
UNSIGNED_LONG_MAX
private static final long
LONG_MAX
private static final long
LONG_MIN
static final int
SIZE_UNDEFINED
private final short
mTagId
private final short
mDataType
private boolean
mHasDefinedDefaultComponentCount
private int
mComponentCountActual
private int
mIfd
private Object
mValue
private int
mOffset
private static final SimpleDateFormat
TIME_FORMAT
Constructors Summary
ExifTag(short tagId, short type, int componentCount, int ifd, boolean hasDefinedComponentCount)

        mTagId = tagId;
        mDataType = type;
        mComponentCountActual = componentCount;
        mHasDefinedDefaultComponentCount = hasDefinedComponentCount;
        mIfd = ifd;
        mValue = null;
    
Methods Summary
private booleancheckBadComponentCount(int count)

        if (mHasDefinedDefaultComponentCount && (mComponentCountActual != count)) {
            return true;
        }
        return false;
    
private booleancheckOverflowForRational(Rational[] value)

        for (Rational v : value) {
            if (v.getNumerator() < LONG_MIN || v.getDenominator() < LONG_MIN
                    || v.getNumerator() > LONG_MAX
                    || v.getDenominator() > LONG_MAX) {
                return true;
            }
        }
        return false;
    
private booleancheckOverflowForUnsignedLong(long[] value)

        for (long v : value) {
            if (v < 0 || v > UNSIGNED_LONG_MAX) {
                return true;
            }
        }
        return false;
    
private booleancheckOverflowForUnsignedLong(int[] value)

        for (int v : value) {
            if (v < 0) {
                return true;
            }
        }
        return false;
    
private booleancheckOverflowForUnsignedRational(Rational[] value)

        for (Rational v : value) {
            if (v.getNumerator() < 0 || v.getDenominator() < 0
                    || v.getNumerator() > UNSIGNED_LONG_MAX
                    || v.getDenominator() > UNSIGNED_LONG_MAX) {
                return true;
            }
        }
        return false;
    
private booleancheckOverflowForUnsignedShort(int[] value)

        for (int v : value) {
            if (v > UNSIGNED_SHORT_MAX || v < 0) {
                return true;
            }
        }
        return false;
    
private static java.lang.StringconvertTypeToString(short type)

        switch (type) {
            case TYPE_UNSIGNED_BYTE:
                return "UNSIGNED_BYTE";
            case TYPE_ASCII:
                return "ASCII";
            case TYPE_UNSIGNED_SHORT:
                return "UNSIGNED_SHORT";
            case TYPE_UNSIGNED_LONG:
                return "UNSIGNED_LONG";
            case TYPE_UNSIGNED_RATIONAL:
                return "UNSIGNED_RATIONAL";
            case TYPE_UNDEFINED:
                return "UNDEFINED";
            case TYPE_LONG:
                return "LONG";
            case TYPE_RATIONAL:
                return "RATIONAL";
            default:
                return "";
        }
    
public booleanequals(java.lang.Object obj)

        if (obj == null) {
            return false;
        }
        if (obj instanceof ExifTag) {
            ExifTag tag = (ExifTag) obj;
            if (tag.mTagId != this.mTagId
                    || tag.mComponentCountActual != this.mComponentCountActual
                    || tag.mDataType != this.mDataType) {
                return false;
            }
            if (mValue != null) {
                if (tag.mValue == null) {
                    return false;
                } else if (mValue instanceof long[]) {
                    if (!(tag.mValue instanceof long[])) {
                        return false;
                    }
                    return Arrays.equals((long[]) mValue, (long[]) tag.mValue);
                } else if (mValue instanceof Rational[]) {
                    if (!(tag.mValue instanceof Rational[])) {
                        return false;
                    }
                    return Arrays.equals((Rational[]) mValue, (Rational[]) tag.mValue);
                } else if (mValue instanceof byte[]) {
                    if (!(tag.mValue instanceof byte[])) {
                        return false;
                    }
                    return Arrays.equals((byte[]) mValue, (byte[]) tag.mValue);
                } else {
                    return mValue.equals(tag.mValue);
                }
            } else {
                return tag.mValue == null;
            }
        }
        return false;
    
public longforceGetValueAsLong(long defaultValue)
Gets a long representation of the value.

param
defaultValue value to return if there is no value or value is a rational with a denominator of 0.
return
the tag's value as a long, or defaultValue if no representation exists.

        long[] l = getValueAsLongs();
        if (l != null && l.length >= 1) {
            return l[0];
        }
        byte[] b = getValueAsBytes();
        if (b != null && b.length >= 1) {
            return b[0];
        }
        Rational[] r = getValueAsRationals();
        if (r != null && r.length >= 1 && r[0].getDenominator() != 0) {
            return (long) r[0].toDouble();
        }
        return defaultValue;
    
public java.lang.StringforceGetValueAsString()
Gets a string representation of the value.

        if (mValue == null) {
            return "";
        } else if (mValue instanceof byte[]) {
            if (mDataType == TYPE_ASCII) {
                return new String((byte[]) mValue, US_ASCII);
            } else {
                return Arrays.toString((byte[]) mValue);
            }
        } else if (mValue instanceof long[]) {
            if (((long[]) mValue).length == 1) {
                return String.valueOf(((long[]) mValue)[0]);
            } else {
                return Arrays.toString((long[]) mValue);
            }
        } else if (mValue instanceof Object[]) {
            if (((Object[]) mValue).length == 1) {
                Object val = ((Object[]) mValue)[0];
                if (val == null) {
                    return "";
                } else {
                    return val.toString();
                }
            } else {
                return Arrays.toString((Object[]) mValue);
            }
        } else {
            return mValue.toString();
        }
    
protected voidforceSetComponentCount(int count)
Sets the component count of this tag. Call this function before setValue() if the length of value does not match the component count.

        mComponentCountActual = count;
    
protected voidgetBytes(byte[] buf)
Equivalent to getBytes(buffer, 0, buffer.length).

        getBytes(buf, 0, buf.length);
    
protected voidgetBytes(byte[] buf, int offset, int length)
Gets the {@link #TYPE_UNDEFINED} or {@link #TYPE_UNSIGNED_BYTE} data.

param
buf the byte array in which to store the bytes read.
param
offset the initial position in buffer to store the bytes.
param
length the maximum number of bytes to store in buffer. If length > component count, only the valid bytes will be stored.
exception
IllegalArgumentException If the type is NOT {@link #TYPE_UNDEFINED} or {@link #TYPE_UNSIGNED_BYTE}.

        if ((mDataType != TYPE_UNDEFINED) && (mDataType != TYPE_UNSIGNED_BYTE)) {
            throw new IllegalArgumentException("Cannot get BYTE value from "
                    + convertTypeToString(mDataType));
        }
        System.arraycopy(mValue, 0, buf, offset,
                (length > mComponentCountActual) ? mComponentCountActual : length);
    
public intgetComponentCount()
Gets the component count of this tag.

        return mComponentCountActual;
    
public intgetDataSize()
Gets the total data size in bytes of the value of this tag.

        return getComponentCount() * getElementSize(getDataType());
    
public shortgetDataType()
Gets the data type of this tag

see
#TYPE_ASCII
see
#TYPE_LONG
see
#TYPE_RATIONAL
see
#TYPE_UNDEFINED
see
#TYPE_UNSIGNED_BYTE
see
#TYPE_UNSIGNED_LONG
see
#TYPE_UNSIGNED_RATIONAL
see
#TYPE_UNSIGNED_SHORT

        return mDataType;
    
public static intgetElementSize(short type)
Gets the element size of the given data type in bytes.

see
#TYPE_ASCII
see
#TYPE_LONG
see
#TYPE_RATIONAL
see
#TYPE_UNDEFINED
see
#TYPE_UNSIGNED_BYTE
see
#TYPE_UNSIGNED_LONG
see
#TYPE_UNSIGNED_RATIONAL
see
#TYPE_UNSIGNED_SHORT

        return TYPE_TO_SIZE_MAP[type];
    
public intgetIfd()
Returns the ID of the IFD this tag belongs to.

see
IfdId#TYPE_IFD_0
see
IfdId#TYPE_IFD_1
see
IfdId#TYPE_IFD_EXIF
see
IfdId#TYPE_IFD_GPS
see
IfdId#TYPE_IFD_INTEROPERABILITY

        return mIfd;
    
protected intgetOffset()
Gets the offset of this tag. This is only valid if this data size > 4 and contains an offset to the location of the actual value.

        return mOffset;
    
protected RationalgetRational(int index)
Gets the {@link #TYPE_RATIONAL} or {@link #TYPE_UNSIGNED_RATIONAL} data.

exception
IllegalArgumentException If the type is NOT {@link #TYPE_RATIONAL} or {@link #TYPE_UNSIGNED_RATIONAL}.

        if ((mDataType != TYPE_RATIONAL) && (mDataType != TYPE_UNSIGNED_RATIONAL)) {
            throw new IllegalArgumentException("Cannot get RATIONAL value from "
                    + convertTypeToString(mDataType));
        }
        return ((Rational[]) mValue)[index];
    
protected java.lang.StringgetString()
Gets the {@link #TYPE_ASCII} data.

exception
IllegalArgumentException If the type is NOT {@link #TYPE_ASCII}.

        if (mDataType != TYPE_ASCII) {
            throw new IllegalArgumentException("Cannot get ASCII value from "
                    + convertTypeToString(mDataType));
        }
        return new String((byte[]) mValue, US_ASCII);
    
protected byte[]getStringByte()

        return (byte[]) mValue;
    
public shortgetTagId()
Gets the TID of this tag.

        return mTagId;
    
public java.lang.ObjectgetValue()
Gets the tag's value or null if none exists.

        return mValue;
    
public bytegetValueAsByte(byte defaultValue)
Gets the value as a byte. If there are more than 1 bytes in this value, gets the first byte. This method should be used for tags of type {@link #TYPE_UNDEFINED} or {@link #TYPE_UNSIGNED_BYTE}.

param
defaultValue the byte to return if tag's value does not exist or cannot be converted to a byte.
return
the tag's value as a byte, or the defaultValue.

        byte[] b = getValueAsBytes();
        if (b == null || b.length < 1) {
            return defaultValue;
        }
        return b[0];
    
public byte[]getValueAsBytes()
Gets the value as a byte array. This method should be used for tags of type {@link #TYPE_UNDEFINED} or {@link #TYPE_UNSIGNED_BYTE}.

return
the value as a byte array, or null if the tag's value does not exist or cannot be converted to a byte array.

        if (mValue instanceof byte[]) {
            return (byte[]) mValue;
        }
        return null;
    
public intgetValueAsInt(int defaultValue)
Gets the value as an int. If there are more than 1 ints in this value, gets the first one. This method should be used for tags of type {@link #TYPE_UNSIGNED_SHORT}, {@link #TYPE_UNSIGNED_LONG}.

param
defaultValue the int to return if tag's value does not exist or cannot be converted to an int.
return
the tag's value as a int, or the defaultValue.

        int[] i = getValueAsInts();
        if (i == null || i.length < 1) {
            return defaultValue;
        }
        return i[0];
    
public int[]getValueAsInts()
Gets the value as an array of ints. This method should be used for tags of type {@link #TYPE_UNSIGNED_SHORT}, {@link #TYPE_UNSIGNED_LONG}.

return
the value as as an array of ints, or null if the tag's value does not exist or cannot be converted to an array of ints.

        if (mValue == null) {
            return null;
        } else if (mValue instanceof long[]) {
            long[] val = (long[]) mValue;
            int[] arr = new int[val.length];
            for (int i = 0; i < val.length; i++) {
                arr[i] = (int) val[i]; // Truncates
            }
            return arr;
        }
        return null;
    
public longgetValueAsLong(long defaultValue)
Gets the value or null if none exists. If there are more than 1 longs in this value, gets the first one. This method should be used for tags of type {@link #TYPE_UNSIGNED_LONG}.

param
defaultValue the long to return if tag's value does not exist or cannot be converted to a long.
return
the tag's value as a long, or the defaultValue.

        long[] l = getValueAsLongs();
        if (l == null || l.length < 1) {
            return defaultValue;
        }
        return l[0];
    
public long[]getValueAsLongs()
Gets the value as an array of longs. This method should be used for tags of type {@link #TYPE_UNSIGNED_LONG}.

return
the value as as an array of longs, or null if the tag's value does not exist or cannot be converted to an array of longs.

        if (mValue instanceof long[]) {
            return (long[]) mValue;
        }
        return null;
    
public RationalgetValueAsRational(Rational defaultValue)
Gets the value as a Rational. If there are more than 1 Rationals in this value, gets the first one. This method should be used for tags of type {@link #TYPE_RATIONAL} or {@link #TYPE_UNSIGNED_RATIONAL}.

param
defaultValue the Rational to return if tag's value does not exist or cannot be converted to a Rational.
return
the tag's value as a Rational, or the defaultValue.

        Rational[] r = getValueAsRationals();
        if (r == null || r.length < 1) {
            return defaultValue;
        }
        return r[0];
    
public RationalgetValueAsRational(long defaultValue)
Gets the value as a Rational. If there are more than 1 Rationals in this value, gets the first one. This method should be used for tags of type {@link #TYPE_RATIONAL} or {@link #TYPE_UNSIGNED_RATIONAL}.

param
defaultValue the numerator of the Rational to return if tag's value does not exist or cannot be converted to a Rational (the denominator will be 1).
return
the tag's value as a Rational, or the defaultValue.

        Rational defaultVal = new Rational(defaultValue, 1);
        return getValueAsRational(defaultVal);
    
public Rational[]getValueAsRationals()
Gets the value as an array of Rationals. This method should be used for tags of type {@link #TYPE_RATIONAL} or {@link #TYPE_UNSIGNED_RATIONAL}.

return
the value as as an array of Rationals, or null if the tag's value does not exist or cannot be converted to an array of Rationals.

        if (mValue instanceof Rational[]) {
            return (Rational[]) mValue;
        }
        return null;
    
public java.lang.StringgetValueAsString()
Gets the value as a String. This method should be used for tags of type {@link #TYPE_ASCII}.

return
the value as a String, or null if the tag's value does not exist or cannot be converted to a String.

        if (mValue == null) {
            return null;
        } else if (mValue instanceof String) {
            return (String) mValue;
        } else if (mValue instanceof byte[]) {
            return new String((byte[]) mValue, US_ASCII);
        }
        return null;
    
public java.lang.StringgetValueAsString(java.lang.String defaultValue)
Gets the value as a String. This method should be used for tags of type {@link #TYPE_ASCII}.

param
defaultValue the String to return if the tag's value does not exist or cannot be converted to a String.
return
the tag's value as a String, or the defaultValue.

        String s = getValueAsString();
        if (s == null) {
            return defaultValue;
        }
        return s;
    
protected longgetValueAt(int index)
Gets the value for type {@link #TYPE_ASCII}, {@link #TYPE_LONG}, {@link #TYPE_UNDEFINED}, {@link #TYPE_UNSIGNED_BYTE}, {@link #TYPE_UNSIGNED_LONG}, or {@link #TYPE_UNSIGNED_SHORT}. For {@link #TYPE_RATIONAL} or {@link #TYPE_UNSIGNED_RATIONAL}, call {@link #getRational(int)} instead.

exception
IllegalArgumentException if the data type is {@link #TYPE_RATIONAL} or {@link #TYPE_UNSIGNED_RATIONAL}.

        if (mValue instanceof long[]) {
            return ((long[]) mValue)[index];
        } else if (mValue instanceof byte[]) {
            return ((byte[]) mValue)[index];
        }
        throw new IllegalArgumentException("Cannot get integer value from "
                + convertTypeToString(mDataType));
    
protected booleanhasDefinedCount()

        return mHasDefinedDefaultComponentCount;
    
public booleanhasValue()
Returns true if this ExifTag contains value; otherwise, this tag will contain an offset value that is determined when the tag is written.

        return mValue != null;
    
public static booleanisValidIfd(int ifdId)
Returns true if the given IFD is a valid IFD.


                   
         
        return ifdId == IfdId.TYPE_IFD_0 || ifdId == IfdId.TYPE_IFD_1
                || ifdId == IfdId.TYPE_IFD_EXIF || ifdId == IfdId.TYPE_IFD_INTEROPERABILITY
                || ifdId == IfdId.TYPE_IFD_GPS;
    
public static booleanisValidType(short type)
Returns true if a given type is a valid tag type.

        return type == TYPE_UNSIGNED_BYTE || type == TYPE_ASCII ||
                type == TYPE_UNSIGNED_SHORT || type == TYPE_UNSIGNED_LONG ||
                type == TYPE_UNSIGNED_RATIONAL || type == TYPE_UNDEFINED ||
                type == TYPE_LONG || type == TYPE_RATIONAL;
    
protected voidsetHasDefinedCount(boolean d)

        mHasDefinedDefaultComponentCount = d;
    
protected voidsetIfd(int ifdId)

        mIfd = ifdId;
    
protected voidsetOffset(int offset)
Sets the offset of this tag.

        mOffset = offset;
    
public booleansetTimeValue(long time)
Sets a timestamp to this tag. The method converts the timestamp with the format of "yyyy:MM:dd kk:mm:ss" and calls {@link #setValue(String)}. This method will fail if the data type is not {@link #TYPE_ASCII} or the component count of this tag is not 20 or undefined.

param
time the number of milliseconds since Jan. 1, 1970 GMT
return
true on success

        // synchronized on TIME_FORMAT as SimpleDateFormat is not thread safe
        synchronized (TIME_FORMAT) {
            return setValue(TIME_FORMAT.format(new Date(time)));
        }
    
public booleansetValue(int[] value)
Sets integer values into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_SHORT}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_SHORT}, {@link #TYPE_UNSIGNED_LONG}, or {@link #TYPE_LONG}.
  • The value overflows.
  • The value.length does NOT match the component count in the definition for this tag.

        if (checkBadComponentCount(value.length)) {
            return false;
        }
        if (mDataType != TYPE_UNSIGNED_SHORT && mDataType != TYPE_LONG &&
                mDataType != TYPE_UNSIGNED_LONG) {
            return false;
        }
        if (mDataType == TYPE_UNSIGNED_SHORT && checkOverflowForUnsignedShort(value)) {
            return false;
        } else if (mDataType == TYPE_UNSIGNED_LONG && checkOverflowForUnsignedLong(value)) {
            return false;
        }

        long[] data = new long[value.length];
        for (int i = 0; i < value.length; i++) {
            data[i] = value[i];
        }
        mValue = data;
        mComponentCountActual = value.length;
        return true;
    
public booleansetValue(int value)
Sets integer value into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_SHORT}, or {@link #TYPE_LONG}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_SHORT}, {@link #TYPE_UNSIGNED_LONG}, or {@link #TYPE_LONG}.
  • The value overflows.
  • The component count in the definition of this tag is not 1.

        return setValue(new int[] {
                value
        });
    
public booleansetValue(long[] value)
Sets long values into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_LONG}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_LONG}.
  • The value overflows.
  • The value.length does NOT match the component count in the definition for this tag.

        if (checkBadComponentCount(value.length) || mDataType != TYPE_UNSIGNED_LONG) {
            return false;
        }
        if (checkOverflowForUnsignedLong(value)) {
            return false;
        }
        mValue = value;
        mComponentCountActual = value.length;
        return true;
    
public booleansetValue(long value)
Sets long values into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_LONG}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_LONG}.
  • The value overflows.
  • The component count in the definition for this tag is not 1.

        return setValue(new long[] {
                value
        });
    
public booleansetValue(java.lang.String value)
Sets a string value into this tag. This method should be used for tags of type {@link #TYPE_ASCII}. The string is converted to an ASCII string. Characters that cannot be converted are replaced with '?'. The length of the string must be equal to either (component count -1) or (component count). The final byte will be set to the string null terminator '\0', overwriting the last character in the string if the value.length is equal to the component count. This method will fail if:
  • The data type is not {@link #TYPE_ASCII} or {@link #TYPE_UNDEFINED}.
  • The length of the string is not equal to (component count -1) or (component count) in the definition for this tag.

        if (mDataType != TYPE_ASCII && mDataType != TYPE_UNDEFINED) {
            return false;
        }

        byte[] buf = value.getBytes(US_ASCII);
        byte[] finalBuf = buf;
        if (buf.length > 0) {
            finalBuf = (buf[buf.length - 1] == 0 || mDataType == TYPE_UNDEFINED) ? buf : Arrays
                .copyOf(buf, buf.length + 1);
        } else if (mDataType == TYPE_ASCII && mComponentCountActual == 1) {
            finalBuf = new byte[] { 0 };
        }
        int count = finalBuf.length;
        if (checkBadComponentCount(count)) {
            return false;
        }
        mComponentCountActual = count;
        mValue = finalBuf;
        return true;
    
public booleansetValue(Rational[] value)
Sets Rational values into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_RATIONAL}, or {@link #TYPE_RATIONAL}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_RATIONAL} or {@link #TYPE_RATIONAL}.
  • The value overflows.
  • The value.length does NOT match the component count in the definition for this tag.

see
Rational

        if (checkBadComponentCount(value.length)) {
            return false;
        }
        if (mDataType != TYPE_UNSIGNED_RATIONAL && mDataType != TYPE_RATIONAL) {
            return false;
        }
        if (mDataType == TYPE_UNSIGNED_RATIONAL && checkOverflowForUnsignedRational(value)) {
            return false;
        } else if (mDataType == TYPE_RATIONAL && checkOverflowForRational(value)) {
            return false;
        }

        mValue = value;
        mComponentCountActual = value.length;
        return true;
    
public booleansetValue(Rational value)
Sets a Rational value into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_RATIONAL}, or {@link #TYPE_RATIONAL}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_RATIONAL} or {@link #TYPE_RATIONAL}.
  • The value overflows.
  • The component count in the definition for this tag is not 1.

see
Rational

        return setValue(new Rational[] {
                value
        });
    
public booleansetValue(byte[] value, int offset, int length)
Sets byte values into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_BYTE} or {@link #TYPE_UNDEFINED}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_BYTE} or {@link #TYPE_UNDEFINED} .
  • The length does NOT match the component count in the definition for this tag.

        if (checkBadComponentCount(length)) {
            return false;
        }
        if (mDataType != TYPE_UNSIGNED_BYTE && mDataType != TYPE_UNDEFINED) {
            return false;
        }
        mValue = new byte[length];
        System.arraycopy(value, offset, mValue, 0, length);
        mComponentCountActual = length;
        return true;
    
public booleansetValue(byte[] value)
Equivalent to setValue(value, 0, value.length).

        return setValue(value, 0, value.length);
    
public booleansetValue(byte value)
Sets byte value into this tag. This method should be used for tags of type {@link #TYPE_UNSIGNED_BYTE} or {@link #TYPE_UNDEFINED}. This method will fail if:
  • The component type of this tag is not {@link #TYPE_UNSIGNED_BYTE} or {@link #TYPE_UNDEFINED} .
  • The component count in the definition for this tag is not 1.

        return setValue(new byte[] {
                value
        });
    
public booleansetValue(java.lang.Object obj)
Sets the value for this tag using an appropriate setValue method for the given object. This method will fail if:
  • The corresponding setValue method for the class of the object passed in would fail.
  • There is no obvious way to cast the object passed in into an EXIF tag type.

        if (obj == null) {
            return false;
        } else if (obj instanceof Short) {
            return setValue(((Short) obj).shortValue() & 0x0ffff);
        } else if (obj instanceof String) {
            return setValue((String) obj);
        } else if (obj instanceof int[]) {
            return setValue((int[]) obj);
        } else if (obj instanceof long[]) {
            return setValue((long[]) obj);
        } else if (obj instanceof Rational) {
            return setValue((Rational) obj);
        } else if (obj instanceof Rational[]) {
            return setValue((Rational[]) obj);
        } else if (obj instanceof byte[]) {
            return setValue((byte[]) obj);
        } else if (obj instanceof Integer) {
            return setValue(((Integer) obj).intValue());
        } else if (obj instanceof Long) {
            return setValue(((Long) obj).longValue());
        } else if (obj instanceof Byte) {
            return setValue(((Byte) obj).byteValue());
        } else if (obj instanceof Short[]) {
            // Nulls in this array are treated as zeroes.
            Short[] arr = (Short[]) obj;
            int[] fin = new int[arr.length];
            for (int i = 0; i < arr.length; i++) {
                fin[i] = (arr[i] == null) ? 0 : arr[i].shortValue() & 0x0ffff;
            }
            return setValue(fin);
        } else if (obj instanceof Integer[]) {
            // Nulls in this array are treated as zeroes.
            Integer[] arr = (Integer[]) obj;
            int[] fin = new int[arr.length];
            for (int i = 0; i < arr.length; i++) {
                fin[i] = (arr[i] == null) ? 0 : arr[i].intValue();
            }
            return setValue(fin);
        } else if (obj instanceof Long[]) {
            // Nulls in this array are treated as zeroes.
            Long[] arr = (Long[]) obj;
            long[] fin = new long[arr.length];
            for (int i = 0; i < arr.length; i++) {
                fin[i] = (arr[i] == null) ? 0 : arr[i].longValue();
            }
            return setValue(fin);
        } else if (obj instanceof Byte[]) {
            // Nulls in this array are treated as zeroes.
            Byte[] arr = (Byte[]) obj;
            byte[] fin = new byte[arr.length];
            for (int i = 0; i < arr.length; i++) {
                fin[i] = (arr[i] == null) ? 0 : arr[i].byteValue();
            }
            return setValue(fin);
        } else {
            return false;
        }
    
public java.lang.StringtoString()

        return String.format("tag id: %04X\n", mTagId) + "ifd id: " + mIfd + "\ntype: "
                + convertTypeToString(mDataType) + "\ncount: " + mComponentCountActual
                + "\noffset: " + mOffset + "\nvalue: " + forceGetValueAsString() + "\n";