Coverage Report - org.jaudiotagger.tag.mp4.field.Mp4TagByteField
 
Classes in this File Line Coverage Branch Coverage Complexity
Mp4TagByteField
76%
25/33
57%
4/7
2.833
 
 1  
 package org.jaudiotagger.tag.mp4.field;
 2  
 
 3  
 import org.jaudiotagger.audio.generic.Utils;
 4  
 import org.jaudiotagger.audio.mp4.atom.Mp4BoxHeader;
 5  
 import org.jaudiotagger.tag.FieldDataInvalidException;
 6  
 import org.jaudiotagger.tag.mp4.Mp4FieldKey;
 7  
 import org.jaudiotagger.tag.mp4.atom.Mp4DataBox;
 8  
 
 9  
 import java.io.UnsupportedEncodingException;
 10  
 import java.nio.ByteBuffer;
 11  
 
 12  
 /**
 13  
  * Represents a single byte as a number
 14  
  * <p/>
 15  
  * <p>Usually single byte fields are used as a boolean field, but not always so we dont do this conversion
 16  
  */
 17  
 public class Mp4TagByteField extends Mp4TagTextField
 18  
 {
 19  
     //Holds the actual size of the data content as held in the databoxitem, this is required when creating new
 20  
     //items because we cant accurately work out the size by looking at the content because sometimes field must be longer
 21  
     //than is actually required to hold the value
 22  
     //e.g byte data length seems to be 1 for pgap and cpil but 2 for tmpo, so we stored the dataSize
 23  
     //when we loaded the value so if greater than 1 we pad the value.
 24  
     private int realDataLength;
 25  
 
 26  
     //Preserved from data from file
 27  
     private byte[] bytedata;
 28  
 
 29  
     /**
 30  
      * Create new field
 31  
      * <p/>
 32  
      * Assume length of 1 which is correct for most but not all byte fields
 33  
      *
 34  
      * @param id
 35  
      * @param value is a String representation of a number
 36  
      */
 37  
     public Mp4TagByteField(Mp4FieldKey id, String value) throws FieldDataInvalidException
 38  
     {
 39  0
         this(id, value, 1);
 40  0
     }
 41  
 
 42  
     /**
 43  
      * Create new field with known length
 44  
      *
 45  
      * @param id
 46  
      * @param value is a String representation of a number
 47  
      */
 48  
     public Mp4TagByteField(Mp4FieldKey id, String value, int realDataLength) throws FieldDataInvalidException
 49  
     {
 50  9
         super(id.getFieldName(), value);
 51  9
         this.realDataLength = realDataLength;
 52  
         //Check that can actually be store dnumercially, otherwise will have big problems
 53  
         //when try and save the field
 54  
         try
 55  
         {
 56  9
             Long.parseLong(value);
 57  
         }
 58  0
         catch (NumberFormatException nfe)
 59  
         {
 60  0
             throw new FieldDataInvalidException("Value of:" + value + " is invalid for field:" + id);
 61  9
         }
 62  9
     }
 63  
 
 64  
     /**
 65  
      * Construct from rawdata from audio file
 66  
      *
 67  
      * @param id
 68  
      * @param raw
 69  
      * @throws UnsupportedEncodingException
 70  
      */
 71  
     public Mp4TagByteField(String id, ByteBuffer raw) throws UnsupportedEncodingException
 72  
     {
 73  331
         super(id, raw);
 74  331
     }
 75  
 
 76  
     public Mp4FieldType getFieldType()
 77  
     {
 78  164
         return Mp4FieldType.BYTE;
 79  
     }
 80  
 
 81  
     /**
 82  
      * Return raw data bytes
 83  
      * <p/>
 84  
      * TODO this code should be done better so generalised to any length
 85  
      *
 86  
      * @return
 87  
      * @throws UnsupportedEncodingException
 88  
      */
 89  
     protected byte[] getDataBytes() throws UnsupportedEncodingException
 90  
     {
 91  
 
 92  
         //Write original data
 93  164
         if (bytedata != null)
 94  
         {
 95  155
             return bytedata;
 96  
         }
 97  
 
 98  
         //new field, lets hope the realDataLength is correct
 99  9
         switch (realDataLength)
 100  
         {
 101  
             case 2:
 102  
             {
 103  
                 //Save as two bytes
 104  8
                 Short shortValue = new Short(content);
 105  8
                 byte rawData[] = Utils.getSizeBEInt16(shortValue);
 106  8
                 return rawData;
 107  
             }
 108  
             case 1:
 109  
             {
 110  
                 //Save as 1 bytes
 111  1
                 Short shortValue = new Short(content);
 112  1
                 byte rawData[] = new byte[1];
 113  1
                 rawData[0] = shortValue.byteValue();
 114  1
                 return rawData;
 115  
             }
 116  
             case 4:
 117  
             {
 118  
                 //Assume could be int
 119  0
                 Integer intValue = new Integer(content);
 120  0
                 byte rawData[] = Utils.getSizeBEInt32(intValue);
 121  0
                 return rawData;
 122  
             }
 123  
             default:
 124  
             {
 125  
                 //TODO
 126  0
                 throw new RuntimeException(id + ":" + realDataLength + ":" + "Dont know how to write byte fields of this length");
 127  
             }
 128  
         }
 129  
 
 130  
     }
 131  
 
 132  
     protected void build(ByteBuffer data) throws UnsupportedEncodingException
 133  
     {
 134  
         //Data actually contains a 'Data' Box so process data using this
 135  331
         Mp4BoxHeader header = new Mp4BoxHeader(data);
 136  331
         Mp4DataBox databox = new Mp4DataBox(header, data);
 137  331
         dataSize = header.getDataLength();
 138  
         //Needed for subsequent write
 139  331
         realDataLength = dataSize - Mp4DataBox.PRE_DATA_LENGTH;
 140  331
         bytedata = databox.getByteData();
 141  331
         content = databox.getContent();
 142  
 
 143  331
     }
 144  
 }