我正在尝试使用FreeImage.Net和C#将JPEG转换为带有JPEG压缩的TIFF。这个过程很顺利,但对于低质量的JPEG来说,TIFF文件比原始文件大得多。我认为TIFF大小不取决于原始JPEG质量,因为输出图像的大小总是大致相同。
例如(转换截图):
为了获取原始图像的信息,我使用了FreeImage,但是任何其他图像库也应该可以工作。
我知道可能还有一些我不知道的陷阱。它可能无法处理任何JPEG文件。此外,我不确定为什么我必须使用PhotometricInterpretation = 6和PlanarConfiguration = 1或其他一些字段的值。然而,它能够正常工作。
我想我的问题在于其他库会产生一个全新的JPEG文件,并且总是具有相同的质量(因为您只能将TIFF压缩设置为JPEG,但不能指定任何进一步的选项),然后将其包装到TIFF容器中。
我现在也知道,在TIFF中进行JPEG压缩并不是最好的选择(它是有损的,不常见且很少受支持,除了JPEG压缩的TIFF不比普通JPEG文件更好)。然而,我们的客户要求这样做。让我们看看上面的解决方案是否合适,或者我是否能找到其他东西。
例如(转换截图):
2065kb JPEG (quality: 100%) --> 1282kb TIFF
379kb JPEG (quality: 50%) --> 1200kb TIFF
我们公司不接受文件尺寸增加,因为我们和客户处理的文档数量很多。
有趣的是,当我使用GIMP转换图像时,结果差不多。现在我想知道:这是符合TIFF标准还是特殊于FreeImage/GIMP?(我认为两者都使用libtiff.dll)。
我想还有其他方法,因为我们公司有一台扫描仪,可以生成文件大小更小的JPEG压缩的TIFF图像。 有没有人知道其他库(免费或付费),可以更有效地处理此转换,或在FreeImage中实现此功能?
更新:
我查看了TIFF 6.0规范,分析了我们扫描仪生成的文件,并编写了一个函数,将JPEG包装到非常简单的TIFF容器中(也适用于多个合并为多页TIFF的JPEG)。
对于那些了解TIFF的人:我生成了一个新的TIFF文件(根据图像/页面数量生成一个或多个IFD),并将现有JPEG图像的原始数据写入单个条带中(每个IFD),使用以下字段/条目:
NewSubfileType = 0
ImageWidth = //(width of the original JPEG)
ImageLength = //(height of the original JPEG)
BitsPerSample = {8, 8, 8} //(count: 3)
Compression = 7 //(JPEG)
PhotometricInterpretation = 6 //(YCbCr)
StripOffsets = //(offset of raw JPEG data, count: 1)
SamplesPerPixel = 3
RowsPerStrip = //(height of the original JPEG)
StripByteCounts = //(length of raw JPEG data, count: 1)
XResolution = //(horizontal resolution of original JPEG data)
YResolution = //(vertical resolution of original JPEG data)
PlanarConfiguration = 1 (chunky)
ResolutionUnit = 2 //(Inch)
为了获取原始图像的信息,我使用了FreeImage,但是任何其他图像库也应该可以工作。
我知道可能还有一些我不知道的陷阱。它可能无法处理任何JPEG文件。此外,我不确定为什么我必须使用PhotometricInterpretation = 6和PlanarConfiguration = 1或其他一些字段的值。然而,它能够正常工作。
我想我的问题在于其他库会产生一个全新的JPEG文件,并且总是具有相同的质量(因为您只能将TIFF压缩设置为JPEG,但不能指定任何进一步的选项),然后将其包装到TIFF容器中。
我现在也知道,在TIFF中进行JPEG压缩并不是最好的选择(它是有损的,不常见且很少受支持,除了JPEG压缩的TIFF不比普通JPEG文件更好)。然而,我们的客户要求这样做。让我们看看上面的解决方案是否合适,或者我是否能找到其他东西。