Browse Source

tiff: fixed decompressing packbits, skip jpeg tags

git-svn-id: trunk@21514 -
Mattias Gaertner 13 years ago
parent
commit
fd18003cd6
1 changed files with 122 additions and 25 deletions
  1. 122 25
      packages/fcl-image/src/fpreadtiff.pas

+ 122 - 25
packages/fcl-image/src/fpreadtiff.pas

@@ -1165,6 +1165,96 @@ begin
         writeln('TFPReaderTiff.ReadDirectoryEntry Tag 347: skipping JPEG Tables');
       {$endif}
     end;
+  512:
+    begin
+      // ToDo: JPEGProc
+      // short
+      // 1 = baseline sequential
+      // 14 = lossless process with Huffman encoding
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 512: skipping JPEGProc');
+      {$endif}
+    end;
+  513:
+    begin
+      // ToDo: JPEGInterchangeFormat
+      // long
+      // non zero: start of start of image SOI marker
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 513: skipping JPEGInterchangeFormat');
+      {$endif}
+    end;
+  514:
+    begin
+      // ToDo: JPEGInterchangeFormatLength
+      // long
+      // length in bytes of 513
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 514: skipping JPEGInterchangeFormatLength');
+      {$endif}
+    end;
+  515:
+    begin
+      // ToDo: JPEGRestartInterval
+      // short
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 515: skipping JPEGRestartInterval');
+      {$endif}
+    end;
+  517:
+    begin
+      // ToDo: JPEGLosslessPredictor
+      // short
+      // Count: SamplesPerPixels
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 517: skipping JPEGLosslessPredictor');
+      {$endif}
+    end;
+  518:
+    begin
+      // ToDo: JPEGPointTransforms
+      // short
+      // Count: SamplesPerPixels
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 518: skipping JPEGPointTransforms');
+      {$endif}
+    end;
+  519:
+    begin
+      // ToDo: JPEGQTables
+      // long
+      // Count: SamplesPerPixels
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 519: skipping JPEGQTables');
+      {$endif}
+    end;
+  520:
+    begin
+      // ToDo: JPEGDCTables
+      // long
+      // Count: SamplesPerPixels
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 520: skipping JPEGDCTables');
+      {$endif}
+    end;
+  521:
+    begin
+      // ToDo: JPEGACTables
+      // long
+      // Count: SamplesPerPixels
+      {$ifdef FPC_Debug_Image}
+      if Debug then
+        writeln('TFPReaderTiff.ReadDirectoryEntry Tag 521: skipping JPEGACTables');
+      {$endif}
+    end;
   530:
     begin
       // ToDo: YCbCrSubSampling alias ChromaSubSampling
@@ -1859,61 +1949,68 @@ end;
 
 procedure DecompressPackBits(Buffer: Pointer; Count: PtrInt; out
   NewBuffer: Pointer; out NewCount: PtrInt);
+{ Algorithm:
+    while not got the expected number of bytes
+      read one byte n
+      if n in 0..127 copy the next n+1 bytes
+      else if n in -127..-1 then copy the next byte 1-n times
+      else continue
+    end
+}
 var
   p: Pcint8;
   n: cint8;
-  SrcStep: PtrInt;
-  i: PtrInt;
   d: pcint8;
-  j: ShortInt;
+  i,j: integer;
+  EndP: Pcint8;
 begin
   // compute NewCount
   NewCount:=0;
   NewBuffer:=nil;
+  if Count=0 then exit;
   p:=Pcint8(Buffer);
-  i:=Count;
-  while i>0 do begin
+  EndP:=p+Count;
+  while p<EndP do begin
     n:=p^;
     case n of
-    0..127:   begin inc(NewCount,n+1);  SrcStep:=n+2; end; // copy the next n+1 bytes
-    -127..-1: begin inc(NewCount,-n+1); SrcStep:=2;   end; // copy the next byte n+1 times
-    else SrcStep:=1; // noop
+    0..127:   begin inc(NewCount,n+1);  inc(p,n+2); end; // copy the next n+1 bytes
+    -127..-1: begin inc(NewCount,1-n); inc(p,2);   end; // copy the next byte 1-n times
+    else inc(p); // noop
     end;
-    inc(p,SrcStep);
-    dec(i,SrcStep);
   end;
 
   // decompress
   if NewCount=0 then exit;
   GetMem(NewBuffer,NewCount);
-  i:=Count;
   p:=Pcint8(Buffer);
   d:=Pcint8(NewBuffer);
-  while i>0 do begin
+  while p<EndP do begin
     n:=p^;
     case n of
     0..127:
       begin
         // copy the next n+1 bytes
-        inc(NewCount,n+1);  SrcStep:=n+2;
-        System.Move(p[1],d^,n+1);
-        inc(d,n+1);
+        i:=n+1;
+        inc(NewCount,i);
+        inc(p);
+        System.Move(p,d^,i);
+        inc(p,i);
+        inc(d,i);
       end;
     -127..-1:
       begin
-        // copy the next byte n+1 times
-        inc(NewCount,-n+1); SrcStep:=2;
-        j:=-n;
-        n:=p[1];
-        while j>=0 do begin
+        // copy the next byte 1-n times
+        i:=1-n;
+        inc(NewCount,i);
+        inc(p);
+        n:=p^;
+        for j:=0 to i-1 do
           d[j]:=n;
-          dec(j);
-        end;
+        inc(d,i);
+        inc(p);
       end;
-    else SrcStep:=1; // noop
+    else inc(p); // noop
     end;
-    inc(p,SrcStep);
-    dec(i,SrcStep);
   end;
 end;