parent
01e3f1fc33
commit
b3ff4d9ed6
@ -52,12 +52,24 @@
|
|||||||
|
|
||||||
#if defined(HAVE_MAGICK6) || defined(HAVE_MAGICK7)
|
#if defined(HAVE_MAGICK6) || defined(HAVE_MAGICK7)
|
||||||
|
|
||||||
/* ImageMagick can't detect some formats, like ICO, by examining the contents --
|
/* ImageMagick can't detect some formats, like ICO and TGA, by examining the contents --
|
||||||
* ico.c simply does not have a recogniser.
|
* ico.c and tga.c simply do not have recognisers.
|
||||||
*
|
*
|
||||||
* For these formats, do the detection ourselves.
|
* For these formats, do the detection ourselves.
|
||||||
*
|
|
||||||
* Return an IM format specifier, or NULL to let IM do the detection.
|
* Return an IM format specifier, or NULL to let IM do the detection.
|
||||||
|
*
|
||||||
|
* For sniffing TGAs, we check that there is at least enough room for the header and that
|
||||||
|
* the preamble contains valid values:
|
||||||
|
* -----------------------------------------------------------
|
||||||
|
* |0x00 | 0-255 idlength, skip |
|
||||||
|
* |0x01 | 0-1, color map present |
|
||||||
|
* |0x02 | Any of (0, 1, 2, 3, 9, 10, 11), Image type |
|
||||||
|
* -----------------------------------------------------------
|
||||||
|
*
|
||||||
|
* References:
|
||||||
|
* * https://www.dca.fee.unicamp.br/~martino/disciplinas/ea978/tgaffs.pdf
|
||||||
|
* * http://www.paulbourke.net/dataformats/tga/
|
||||||
|
* * https://en.wikipedia.org/wiki/Truevision_TGA#Technical_details
|
||||||
*/
|
*/
|
||||||
static const char *
|
static const char *
|
||||||
magick_sniff( const unsigned char *bytes, size_t length )
|
magick_sniff( const unsigned char *bytes, size_t length )
|
||||||
@ -68,6 +80,16 @@ magick_sniff( const unsigned char *bytes, size_t length )
|
|||||||
bytes[2] == 1 &&
|
bytes[2] == 1 &&
|
||||||
bytes[3] == 0 )
|
bytes[3] == 0 )
|
||||||
return( "ICO" );
|
return( "ICO" );
|
||||||
|
if( length >= 18 &&
|
||||||
|
(bytes[1] == 0 || bytes[1] == 1) && (
|
||||||
|
bytes[2] == 0 ||
|
||||||
|
bytes[2] == 1 ||
|
||||||
|
bytes[2] == 2 ||
|
||||||
|
bytes[2] == 3 ||
|
||||||
|
bytes[2] == 9 ||
|
||||||
|
bytes[2] == 10 ||
|
||||||
|
bytes[2] == 11) )
|
||||||
|
return( "TGA" );
|
||||||
|
|
||||||
return( NULL );
|
return( NULL );
|
||||||
}
|
}
|
||||||
|
@ -41,6 +41,8 @@ DICOM_FILE = os.path.join(IMAGES, "dicom_test_image.dcm")
|
|||||||
BMP_FILE = os.path.join(IMAGES, "MARBLES.BMP")
|
BMP_FILE = os.path.join(IMAGES, "MARBLES.BMP")
|
||||||
NIFTI_FILE = os.path.join(IMAGES, "avg152T1_LR_nifti.nii.gz")
|
NIFTI_FILE = os.path.join(IMAGES, "avg152T1_LR_nifti.nii.gz")
|
||||||
ICO_FILE = os.path.join(IMAGES, "favicon.ico")
|
ICO_FILE = os.path.join(IMAGES, "favicon.ico")
|
||||||
|
TGA_FILE = os.path.join(IMAGES, "targa.tga")
|
||||||
|
SGI_FILE = os.path.join(IMAGES, "silicongraphics.sgi")
|
||||||
AVIF_FILE = os.path.join(IMAGES, "avif-orientation-6.avif")
|
AVIF_FILE = os.path.join(IMAGES, "avif-orientation-6.avif")
|
||||||
HEIC_FILE = os.path.join(IMAGES, "heic-orientation-6.heic")
|
HEIC_FILE = os.path.join(IMAGES, "heic-orientation-6.heic")
|
||||||
RGBA_FILE = os.path.join(IMAGES, "rgba.png")
|
RGBA_FILE = os.path.join(IMAGES, "rgba.png")
|
||||||
|
BIN
test/test-suite/images/silicongraphics.sgi
Normal file
BIN
test/test-suite/images/silicongraphics.sgi
Normal file
Binary file not shown.
BIN
test/test-suite/images/targa.tga
Normal file
BIN
test/test-suite/images/targa.tga
Normal file
Binary file not shown.
@ -10,7 +10,7 @@ from helpers import \
|
|||||||
JPEG_FILE, SRGB_FILE, MATLAB_FILE, PNG_FILE, TIF_FILE, OME_FILE, \
|
JPEG_FILE, SRGB_FILE, MATLAB_FILE, PNG_FILE, TIF_FILE, OME_FILE, \
|
||||||
ANALYZE_FILE, GIF_FILE, WEBP_FILE, EXR_FILE, FITS_FILE, OPENSLIDE_FILE, \
|
ANALYZE_FILE, GIF_FILE, WEBP_FILE, EXR_FILE, FITS_FILE, OPENSLIDE_FILE, \
|
||||||
PDF_FILE, SVG_FILE, SVGZ_FILE, SVG_GZ_FILE, GIF_ANIM_FILE, DICOM_FILE, \
|
PDF_FILE, SVG_FILE, SVGZ_FILE, SVG_GZ_FILE, GIF_ANIM_FILE, DICOM_FILE, \
|
||||||
BMP_FILE, NIFTI_FILE, ICO_FILE, AVIF_FILE, TRUNCATED_FILE, \
|
BMP_FILE, NIFTI_FILE, ICO_FILE, TGA_FILE, SGI_FILE, AVIF_FILE, TRUNCATED_FILE, \
|
||||||
GIF_ANIM_EXPECTED_PNG_FILE, GIF_ANIM_DISPOSE_BACKGROUND_FILE, \
|
GIF_ANIM_EXPECTED_PNG_FILE, GIF_ANIM_DISPOSE_BACKGROUND_FILE, \
|
||||||
GIF_ANIM_DISPOSE_BACKGROUND_EXPECTED_PNG_FILE, \
|
GIF_ANIM_DISPOSE_BACKGROUND_EXPECTED_PNG_FILE, \
|
||||||
GIF_ANIM_DISPOSE_PREVIOUS_FILE, \
|
GIF_ANIM_DISPOSE_PREVIOUS_FILE, \
|
||||||
@ -664,6 +664,22 @@ class TestForeign:
|
|||||||
assert im.width == 16
|
assert im.width == 16
|
||||||
assert im.height == 16
|
assert im.height == 16
|
||||||
|
|
||||||
|
# libvips has its own sniffer for TGA, test that
|
||||||
|
with open(TGA_FILE, 'rb') as f:
|
||||||
|
buf = f.read()
|
||||||
|
im = pyvips.Image.new_from_buffer(buf, "")
|
||||||
|
assert im.width == 433
|
||||||
|
assert im.height == 433
|
||||||
|
|
||||||
|
# Test SGI/RGB files to sanity check that sniffers
|
||||||
|
# aren't too broad
|
||||||
|
with open(SGI_FILE, 'rb') as f:
|
||||||
|
buf = f.read()
|
||||||
|
im = pyvips.Image.new_from_buffer(buf, "")
|
||||||
|
assert im.width == 433
|
||||||
|
assert im.height == 433
|
||||||
|
|
||||||
|
|
||||||
# load should see metadata like eg. icc profiles
|
# load should see metadata like eg. icc profiles
|
||||||
im = pyvips.Image.magickload(JPEG_FILE)
|
im = pyvips.Image.magickload(JPEG_FILE)
|
||||||
assert len(im.get("icc-profile-data")) == 564
|
assert len(im.get("icc-profile-data")) == 564
|
||||||
|
Loading…
Reference in New Issue
Block a user