1 /*
   2  * Copyright (c) 2005, 2015, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 package javax.imageio.plugins.tiff;
  26 
  27 import java.util.StringTokenizer;
  28 import org.w3c.dom.NamedNodeMap;
  29 import org.w3c.dom.Node;
  30 import com.sun.imageio.plugins.tiff.TIFFFieldNode;
  31 import com.sun.imageio.plugins.tiff.TIFFIFD;
  32 
  33 /**
  34  * A class representing a field in a TIFF 6.0 Image File Directory.
  35  *
  36  * <p> A field in a TIFF Image File Directory (IFD) is defined as a
  37  * tag number accompanied by a sequence of values of identical data type.
  38  * TIFF 6.0 defines 12 data types; a 13th type <code>IFD</code> is
  39  * defined in TIFF Tech Note 1 of TIFF Specification Supplement 1. These
  40  * TIFF data types are referred to by Java constants and mapped internally
  41  * onto Java language data types and type names as follows:
  42  *
  43  * <br>
  44  * <br>
  45  * <table border="1">
  46  * <caption>TIFF Data Type to Java Data Type Mapping</caption>
  47  *
  48  * <tr>
  49  * <th>
  50  * <b>TIFF Data Type</b>
  51  * </th>
  52  * <th>
  53  * <b>Java Constant</b>
  54  * </th>
  55  * <th>
  56  * <b>Java Data Type</b>
  57  * </th>
  58  * <th>
  59  * <b>Java Type Name</b>
  60  * </th>
  61  * </tr>
  62  *
  63  * <tr>
  64  * <td>
  65  * <tt>BYTE</tt>
  66  * </td>
  67  * <td>
  68  * {@link TIFFTag#TIFF_BYTE}
  69  * </td>
  70  * <td>
  71  * <code>byte</code>
  72  * </td>
  73  * <td>
  74  * <code>"Byte"</code>
  75  * </td>
  76  * </tr>
  77  *
  78  * <tr>
  79  * <td>
  80  * <tt>ASCII</tt>
  81  * </td>
  82  * <td>
  83  * {@link TIFFTag#TIFF_ASCII}
  84  * </td>
  85  * <td>
  86  * <code>String</code>
  87  * </td>
  88  * <td>
  89  * <code>"Ascii"</code>
  90  * </td>
  91  * </tr>
  92  *
  93  * <tr>
  94  * <td>
  95  * <tt>SHORT</tt>
  96  * </td>
  97  * <td>
  98  * {@link TIFFTag#TIFF_SHORT}
  99  * </td>
 100  * <td>
 101  * <code>char</code>
 102  * </td>
 103  * <td>
 104  * <code>"Short"</code>
 105  * </td>
 106  * </tr>
 107  *
 108  * <tr>
 109  * <td>
 110  * <tt>LONG</tt>
 111  * </td>
 112  * <td>
 113  * {@link TIFFTag#TIFF_LONG}
 114  * </td>
 115  * <td>
 116  * <code>long</code>
 117  * </td>
 118  * <td>
 119  * <code>"Long"</code>
 120  * </td>
 121  * </tr>
 122  *
 123  * <tr>
 124  * <td>
 125  * <tt>RATIONAL</tt>
 126  * </td>
 127  * <td>
 128  * {@link TIFFTag#TIFF_RATIONAL}
 129  * </td>
 130  * <td>
 131  * <code>long[2]</code> {numerator, denominator}
 132  * </td>
 133  * <td>
 134  * <code>"Rational"</code>
 135  * </td>
 136  * </tr>
 137  *
 138  * <tr>
 139  * <td>
 140  * <tt>SBYTE</tt>
 141  * </td>
 142  * <td>
 143  * {@link TIFFTag#TIFF_SBYTE}
 144  * </td>
 145  * <td>
 146  * <code>byte</code>
 147  * </td>
 148  * <td>
 149  * <code>"SByte"</code>
 150  * </td>
 151  * </tr>
 152  *
 153  * <tr>
 154  * <td>
 155  * <tt>UNDEFINED</tt>
 156  * </td>
 157  * <td>
 158  * {@link TIFFTag#TIFF_UNDEFINED}
 159  * </td>
 160  * <td>
 161  * <code>byte</code>
 162  * </td>
 163  * <td>
 164  * <code>"Undefined"</code>
 165  * </td>
 166  * </tr>
 167  *
 168  * <tr>
 169  * <td>
 170  * <tt>SSHORT</tt>
 171  * </td>
 172  * <td>
 173  * {@link TIFFTag#TIFF_SSHORT}
 174  * </td>
 175  * <td>
 176  * <code>short</code>
 177  * </td>
 178  * <td>
 179  * <code>"SShort"</code>
 180  * </td>
 181  * </tr>
 182  *
 183  * <tr>
 184  * <td>
 185  * <tt>SLONG</tt>
 186  * </td>
 187  * <td>
 188  * {@link TIFFTag#TIFF_SLONG}
 189  * </td>
 190  * <td>
 191  * <code>int</code>
 192  * </td>
 193  * <td>
 194  * <code>"SLong"</code>
 195  * </td>
 196  * </tr>
 197  *
 198  * <tr>
 199  * <td>
 200  * <tt>SRATIONAL</tt>
 201  * </td>
 202  * <td>
 203  * {@link TIFFTag#TIFF_SRATIONAL}
 204  * </td>
 205  * <td>
 206  * <code>int[2]</code> {numerator, denominator}
 207  * </td>
 208  * <td>
 209  * <code>"SRational"</code>
 210  * </td>
 211  * </tr>
 212  *
 213  * <tr>
 214  * <td>
 215  * <tt>FLOAT</tt>
 216  * </td>
 217  * <td>
 218  * {@link TIFFTag#TIFF_FLOAT}
 219  * </td>
 220  * <td>
 221  * <code>float</code>
 222  * </td>
 223  * <td>
 224  * <code>"Float"</code>
 225  * </td>
 226  * </tr>
 227  *
 228  * <tr>
 229  * <td>
 230  * <tt>DOUBLE</tt>
 231  * </td>
 232  * <td>
 233  * {@link TIFFTag#TIFF_DOUBLE}
 234  * </td>
 235  * <td>
 236  * <code>double</code>
 237  * </td>
 238  * <td>
 239  * <code>"Double"</code>
 240  * </td>
 241  * </tr>
 242  *
 243  * <tr>
 244  * <td>
 245  * <tt>IFD</tt>
 246  * </td>
 247  * <td>
 248  * {@link TIFFTag#TIFF_IFD_POINTER}
 249  * </td>
 250  * <td>
 251  * <code>long</code>
 252  * </td>
 253  * <td>
 254  * <code>"IFDPointer"</code>
 255  * </td>
 256  * </tr>
 257  *
 258  * </table>
 259  *
 260  * @since 1.9
 261  * @see   TIFFDirectory
 262  * @see   TIFFTag
 263  */
 264 public class TIFFField implements Cloneable {
 265 
 266     private static final String[] typeNames = {
 267         null,
 268         "Byte", "Ascii", "Short", "Long", "Rational",
 269         "SByte", "Undefined", "SShort", "SLong", "SRational",
 270         "Float", "Double", "IFDPointer"
 271     };
 272 
 273     private static final boolean[] isIntegral = {
 274         false,
 275         true, false, true, true, false,
 276         true, true, true, true, false,
 277         false, false, false
 278     };
 279 
 280     /** The tag. */
 281     private TIFFTag tag;
 282 
 283     /** The tag number. */
 284     private int tagNumber;
 285 
 286     /** The tag type. */
 287     private int type;
 288 
 289     /** The number of data items present in the field. */
 290     private int count;
 291 
 292     /** The field data. */
 293     private Object data;
 294 
 295     /** The IFD contents if available. This will usually be a TIFFIFD. */
 296     private TIFFDirectory dir;
 297 
 298     /** The default constructor. */
 299     private TIFFField() {}
 300 
 301     private static String getAttribute(Node node, String attrName) {
 302         NamedNodeMap attrs = node.getAttributes();
 303         return attrs.getNamedItem(attrName).getNodeValue();
 304     }
 305 
 306     private static void initData(Node node,
 307                                  int[] otype, int[] ocount, Object[] odata) {
 308         int type;
 309         int count;
 310         Object data = null;
 311 
 312         String typeName = node.getNodeName();
 313         typeName = typeName.substring(4);
 314         typeName = typeName.substring(0, typeName.length() - 1);
 315         type = TIFFField.getTypeByName(typeName);
 316         if (type == -1) {
 317             throw new IllegalArgumentException("typeName = " + typeName);
 318         }
 319 
 320         Node child = node.getFirstChild();
 321 
 322         count = 0;
 323         while (child != null) {
 324             String childTypeName = child.getNodeName().substring(4);
 325             if (!typeName.equals(childTypeName)) {
 326                 // warning
 327             }
 328 
 329             ++count;
 330             child = child.getNextSibling();
 331         }
 332 
 333         if (count > 0) {
 334             data = createArrayForType(type, count);
 335             child = node.getFirstChild();
 336             int idx = 0;
 337             while (child != null) {
 338                 String value = getAttribute(child, "value");
 339 
 340                 String numerator, denominator;
 341                 int slashPos;
 342 
 343                 switch (type) {
 344                 case TIFFTag.TIFF_ASCII:
 345                     ((String[])data)[idx] = value;
 346                     break;
 347                 case TIFFTag.TIFF_BYTE:
 348                 case TIFFTag.TIFF_SBYTE:
 349                     ((byte[])data)[idx] =
 350                         (byte)Integer.parseInt(value);
 351                     break;
 352                 case TIFFTag.TIFF_SHORT:
 353                     ((char[])data)[idx] =
 354                         (char)Integer.parseInt(value);
 355                     break;
 356                 case TIFFTag.TIFF_SSHORT:
 357                     ((short[])data)[idx] =
 358                         (short)Integer.parseInt(value);
 359                     break;
 360                 case TIFFTag.TIFF_SLONG:
 361                     ((int[])data)[idx] =
 362                         Integer.parseInt(value);
 363                     break;
 364                 case TIFFTag.TIFF_LONG:
 365                 case TIFFTag.TIFF_IFD_POINTER:
 366                     ((long[])data)[idx] =
 367                         Long.parseLong(value);
 368                     break;
 369                 case TIFFTag.TIFF_FLOAT:
 370                     ((float[])data)[idx] =
 371                         Float.parseFloat(value);
 372                     break;
 373                 case TIFFTag.TIFF_DOUBLE:
 374                     ((double[])data)[idx] =
 375                         Double.parseDouble(value);
 376                     break;
 377                 case TIFFTag.TIFF_SRATIONAL:
 378                     slashPos = value.indexOf("/");
 379                     numerator = value.substring(0, slashPos);
 380                     denominator = value.substring(slashPos + 1);
 381 
 382                     ((int[][])data)[idx] = new int[2];
 383                     ((int[][])data)[idx][0] =
 384                         Integer.parseInt(numerator);
 385                     ((int[][])data)[idx][1] =
 386                         Integer.parseInt(denominator);
 387                     break;
 388                 case TIFFTag.TIFF_RATIONAL:
 389                     slashPos = value.indexOf("/");
 390                     numerator = value.substring(0, slashPos);
 391                     denominator = value.substring(slashPos + 1);
 392 
 393                     ((long[][])data)[idx] = new long[2];
 394                     ((long[][])data)[idx][0] =
 395                         Long.parseLong(numerator);
 396                     ((long[][])data)[idx][1] =
 397                         Long.parseLong(denominator);
 398                     break;
 399                 default:
 400                     // error
 401                 }
 402 
 403                 idx++;
 404                 child = child.getNextSibling();
 405             }
 406         }
 407 
 408         otype[0] = type;
 409         ocount[0] = count;
 410         odata[0] = data;
 411     }
 412 
 413     /**
 414      * Creates a <code>TIFFField</code> from a TIFF native image
 415      * metadata node. If the value of the <tt>"tagNumber"</tt> attribute
 416      * of the node is not found in <code>tagSet</code> then a new
 417      * <code>TIFFTag</code> with name <code>TIFFTag.UNKNOWN_TAG_NAME</code>
 418      * will be created and assigned to the field.
 419      *
 420      * @param tagSet The <code>TIFFTagSet</code> to which the
 421      * <code>TIFFTag</code> of the field belongs.
 422      * @param node A native TIFF image metadata <code>TIFFField</code> node.
 423      * @throws NullPointerException if <code>node</code> is
 424      * <code>null</code>.
 425      * @throws IllegalArgumentException if the name of the node is not
 426      * <code>"TIFFField"</code>.
 427      * @return A new {@code TIFFField}.
 428      */
 429     public static TIFFField createFromMetadataNode(TIFFTagSet tagSet,
 430                                                    Node node) {
 431         if (node == null) {
 432             throw new NullPointerException("node == null!");
 433         }
 434         String name = node.getNodeName();
 435         if (!name.equals("TIFFField")) {
 436             throw new IllegalArgumentException("!name.equals(\"TIFFField\")");
 437         }
 438 
 439         int tagNumber = Integer.parseInt(getAttribute(node, "number"));
 440         TIFFTag tag = null;
 441         if (tagSet != null) {
 442             tag = tagSet.getTag(tagNumber);
 443         }
 444 
 445         int type = TIFFTag.TIFF_UNDEFINED;
 446         int count = 0;
 447         Object data = null;
 448 
 449         Node child = node.getFirstChild();
 450         if (child != null) {
 451             String typeName = child.getNodeName();
 452             if (typeName.equals("TIFFUndefined")) {
 453                 String values = getAttribute(child, "value");
 454                 StringTokenizer st = new StringTokenizer(values, ",");
 455                 count = st.countTokens();
 456 
 457                 byte[] bdata = new byte[count];
 458                 for (int i = 0; i < count; i++) {
 459                     bdata[i] = (byte)Integer.parseInt(st.nextToken());
 460                 }
 461 
 462                 type = TIFFTag.TIFF_UNDEFINED;
 463                 data = bdata;
 464             } else {
 465                 int[] otype = new int[1];
 466                 int[] ocount = new int[1];
 467                 Object[] odata = new Object[1];
 468 
 469                 initData(node.getFirstChild(), otype, ocount, odata);
 470                 type = otype[0];
 471                 count = ocount[0];
 472                 data = odata[0];
 473             }
 474         } else if (tag != null) {
 475             int t = TIFFTag.MAX_DATATYPE;
 476             while(t >= TIFFTag.MIN_DATATYPE && !tag.isDataTypeOK(t)) {
 477                 t--;
 478             }
 479             type = t;
 480         }
 481 
 482         if (tag == null) {
 483             tag = new TIFFTag(TIFFTag.UNKNOWN_TAG_NAME, tagNumber, 1 << type);
 484         }
 485 
 486         return new TIFFField(tag, type, count, data);
 487     }
 488 
 489     /**
 490      * Constructs a <code>TIFFField</code> with arbitrary data. The
 491      * <code>type</code> parameter must be a value for which
 492      * {@link TIFFTag#isDataTypeOK tag.isDataTypeOK()}
 493      * returns <code>true</code>. The <code>data</code> parameter must
 494      * be an array of a Java type appropriate for the type of the TIFF
 495      * field.
 496      *
 497      * <p>Note that the value (data) of the <code>TIFFField</code>
 498      * will always be the actual field value regardless of the number of
 499      * bytes required for that value. This is the case despite the fact
 500      * that the TIFF <i>IFD Entry</i> corresponding to the field may
 501      * actually contain the offset to the value of the field rather than
 502      * the value itself (the latter occurring if and only if the
 503      * value fits into 4 bytes). In other words, the value of the
 504      * field will already have been read from the TIFF stream. (An exception
 505      * to this case may occur when the field represents the contents of a
 506      * non-baseline IFD. In that case the data will be a <code>long[]</code>
 507      * containing the offset to the IFD and the <code>TIFFDirectory</code>
 508      * returned by {@link #getDirectory()} will be its contents.)
 509      *
 510      * @param tag The tag to associated with this field.
 511      * @param type One of the <code>TIFFTag.TIFF_*</code> constants
 512      * indicating the data type of the field as written to the TIFF stream.
 513      * @param count The number of data values.
 514      * @param data The actual data content of the field.
 515      *
 516      * @throws NullPointerException if <code>tag&nbsp;==&nbsp;null</code>.
 517      * @throws IllegalArgumentException if <code>type</code> is not
 518      * one of the <code>TIFFTag.TIFF_*</code> data type constants.
 519      * @throws IllegalArgumentException if <code>type</code> is an unacceptable
 520      * data type for the supplied <code>TIFFTag</code>.
 521      * @throws IllegalArgumentException if <code>count&nbsp;&lt;&nbsp;0</code>.
 522      * @throws NullPointerException if <code>data&nbsp;==&nbsp;null</code>.
 523      * @throws IllegalArgumentException if <code>data</code> is an instance of
 524      * a class incompatible with the specified type.
 525      * @throws IllegalArgumentException if the size of the data array is wrong.
 526      */
 527     public TIFFField(TIFFTag tag, int type, int count, Object data) {
 528         if(tag == null) {
 529             throw new NullPointerException("tag == null!");
 530         } else if(type < TIFFTag.MIN_DATATYPE || type > TIFFTag.MAX_DATATYPE) {
 531             throw new IllegalArgumentException("Unknown data type "+type);
 532         } else if(!tag.isDataTypeOK(type)) {
 533             throw new IllegalArgumentException("Illegal data type " + type
 534                 + " for " + tag.getName() + " tag");
 535         } else if(count < 0) {
 536             throw new IllegalArgumentException("count < 0!");
 537         } else if(data == null) {
 538             throw new NullPointerException("data == null!");
 539         }
 540 
 541         boolean isDataArrayCorrect = false;
 542 
 543         switch (type) {
 544         case TIFFTag.TIFF_BYTE:
 545         case TIFFTag.TIFF_SBYTE:
 546         case TIFFTag.TIFF_UNDEFINED:
 547             isDataArrayCorrect = data instanceof byte[]
 548                 && ((byte[])data).length == count;
 549             break;
 550         case TIFFTag.TIFF_ASCII:
 551             isDataArrayCorrect = data instanceof String[]
 552                 && ((String[])data).length == count;
 553             break;
 554         case TIFFTag.TIFF_SHORT:
 555             isDataArrayCorrect = data instanceof char[]
 556                 && ((char[])data).length == count;
 557             break;
 558         case TIFFTag.TIFF_LONG:
 559             isDataArrayCorrect = data instanceof long[]
 560                 && ((long[])data).length == count;
 561             break;
 562         case TIFFTag.TIFF_IFD_POINTER:
 563             isDataArrayCorrect = data instanceof long[]
 564                 && ((long[])data).length == 1;
 565             break;
 566         case TIFFTag.TIFF_RATIONAL:
 567             isDataArrayCorrect = data instanceof long[][]
 568                 && ((long[][])data).length == count
 569                 && ((long[][])data)[0].length == 2;
 570             break;
 571         case TIFFTag.TIFF_SSHORT:
 572             isDataArrayCorrect = data instanceof short[]
 573                 && ((short[])data).length == count;
 574             break;
 575         case TIFFTag.TIFF_SLONG:
 576             isDataArrayCorrect = data instanceof int[]
 577                 && ((int[])data).length == count;
 578             break;
 579         case TIFFTag.TIFF_SRATIONAL:
 580             isDataArrayCorrect = data instanceof int[][]
 581                 && ((int[][])data).length == count
 582                 && ((int[][])data)[0].length == 2;
 583             break;
 584         case TIFFTag.TIFF_FLOAT:
 585             isDataArrayCorrect = data instanceof float[]
 586                 && ((float[])data).length == count;
 587             break;
 588         case TIFFTag.TIFF_DOUBLE:
 589             isDataArrayCorrect = data instanceof double[]
 590                 && ((double[])data).length == count;
 591             break;
 592         default:
 593             throw new IllegalArgumentException("Unknown data type "+type);
 594         }
 595 
 596         if (!isDataArrayCorrect) {
 597             throw new IllegalArgumentException
 598                 ("Illegal class or length for data array");
 599         }
 600 
 601         this.tag = tag;
 602         this.tagNumber = tag.getNumber();
 603         this.type = type;
 604         this.count = count;
 605         this.data = data;
 606     }
 607 
 608     /**
 609      * Constructs a data array using {@link #createArrayForType
 610      * createArrayForType()} and invokes
 611      * {@link #TIFFField(TIFFTag,int,int,Object)} with the supplied
 612      * parameters and the created array.
 613      *
 614      * @param tag The tag to associated with this field.
 615      * @param type One of the <code>TIFFTag.TIFF_*</code> constants
 616      * indicating the data type of the field as written to the TIFF stream.
 617      * @param count The number of data values.
 618      * @throws NullPointerException if <code>tag&nbsp;==&nbsp;null</code>.
 619      * @throws IllegalArgumentException if <code>type</code> is not
 620      * one of the <code>TIFFTag.TIFF_*</code> data type constants.
 621      * @throws IllegalArgumentException if <code>type</code> is an unacceptable
 622      * data type for the supplied <code>TIFFTag</code>.
 623      * @throws IllegalArgumentException if <code>count&nbsp;&lt;&nbsp;0</code>.
 624      * @see #TIFFField(TIFFTag,int,int,Object)
 625      */
 626     public TIFFField(TIFFTag tag, int type, int count) {
 627         this(tag, type, count, createArrayForType(type, count));
 628     }
 629 
 630     /**
 631      * Constructs a <code>TIFFField</code> with a single non-negative integral
 632      * value.
 633      * The field will have type
 634      * {@link TIFFTag#TIFF_SHORT  TIFF_SHORT} if
 635      * <code>val&nbsp;&lt;&nbsp;65536</code> and type
 636      * {@link TIFFTag#TIFF_LONG TIFF_LONG} otherwise.  The count
 637      * of the field will be unity.
 638      *
 639      * @param tag The tag to associate with this field.
 640      * @param value The value to associate with this field.
 641      * @throws NullPointerException if <code>tag&nbsp;==&nbsp;null</code>.
 642      * @throws IllegalArgumentException if the derived type is unacceptable
 643      * for the supplied <code>TIFFTag</code>.
 644      * @throws IllegalArgumentException if <code>value&nbsp;&lt;&nbsp;0</code>.
 645      */
 646     public TIFFField(TIFFTag tag, int value) {
 647         if(tag == null) {
 648             throw new NullPointerException("tag == null!");
 649         }
 650         if (value < 0) {
 651             throw new IllegalArgumentException("value < 0!");
 652         }
 653 
 654         this.tag = tag;
 655         this.tagNumber = tag.getNumber();
 656         this.count = 1;
 657 
 658         if (value < 65536) {
 659             if (!tag.isDataTypeOK(TIFFTag.TIFF_SHORT)) {
 660                 throw new IllegalArgumentException("Illegal data type "
 661                     + TIFFTag.TIFF_SHORT + " for " + tag.getName() + " tag");
 662             }
 663             this.type = TIFFTag.TIFF_SHORT;
 664             char[] cdata = new char[1];
 665             cdata[0] = (char)value;
 666             this.data = cdata;
 667         } else {
 668             if (!tag.isDataTypeOK(TIFFTag.TIFF_LONG)) {
 669                 throw new IllegalArgumentException("Illegal data type "
 670                     + TIFFTag.TIFF_LONG + " for " + tag.getName() + " tag");
 671             }
 672             this.type = TIFFTag.TIFF_LONG;
 673             long[] ldata = new long[1];
 674             ldata[0] = value;
 675             this.data = ldata;
 676         }
 677     }
 678 
 679     /**
 680      * Constructs a <code>TIFFField</code> with an IFD offset and contents.
 681      * The offset will be stored as the data of this field as
 682      * <code>long[] {offset}</code>. The directory will not be cloned. The count
 683      * of the field will be unity.
 684      *
 685      * @param tag The tag to associated with this field.
 686      * @param type One of the constants <code>TIFFTag.TIFF_LONG</code> or
 687      * <code>TIFFTag.TIFF_IFD_POINTER</code>.
 688      * @param offset The IFD offset.
 689      * @param dir The directory.
 690      *
 691      * @throws NullPointerException if <code>tag&nbsp;==&nbsp;null</code>.
 692      * @throws IllegalArgumentException if <code>type</code> is neither
 693      * <code>TIFFTag.TIFF_LONG</code> nor <code>TIFFTag.TIFF_IFD_POINTER</code>.
 694      * @throws IllegalArgumentException if <code>type</code> is an unacceptable
 695      * data type for the supplied <code>TIFFTag</code>.
 696      * @throws IllegalArgumentException if <code>offset</code> is non-positive.
 697      * @throws NullPointerException if <code>dir&nbsp;==&nbsp;null</code>.
 698      *
 699      * @see #TIFFField(TIFFTag,int,int,Object)
 700      */
 701     public TIFFField(TIFFTag tag, int type, long offset, TIFFDirectory dir) {
 702         this(tag, type, 1, new long[] {offset});
 703         if (type != TIFFTag.TIFF_LONG && type != TIFFTag.TIFF_IFD_POINTER) {
 704             throw new IllegalArgumentException("type " + type
 705                 + " is neither TIFFTag.TIFF_LONG nor TIFFTag.TIFF_IFD_POINTER");
 706         } else if (offset <= 0) {
 707             throw new IllegalArgumentException("offset " + offset
 708                 + " is non-positive");
 709         } else if (dir == null) {
 710             throw new NullPointerException("dir == null");
 711         }
 712         this.dir = dir;
 713     }
 714 
 715     /**
 716      * Retrieves the tag associated with this field.
 717      *
 718      * @return The associated <code>TIFFTag</code>.
 719      */
 720     public TIFFTag getTag() {
 721         return tag;
 722     }
 723 
 724     /**
 725      * Retrieves the tag number in the range <code>[0,&nbsp;65535]</code>.
 726      *
 727      * @return The tag number.
 728      */
 729     public int getTagNumber() {
 730         return tagNumber;
 731     }
 732 
 733     /**
 734      * Returns the type of the data stored in the field.  For a TIFF 6.0
 735      * stream, the value will equal one of the <code>TIFFTag.TIFF_*</code>
 736      * constants. For future revisions of TIFF, higher values are possible.
 737      *
 738      * @return The data type of the field value.
 739      */
 740     public int getType() {
 741         return type;
 742     }
 743 
 744     /**
 745      * Returns the name of the supplied data type constant.
 746      *
 747      * @param dataType One of the <code>TIFFTag.TIFF_*</code> constants
 748      * indicating the data type of the field as written to the TIFF stream.
 749      * @return The type name corresponding to the supplied type constant.
 750      * @throws IllegalArgumentException if <code>dataType</code> is not
 751      * one of the <code>TIFFTag.TIFF_*</code> data type constants.
 752      */
 753     public static String getTypeName(int dataType) {
 754         if (dataType < TIFFTag.MIN_DATATYPE ||
 755             dataType > TIFFTag.MAX_DATATYPE) {
 756             throw new IllegalArgumentException("Unknown data type "+dataType);
 757         }
 758 
 759         return typeNames[dataType];
 760     }
 761 
 762     /**
 763      * Returns the data type constant corresponding to the supplied data
 764      * type name. If the name is unknown <code>-1</code> will be returned.
 765      *
 766      * @param typeName The type name.
 767      * @return One of the <code>TIFFTag.TIFF_*</code> constants or
 768      * <code>-1</code> if the name is not recognized.
 769      */
 770     public static int getTypeByName(String typeName) {
 771         for (int i = TIFFTag.MIN_DATATYPE; i <= TIFFTag.MAX_DATATYPE; i++) {
 772             if (typeName.equals(typeNames[i])) {
 773                 return i;
 774             }
 775         }
 776 
 777         return -1;
 778     }
 779 
 780     /**
 781      * Creates an array appropriate for the indicated data type.
 782      *
 783      * @param dataType One of the <code>TIFFTag.TIFF_*</code> data type
 784      * constants.
 785      * @param count The number of values in the array.
 786      * @return An array appropriate for the specified data type.
 787      *
 788      * @throws IllegalArgumentException if <code>dataType</code> is not
 789      * one of the <code>TIFFTag.TIFF_*</code> data type constants.
 790      * @throws IllegalArgumentException if <code>count&nbsp;&lt;&nbsp;0</code>.
 791      */
 792     public static Object createArrayForType(int dataType, int count) {
 793         if(count < 0) {
 794             throw new IllegalArgumentException("count < 0!");
 795         }
 796         switch (dataType) {
 797         case TIFFTag.TIFF_BYTE:
 798         case TIFFTag.TIFF_SBYTE:
 799         case TIFFTag.TIFF_UNDEFINED:
 800             return new byte[count];
 801         case TIFFTag.TIFF_ASCII:
 802             return new String[count];
 803         case TIFFTag.TIFF_SHORT:
 804             return new char[count];
 805         case TIFFTag.TIFF_LONG:
 806         case TIFFTag.TIFF_IFD_POINTER:
 807             return new long[count];
 808         case TIFFTag.TIFF_RATIONAL:
 809             return new long[count][2];
 810         case TIFFTag.TIFF_SSHORT:
 811             return new short[count];
 812         case TIFFTag.TIFF_SLONG:
 813             return new int[count];
 814         case TIFFTag.TIFF_SRATIONAL:
 815             return new int[count][2];
 816         case TIFFTag.TIFF_FLOAT:
 817             return new float[count];
 818         case TIFFTag.TIFF_DOUBLE:
 819             return new double[count];
 820         default:
 821             throw new IllegalArgumentException("Unknown data type "+dataType);
 822         }
 823     }
 824 
 825     /**
 826      * Returns the <code>TIFFField</code> as a node named either
 827      * <tt>"TIFFField"</tt> or <tt>"TIFFIFD"</tt> as described in the
 828      * TIFF native image metadata specification. The node will be named
 829      * <tt>"TIFFIFD"</tt> if and only if the field's data object is an
 830      * instance of {@link TIFFDirectory} or equivalently
 831      * {@link TIFFTag#isIFDPointer getTag.isIFDPointer()} returns
 832      * <code>true</code>.
 833      *
 834      * @return a <code>Node</code> named <tt>"TIFFField"</tt> or
 835      * <tt>"TIFFIFD"</tt>.
 836      */
 837     public Node getAsNativeNode() {
 838         return new TIFFFieldNode(this);
 839     }
 840 
 841     /**
 842      * Indicates whether the value associated with the field is of
 843      * integral data type.
 844      *
 845      * @return Whether the field type is integral.
 846      */
 847     public boolean isIntegral() {
 848         return isIntegral[type];
 849     }
 850 
 851     /**
 852      * Returns the number of data items present in the field.  For
 853      * <code>TIFFTag.TIFF_ASCII</code> fields, the value returned is the
 854      * number of <code>String</code>s, not the total length of the
 855      * data as in the file representation.
 856      *
 857      * @return The number of data items present in the field.
 858      */
 859     public int getCount() {
 860         return count;
 861     }
 862 
 863     /**
 864      * Returns a reference to the data object associated with the field.
 865      *
 866      * @return The data object of the field.
 867      */
 868     public Object getData() {
 869         return data;
 870     }
 871 
 872     /**
 873      * Returns the data as an uninterpreted array of
 874      * <code>byte</code>s.  The type of the field must be one of
 875      * <code>TIFFTag.TIFF_BYTE</code>, <code>TIFF_SBYTE</code>, or
 876      * <code>TIFF_UNDEFINED</code>.
 877      *
 878      * <p> For data in <code>TIFFTag.TIFF_BYTE</code> format, the application
 879      * must take care when promoting the data to longer integral types
 880      * to avoid sign extension.
 881      *
 882      * @throws ClassCastException if the field is not of type
 883      * <code>TIFF_BYTE</code>, <code>TIFF_SBYTE</code>, or
 884      * <code>TIFF_UNDEFINED</code>.
 885      * @return The data as an uninterpreted array of bytes.
 886      */
 887     public byte[] getAsBytes() {
 888         return (byte[])data;
 889     }
 890 
 891     /**
 892      * Returns <code>TIFFTag.TIFF_SHORT</code> data as an array of
 893      * <code>char</code>s (unsigned 16-bit integers).
 894      *
 895      * @throws ClassCastException if the field is not of type
 896      * <code>TIFF_SHORT</code>.
 897      * @return The data as an array of {@code char}s.
 898      */
 899     public char[] getAsChars() {
 900         return (char[])data;
 901     }
 902 
 903     /**
 904      * Returns <code>TIFFTag.TIFF_SSHORT</code> data as an array of
 905      * <code>short</code>s (signed 16-bit integers).
 906      *
 907      * @throws ClassCastException if the field is not of type
 908      * <code>TIFF_SSHORT</code>.
 909      * @return The data as an array of {@code short}s.
 910      */
 911     public short[] getAsShorts() {
 912         return (short[])data;
 913     }
 914 
 915     /**
 916      * Returns <code>TIFFTag.TIFF_SLONG</code> data as an array of
 917      * <code>int</code>s (signed 32-bit integers).
 918      *
 919      * @throws ClassCastException if the field is not of type
 920      * <code>TIFF_SHORT</code>, <code>TIFF_SSHORT</code>, or
 921      * <code>TIFF_SLONG</code>.
 922      * @return The data as an array of {@code int}s.
 923      */
 924     public int[] getAsInts() {
 925         if (data instanceof int[]) {
 926             return (int[])data;
 927         } else if (data instanceof char[]){
 928             char[] cdata = (char[])data;
 929             int[] idata = new int[cdata.length];
 930             for (int i = 0; i < cdata.length; i++) {
 931                 idata[i] = cdata[i] & 0xffff;
 932             }
 933             return idata;
 934         } else if (data instanceof short[]){
 935             short[] sdata = (short[])data;
 936             int[] idata = new int[sdata.length];
 937             for (int i = 0; i < sdata.length; i++) {
 938                 idata[i] = (int)sdata[i];
 939             }
 940             return idata;
 941         } else {
 942             throw new ClassCastException("Data not char[], short[], or int[]!");
 943         }
 944     }
 945 
 946     /**
 947      * Returns <code>TIFFTag.TIFF_LONG</code> or
 948      * <code>TIFF_IFD_POINTER</code> data as an array of
 949      * <code>long</code>s (signed 64-bit integers).
 950      *
 951      * @throws ClassCastException if the field is not of type
 952      * <code>TIFF_LONG</code> or <code>TIFF_IFD_POINTER</code>.
 953      * @return The data as an array of {@code long}s.
 954      */
 955     public long[] getAsLongs() {
 956         return (long[])data;
 957     }
 958 
 959     /**
 960      * Returns <code>TIFFTag.TIFF_FLOAT</code> data as an array of
 961      * <code>float</code>s (32-bit floating-point values).
 962      *
 963      * @throws ClassCastException if the field is not of type
 964      * <code>TIFF_FLOAT</code>.
 965      * @return The data as an array of {@code float}s.
 966      */
 967     public float[] getAsFloats() {
 968         return (float[])data;
 969     }
 970 
 971     /**
 972      * Returns <code>TIFFTag.TIFF_DOUBLE</code> data as an array of
 973      * <code>double</code>s (64-bit floating-point values).
 974      *
 975      * @throws ClassCastException if the field is not of type
 976      * <code>TIFF_DOUBLE</code>.
 977      * @return The data as an array of {@code double}s.
 978      */
 979     public double[] getAsDoubles() {
 980         return (double[])data;
 981     }
 982 
 983     /**
 984      * Returns <code>TIFFTag.TIFF_SRATIONAL</code> data as an array of
 985      * 2-element arrays of <code>int</code>s.
 986      *
 987      * @throws ClassCastException if the field is not of type
 988      * <code>TIFF_SRATIONAL</code>.
 989      * @return The data as an array of signed rationals.
 990      */
 991     public int[][] getAsSRationals() {
 992         return (int[][])data;
 993     }
 994 
 995     /**
 996      * Returns <code>TIFFTag.TIFF_RATIONAL</code> data as an array of
 997      * 2-element arrays of <code>long</code>s.
 998      *
 999      * @throws ClassCastException if the field is not of type
1000      * <code>TIFF_RATIONAL</code>.
1001      * @return The data as an array of unsigned rationals.
1002      */
1003     public long[][] getAsRationals() {
1004         return (long[][])data;
1005     }
1006 
1007     /**
1008      * Returns data in any format as an <code>int</code>.
1009      *
1010      * <p> <code>TIFFTag.TIFF_BYTE</code> values are treated as unsigned; that
1011      * is, no sign extension will take place and the returned value
1012      * will be in the range [0, 255].  <code>TIFF_SBYTE</code> data
1013      * will be returned in the range [-128, 127].
1014      *
1015      * <p> A <code>TIFF_UNDEFINED</code> value is treated as though
1016      * it were a <code>TIFF_BYTE</code>.
1017      *
1018      * <p> Data in <code>TIFF_SLONG</code>, <code>TIFF_LONG</code>,
1019      * <code>TIFF_FLOAT</code>, <code>TIFF_DOUBLE</code> or
1020      * <code>TIFF_IFD_POINTER</code> format are simply cast to
1021      * <code>int</code> and may suffer from truncation.
1022      *
1023      * <p> Data in <code>TIFF_SRATIONAL</code> or
1024      * <code>TIFF_RATIONAL</code> format are evaluated by dividing the
1025      * numerator into the denominator using double-precision
1026      * arithmetic and then casting to <code>int</code>.  Loss of
1027      * precision and truncation may occur.
1028      *
1029      * <p> Data in <code>TIFF_ASCII</code> format will be parsed as by
1030      * the <code>Double.parseDouble</code> method, with the result
1031      * case to <code>int</code>.
1032      *
1033      * @param index The index of the data.
1034      * @return The data at the given index as an {@code int}.
1035      */
1036     public int getAsInt(int index) {
1037         switch (type) {
1038         case TIFFTag.TIFF_BYTE:
1039         case TIFFTag.TIFF_UNDEFINED:
1040             return ((byte[])data)[index] & 0xff;
1041         case TIFFTag.TIFF_SBYTE:
1042             return ((byte[])data)[index];
1043         case TIFFTag.TIFF_SHORT:
1044             return ((char[])data)[index] & 0xffff;
1045         case TIFFTag.TIFF_SSHORT:
1046             return ((short[])data)[index];
1047         case TIFFTag.TIFF_SLONG:
1048             return ((int[])data)[index];
1049         case TIFFTag.TIFF_LONG:
1050         case TIFFTag.TIFF_IFD_POINTER:
1051             return (int)((long[])data)[index];
1052         case TIFFTag.TIFF_FLOAT:
1053             return (int)((float[])data)[index];
1054         case TIFFTag.TIFF_DOUBLE:
1055             return (int)((double[])data)[index];
1056         case TIFFTag.TIFF_SRATIONAL:
1057             int[] ivalue = getAsSRational(index);
1058             return (int)((double)ivalue[0]/ivalue[1]);
1059         case TIFFTag.TIFF_RATIONAL:
1060             long[] lvalue = getAsRational(index);
1061             return (int)((double)lvalue[0]/lvalue[1]);
1062         case TIFFTag.TIFF_ASCII:
1063              String s = ((String[])data)[index];
1064              return (int)Double.parseDouble(s);
1065         default:
1066             throw new ClassCastException(); // should never happen
1067         }
1068     }
1069 
1070     /**
1071      * Returns data in any format as a <code>long</code>.
1072      *
1073      * <p> <code>TIFFTag.TIFF_BYTE</code> and <code>TIFF_UNDEFINED</code> data
1074      * are treated as unsigned; that is, no sign extension will take
1075      * place and the returned value will be in the range [0, 255].
1076      * <code>TIFF_SBYTE</code> data will be returned in the range
1077      * [-128, 127].
1078      *
1079      * <p> Data in <code>TIFF_ASCII</code> format will be parsed as by
1080      * the <code>Double.parseDouble</code> method, with the result
1081      * cast to <code>long</code>.
1082      *
1083      * @param index The index of the data.
1084      * @return The data at the given index as a {@code long}.
1085      */
1086     public long getAsLong(int index) {
1087         switch (type) {
1088         case TIFFTag.TIFF_BYTE:
1089         case TIFFTag.TIFF_UNDEFINED:
1090             return ((byte[])data)[index] & 0xff;
1091         case TIFFTag.TIFF_SBYTE:
1092             return ((byte[])data)[index];
1093         case TIFFTag.TIFF_SHORT:
1094             return ((char[])data)[index] & 0xffff;
1095         case TIFFTag.TIFF_SSHORT:
1096             return ((short[])data)[index];
1097         case TIFFTag.TIFF_SLONG:
1098             return ((int[])data)[index];
1099         case TIFFTag.TIFF_LONG:
1100         case TIFFTag.TIFF_IFD_POINTER:
1101             return ((long[])data)[index];
1102         case TIFFTag.TIFF_SRATIONAL:
1103             int[] ivalue = getAsSRational(index);
1104             return (long)((double)ivalue[0]/ivalue[1]);
1105         case TIFFTag.TIFF_RATIONAL:
1106             long[] lvalue = getAsRational(index);
1107             return (long)((double)lvalue[0]/lvalue[1]);
1108         case TIFFTag.TIFF_ASCII:
1109              String s = ((String[])data)[index];
1110              return (long)Double.parseDouble(s);
1111         default:
1112             throw new ClassCastException(); // should never happen
1113         }
1114     }
1115 
1116     /**
1117      * Returns data in any format as a <code>float</code>.
1118      *
1119      * <p> <code>TIFFTag.TIFF_BYTE</code> and <code>TIFF_UNDEFINED</code> data
1120      * are treated as unsigned; that is, no sign extension will take
1121      * place and the returned value will be in the range [0, 255].
1122      * <code>TIFF_SBYTE</code> data will be returned in the range
1123      * [-128, 127].
1124      *
1125      * <p> Data in <code>TIFF_SLONG</code>, <code>TIFF_LONG</code>,
1126      * <code>TIFF_DOUBLE</code>, or <code>TIFF_IFD_POINTER</code> format are
1127      * simply cast to <code>float</code> and may suffer from
1128      * truncation.
1129      *
1130      * <p> Data in <code>TIFF_SRATIONAL</code> or
1131      * <code>TIFF_RATIONAL</code> format are evaluated by dividing the
1132      * numerator into the denominator using double-precision
1133      * arithmetic and then casting to <code>float</code>.
1134      *
1135      * <p> Data in <code>TIFF_ASCII</code> format will be parsed as by
1136      * the <code>Double.parseDouble</code> method, with the result
1137      * cast to <code>float</code>.
1138      *
1139      * @param index The index of the data.
1140      * @return The data at the given index as a {@code float}.
1141      */
1142     public float getAsFloat(int index) {
1143         switch (type) {
1144         case TIFFTag.TIFF_BYTE:
1145         case TIFFTag.TIFF_UNDEFINED:
1146             return ((byte[])data)[index] & 0xff;
1147         case TIFFTag.TIFF_SBYTE:
1148             return ((byte[])data)[index];
1149         case TIFFTag.TIFF_SHORT:
1150             return ((char[])data)[index] & 0xffff;
1151         case TIFFTag.TIFF_SSHORT:
1152             return ((short[])data)[index];
1153         case TIFFTag.TIFF_SLONG:
1154             return ((int[])data)[index];
1155         case TIFFTag.TIFF_LONG:
1156         case TIFFTag.TIFF_IFD_POINTER:
1157             return ((long[])data)[index];
1158         case TIFFTag.TIFF_FLOAT:
1159             return ((float[])data)[index];
1160         case TIFFTag.TIFF_DOUBLE:
1161             return (float)((double[])data)[index];
1162         case TIFFTag.TIFF_SRATIONAL:
1163             int[] ivalue = getAsSRational(index);
1164             return (float)((double)ivalue[0]/ivalue[1]);
1165         case TIFFTag.TIFF_RATIONAL:
1166             long[] lvalue = getAsRational(index);
1167             return (float)((double)lvalue[0]/lvalue[1]);
1168         case TIFFTag.TIFF_ASCII:
1169              String s = ((String[])data)[index];
1170              return (float)Double.parseDouble(s);
1171         default:
1172             throw new ClassCastException(); // should never happen
1173         }
1174     }
1175 
1176     /**
1177      * Returns data in any format as a <code>double</code>.
1178      *
1179      * <p> <code>TIFFTag.TIFF_BYTE</code> and <code>TIFF_UNDEFINED</code> data
1180      * are treated as unsigned; that is, no sign extension will take
1181      * place and the returned value will be in the range [0, 255].
1182      * <code>TIFF_SBYTE</code> data will be returned in the range
1183      * [-128, 127].
1184      *
1185      * <p> Data in <code>TIFF_SRATIONAL</code> or
1186      * <code>TIFF_RATIONAL</code> format are evaluated by dividing the
1187      * numerator into the denominator using double-precision
1188      * arithmetic.
1189      *
1190      * <p> Data in <code>TIFF_ASCII</code> format will be parsed as by
1191      * the <code>Double.parseDouble</code> method.
1192      *
1193      * @param index The index of the data.
1194      * @return The data at the given index as a {@code double}.
1195      */
1196     public double getAsDouble(int index) {
1197         switch (type) {
1198         case TIFFTag.TIFF_BYTE:
1199         case TIFFTag.TIFF_UNDEFINED:
1200             return ((byte[])data)[index] & 0xff;
1201         case TIFFTag.TIFF_SBYTE:
1202             return ((byte[])data)[index];
1203         case TIFFTag.TIFF_SHORT:
1204             return ((char[])data)[index] & 0xffff;
1205         case TIFFTag.TIFF_SSHORT:
1206             return ((short[])data)[index];
1207         case TIFFTag.TIFF_SLONG:
1208             return ((int[])data)[index];
1209         case TIFFTag.TIFF_LONG:
1210         case TIFFTag.TIFF_IFD_POINTER:
1211             return ((long[])data)[index];
1212         case TIFFTag.TIFF_FLOAT:
1213             return ((float[])data)[index];
1214         case TIFFTag.TIFF_DOUBLE:
1215             return ((double[])data)[index];
1216         case TIFFTag.TIFF_SRATIONAL:
1217             int[] ivalue = getAsSRational(index);
1218             return (double)ivalue[0]/ivalue[1];
1219         case TIFFTag.TIFF_RATIONAL:
1220             long[] lvalue = getAsRational(index);
1221             return (double)lvalue[0]/lvalue[1];
1222         case TIFFTag.TIFF_ASCII:
1223              String s = ((String[])data)[index];
1224              return Double.parseDouble(s);
1225         default:
1226             throw new ClassCastException(); // should never happen
1227         }
1228     }
1229 
1230     /**
1231      * Returns a <code>TIFFTag.TIFF_ASCII</code> value as a
1232      * <code>String</code>.
1233      *
1234      * @throws ClassCastException if the field is not of type
1235      * <code>TIFF_ASCII</code>.
1236      *
1237      * @param index The index of the data.
1238      * @return The data at the given index as a {@code String}.
1239      */
1240     public String getAsString(int index) {
1241         return ((String[])data)[index];
1242     }
1243 
1244     /**
1245      * Returns a <code>TIFFTag.TIFF_SRATIONAL</code> data item as a
1246      * two-element array of <code>int</code>s.
1247      *
1248      * @param index The index of the data.
1249      * @return The data at the given index as a signed rational.
1250      * @throws ClassCastException if the field is not of type
1251      * <code>TIFF_SRATIONAL</code>.
1252      */
1253     public int[] getAsSRational(int index) {
1254         return ((int[][])data)[index];
1255     }
1256 
1257     /**
1258      * Returns a TIFFTag.TIFF_RATIONAL data item as a two-element array
1259      * of ints.
1260      *
1261      * @param index The index of the data.
1262      * @return The data at the given index as an unsigned rational.
1263      * @throws ClassCastException if the field is not of type
1264      * <code>TIFF_RATIONAL</code>.
1265      */
1266     public long[] getAsRational(int index) {
1267         return ((long[][])data)[index];
1268     }
1269 
1270 
1271     /**
1272      * Returns a <code>String</code> containing a human-readable
1273      * version of the data item.  Data of type
1274      * <code>TIFFTag.TIFF_RATIONAL</code> or <code>TIFF_SRATIONAL</code> are
1275      * represented as a pair of integers separated by a
1276      * <code>'/'</code> character.
1277      *
1278      * @param index The index of the data.
1279      * @return The data at the given index as a {@code String}.
1280      * @throws ClassCastException if the field is not of one of the
1281      * legal field types.
1282      */
1283     public String getValueAsString(int index) {
1284         switch (type) {
1285         case TIFFTag.TIFF_ASCII:
1286             return ((String[])data)[index];
1287         case TIFFTag.TIFF_BYTE:
1288         case TIFFTag.TIFF_UNDEFINED:
1289             return Integer.toString(((byte[])data)[index] & 0xff);
1290         case TIFFTag.TIFF_SBYTE:
1291             return Integer.toString(((byte[])data)[index]);
1292         case TIFFTag.TIFF_SHORT:
1293             return Integer.toString(((char[])data)[index] & 0xffff);
1294         case TIFFTag.TIFF_SSHORT:
1295             return Integer.toString(((short[])data)[index]);
1296         case TIFFTag.TIFF_SLONG:
1297             return Integer.toString(((int[])data)[index]);
1298         case TIFFTag.TIFF_LONG:
1299         case TIFFTag.TIFF_IFD_POINTER:
1300             return Long.toString(((long[])data)[index]);
1301         case TIFFTag.TIFF_FLOAT:
1302             return Float.toString(((float[])data)[index]);
1303         case TIFFTag.TIFF_DOUBLE:
1304             return Double.toString(((double[])data)[index]);
1305         case TIFFTag.TIFF_SRATIONAL:
1306             int[] ivalue = getAsSRational(index);
1307             String srationalString;
1308             if(ivalue[1] != 0 && ivalue[0] % ivalue[1] == 0) {
1309                 // If the denominator is a non-zero integral divisor
1310                 // of the numerator then convert the fraction to be
1311                 // with respect to a unity denominator.
1312                 srationalString =
1313                     Integer.toString(ivalue[0] / ivalue[1]) + "/1";
1314             } else {
1315                 // Use the values directly.
1316                 srationalString =
1317                     Integer.toString(ivalue[0]) +
1318                     "/" +
1319                     Integer.toString(ivalue[1]);
1320             }
1321             return srationalString;
1322         case TIFFTag.TIFF_RATIONAL:
1323             long[] lvalue = getAsRational(index);
1324             String rationalString;
1325             if(lvalue[1] != 0L && lvalue[0] % lvalue[1] == 0) {
1326                 // If the denominator is a non-zero integral divisor
1327                 // of the numerator then convert the fraction to be
1328                 // with respect to a unity denominator.
1329                 rationalString =
1330                     Long.toString(lvalue[0] / lvalue[1]) + "/1";
1331             } else {
1332                 // Use the values directly.
1333                 rationalString =
1334                     Long.toString(lvalue[0]) +
1335                     "/" +
1336                     Long.toString(lvalue[1]);
1337             }
1338             return rationalString;
1339         default:
1340             throw new ClassCastException(); // should never happen
1341         }
1342     }
1343 
1344     /**
1345      * Returns whether the field has a <code>TIFFDirectory</code>.
1346      *
1347      * @return true if and only if getDirectory() returns non-null.
1348      */
1349     public boolean hasDirectory() {
1350         return getDirectory() != null;
1351     }
1352 
1353     /**
1354      * Returns the associated <code>TIFFDirectory</code>, if available. If no
1355      * directory is set, then <code>null</code> will be returned.
1356      *
1357      * @return the TIFFDirectory instance or null.
1358      */
1359     public TIFFDirectory getDirectory() {
1360         return dir;
1361     }
1362 
1363     /**
1364      * Clones the field and all the information contained therein.
1365      *
1366      * @return A clone of this <code>TIFFField</code>.
1367      * @throws CloneNotSupportedException if the instance cannot be cloned.
1368      */
1369     @Override
1370     public TIFFField clone() throws CloneNotSupportedException {
1371         TIFFField field = (TIFFField)super.clone();
1372 
1373         Object fieldData;
1374         switch (type) {
1375         case TIFFTag.TIFF_BYTE:
1376         case TIFFTag.TIFF_UNDEFINED:
1377         case TIFFTag.TIFF_SBYTE:
1378             fieldData = ((byte[])data).clone();
1379             break;
1380         case TIFFTag.TIFF_SHORT:
1381             fieldData = ((char[])data).clone();
1382             break;
1383         case TIFFTag.TIFF_SSHORT:
1384             fieldData = ((short[])data).clone();
1385             break;
1386         case TIFFTag.TIFF_SLONG:
1387             fieldData = ((int[])data).clone();
1388             break;
1389         case TIFFTag.TIFF_LONG:
1390         case TIFFTag.TIFF_IFD_POINTER:
1391             fieldData = ((long[])data).clone();
1392             break;
1393         case TIFFTag.TIFF_FLOAT:
1394             fieldData = ((float[])data).clone();
1395             break;
1396         case TIFFTag.TIFF_DOUBLE:
1397             fieldData = ((double[])data).clone();
1398             break;
1399         case TIFFTag.TIFF_SRATIONAL:
1400             fieldData = ((int[][])data).clone();
1401             break;
1402         case TIFFTag.TIFF_RATIONAL:
1403             fieldData = ((long[][])data).clone();
1404             break;
1405         case TIFFTag.TIFF_ASCII:
1406             fieldData = ((String[])data).clone();
1407             break;
1408         default:
1409             throw new ClassCastException(); // should never happen
1410         }
1411 
1412         field.tag = tag;
1413         field.tagNumber = tagNumber;
1414         field.type = type;
1415         field.count = count;
1416         field.data = fieldData;
1417         field.dir = dir != null ? dir.clone() : null;
1418 
1419         return field;
1420     }
1421 }
--- EOF ---