20 {
21
22 fseek($fd, $ThisFileInfo[
'avdataoffset'], SEEK_SET);
23 $TIFFheader =
fread($fd, 4);
24
25 switch (substr($TIFFheader, 0, 2)) {
26 case 'II':
27 $ThisFileInfo['tiff']['byte_order'] = 'Intel';
28 break;
29 case 'MM':
30 $ThisFileInfo['tiff']['byte_order'] = 'Motorola';
31 break;
32 default:
33 $ThisFileInfo['error'][] = 'Invalid TIFF byte order identifier ('.substr($TIFFheader, 0, 2).') at offset '.$ThisFileInfo['avdataoffset'];
34 return false;
35 break;
36 }
37
38 $ThisFileInfo['fileformat'] = 'tiff';
39 $ThisFileInfo['video']['dataformat'] = 'tiff';
40 $ThisFileInfo['video']['lossless'] = true;
41 $ThisFileInfo['tiff']['ifd'] = array();
42 $CurrentIFD = array();
43
44 $FieldTypeByteLength = array(1=>1, 2=>1, 3=>2, 4=>4, 5=>8);
45
47
48 while ($nextIFDoffset > 0) {
49
50 $CurrentIFD['offset'] = $nextIFDoffset;
51
52 fseek($fd, $ThisFileInfo[
'avdataoffset'] + $nextIFDoffset, SEEK_SET);
53 $CurrentIFD[
'fieldcount'] = $this->
TIFFendian2Int(
fread($fd, 2), $ThisFileInfo[
'tiff'][
'byte_order']);
54
55 for ($i = 0; $i < $CurrentIFD['fieldcount']; $i++) {
56 $CurrentIFD[
'fields'][$i][
'raw'][
'tag'] = $this->
TIFFendian2Int(
fread($fd, 2), $ThisFileInfo[
'tiff'][
'byte_order']);
57 $CurrentIFD[
'fields'][$i][
'raw'][
'type'] = $this->
TIFFendian2Int(
fread($fd, 2), $ThisFileInfo[
'tiff'][
'byte_order']);
58 $CurrentIFD[
'fields'][$i][
'raw'][
'length'] = $this->
TIFFendian2Int(
fread($fd, 4), $ThisFileInfo[
'tiff'][
'byte_order']);
59 $CurrentIFD[
'fields'][$i][
'raw'][
'offset'] =
fread($fd, 4);
60
61 switch ($CurrentIFD['fields'][$i]['raw']['type']) {
62 case 1:
63 if ($CurrentIFD['fields'][$i]['raw']['length'] <= 4) {
64 $CurrentIFD[
'fields'][$i][
'value'] = $this->
TIFFendian2Int(substr($CurrentIFD[
'fields'][$i][
'raw'][
'offset'], 0, 1), $ThisFileInfo[
'tiff'][
'byte_order']);
65 } else {
66 $CurrentIFD[
'fields'][$i][
'offset'] = $this->
TIFFendian2Int($CurrentIFD[
'fields'][$i][
'raw'][
'offset'], $ThisFileInfo[
'tiff'][
'byte_order']);
67 }
68 break;
69
70 case 2:
71 if ($CurrentIFD['fields'][$i]['raw']['length'] <= 4) {
72 $CurrentIFD['fields'][$i]['value'] = substr($CurrentIFD['fields'][$i]['raw']['offset'], 3);
73 } else {
74 $CurrentIFD[
'fields'][$i][
'offset'] = $this->
TIFFendian2Int($CurrentIFD[
'fields'][$i][
'raw'][
'offset'], $ThisFileInfo[
'tiff'][
'byte_order']);
75 }
76 break;
77
78 case 3:
79 if ($CurrentIFD['fields'][$i]['raw']['length'] <= 2) {
80 $CurrentIFD[
'fields'][$i][
'value'] = $this->
TIFFendian2Int(substr($CurrentIFD[
'fields'][$i][
'raw'][
'offset'], 0, 2), $ThisFileInfo[
'tiff'][
'byte_order']);
81 } else {
82 $CurrentIFD[
'fields'][$i][
'offset'] = $this->
TIFFendian2Int($CurrentIFD[
'fields'][$i][
'raw'][
'offset'], $ThisFileInfo[
'tiff'][
'byte_order']);
83 }
84 break;
85
86 case 4:
87 if ($CurrentIFD['fields'][$i]['raw']['length'] <= 1) {
88 $CurrentIFD[
'fields'][$i][
'value'] = $this->
TIFFendian2Int($CurrentIFD[
'fields'][$i][
'raw'][
'offset'], $ThisFileInfo[
'tiff'][
'byte_order']);
89 } else {
90 $CurrentIFD[
'fields'][$i][
'offset'] = $this->
TIFFendian2Int($CurrentIFD[
'fields'][$i][
'raw'][
'offset'], $ThisFileInfo[
'tiff'][
'byte_order']);
91 }
92 break;
93
94 case 5:
95 break;
96 }
97 }
98
99 $ThisFileInfo['tiff']['ifd'][] = $CurrentIFD;
100 $CurrentIFD = array();
101 $nextIFDoffset = $this->
TIFFendian2Int(
fread($fd, 4), $ThisFileInfo[
'tiff'][
'byte_order']);
102
103 }
104
105 foreach ($ThisFileInfo['tiff']['ifd'] as $IFDid => $IFDarray) {
106 foreach ($IFDarray['fields'] as $key => $fieldarray) {
107 switch ($fieldarray['raw']['tag']) {
108 case 256:
109 case 257:
110 case 258:
111 case 259:
112 if (!isset($fieldarray['value'])) {
113 fseek($fd, $fieldarray[
'offset'], SEEK_SET);
114 $ThisFileInfo[
'tiff'][
'ifd'][$IFDid][
'fields'][$key][
'raw'][
'data'] =
fread($fd, $fieldarray[
'raw'][
'length'] * $FieldTypeByteLength[$fieldarray[
'raw'][
'type']]);
115
116 }
117 break;
118
119 case 270:
120 case 271:
121 case 272:
122 case 305:
123 case 306:
124 case 315:
125 case 316:
126 if (isset($fieldarray['value'])) {
127 $ThisFileInfo['tiff']['ifd'][$IFDid]['fields'][$key]['raw']['data'] = $fieldarray['value'];
128 } else {
129 fseek($fd, $fieldarray[
'offset'], SEEK_SET);
130 $ThisFileInfo[
'tiff'][
'ifd'][$IFDid][
'fields'][$key][
'raw'][
'data'] =
fread($fd, $fieldarray[
'raw'][
'length'] * $FieldTypeByteLength[$fieldarray[
'raw'][
'type']]);
131
132 }
133 break;
134 }
135 switch ($fieldarray['raw']['tag']) {
136 case 256:
137 $ThisFileInfo['video']['resolution_x'] = $fieldarray['value'];
138 break;
139
140 case 257:
141 $ThisFileInfo['video']['resolution_y'] = $fieldarray['value'];
142 break;
143
144 case 258:
145 if (isset($fieldarray['value'])) {
146 $ThisFileInfo['video']['bits_per_sample'] = $fieldarray['value'];
147 } else {
148 $ThisFileInfo['video']['bits_per_sample'] = 0;
149 for ($i = 0; $i < $fieldarray['raw']['length']; $i++) {
150 $ThisFileInfo[
'video'][
'bits_per_sample'] += $this->
TIFFendian2Int(substr($ThisFileInfo[
'tiff'][
'ifd'][$IFDid][
'fields'][$key][
'raw'][
'data'], $i * $FieldTypeByteLength[$fieldarray[
'raw'][
'type']], $FieldTypeByteLength[$fieldarray[
'raw'][
'type']]), $ThisFileInfo[
'tiff'][
'byte_order']);
151 }
152 }
153 break;
154
155 case 259:
157 break;
158
159 case 270:
160 case 271:
161 case 272:
162 case 305:
163 case 306:
164 case 315:
165 case 316:
166 @$ThisFileInfo[
'tiff'][
'comments'][$this->
TIFFcommentName($fieldarray[
'raw'][
'tag'])][] = $ThisFileInfo[
'tiff'][
'ifd'][$IFDid][
'fields'][$key][
'raw'][
'data'];
167 break;
168
169 default:
170 break;
171 }
172 }
173 }
174
175 return true;
176 }