small cleanups to svgz support
This commit is contained in:
parent
fe615af233
commit
b0e3035590
@ -31,6 +31,7 @@
|
|||||||
- added vips_perlin(), generate Perlin noise
|
- added vips_perlin(), generate Perlin noise
|
||||||
- gif loader can write 1, 2, 3, or 4 bands depending on file contents
|
- gif loader can write 1, 2, 3, or 4 bands depending on file contents
|
||||||
- support --strip for pngsave
|
- support --strip for pngsave
|
||||||
|
- add svgz support [Felix Bünemann]
|
||||||
|
|
||||||
30/7/16 started 8.3.3
|
30/7/16 started 8.3.3
|
||||||
- fix performance regression in 8.3.2, thanks Lovell
|
- fix performance regression in 8.3.2, thanks Lovell
|
||||||
|
2
TODO
2
TODO
@ -1,3 +1,5 @@
|
|||||||
|
- can we hjave .svg.gz as a suffix? should be possible
|
||||||
|
|
||||||
- try:
|
- try:
|
||||||
|
|
||||||
$ vips avg broken.jpg[fail]
|
$ vips avg broken.jpg[fail]
|
||||||
|
@ -1061,6 +1061,7 @@ PDF import with poppler-glib: $with_poppler
|
|||||||
(requires poppler-glib 0.16.0 or later)
|
(requires poppler-glib 0.16.0 or later)
|
||||||
SVG import with librsvg-2.0: $with_rsvg
|
SVG import with librsvg-2.0: $with_rsvg
|
||||||
(requires librsvg-2.0 2.34.0 or later)
|
(requires librsvg-2.0 2.34.0 or later)
|
||||||
|
zlib: $with_zlib
|
||||||
file import with cfitsio: $with_cfitsio
|
file import with cfitsio: $with_cfitsio
|
||||||
file import/export with libwebp: $with_libwebp
|
file import/export with libwebp: $with_libwebp
|
||||||
(requires libwebp-0.1.3 or later)
|
(requires libwebp-0.1.3 or later)
|
||||||
|
@ -2,6 +2,8 @@
|
|||||||
*
|
*
|
||||||
* 7/2/16
|
* 7/2/16
|
||||||
* - from svgload.c
|
* - from svgload.c
|
||||||
|
* 1/8/16 felixbuenemann
|
||||||
|
* - add svgz support
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -54,14 +56,21 @@
|
|||||||
|
|
||||||
#include <cairo.h>
|
#include <cairo.h>
|
||||||
#include <librsvg/rsvg.h>
|
#include <librsvg/rsvg.h>
|
||||||
/* Old librsvg versions don't include librsvg-features.h by default,
|
|
||||||
* while newer versions deprecate direct inclusion.
|
/* Old librsvg versions don't include librsvg-features.h by default.
|
||||||
|
* Newer versions deprecate direct inclusion.
|
||||||
*/
|
*/
|
||||||
#ifndef LIBRSVG_FEATURES_H
|
#ifndef LIBRSVG_FEATURES_H
|
||||||
#include <librsvg/librsvg-features.h>
|
#include <librsvg/librsvg-features.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* A handy #define for we-will-handle-svgz.
|
||||||
|
*/
|
||||||
#if LIBRSVG_CHECK_FEATURE(SVGZ) && defined(HAVE_ZLIB)
|
#if LIBRSVG_CHECK_FEATURE(SVGZ) && defined(HAVE_ZLIB)
|
||||||
|
#define HANDLE_SVGZ
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef HANDLE_SVGZ
|
||||||
#include <zlib.h>
|
#include <zlib.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@ -325,6 +334,8 @@ vips_foreign_load_svg_file_header( VipsForeignLoad *load )
|
|||||||
|
|
||||||
static const char *vips_foreign_svg_suffs[] = {
|
static const char *vips_foreign_svg_suffs[] = {
|
||||||
".svg",
|
".svg",
|
||||||
|
/* librsvg supports svgz directly, no need to check for zlib here.
|
||||||
|
*/
|
||||||
#if LIBRSVG_CHECK_FEATURE(SVGZ)
|
#if LIBRSVG_CHECK_FEATURE(SVGZ)
|
||||||
".svgz",
|
".svgz",
|
||||||
#endif
|
#endif
|
||||||
@ -377,65 +388,77 @@ typedef VipsForeignLoadSvgClass VipsForeignLoadSvgBufferClass;
|
|||||||
G_DEFINE_TYPE( VipsForeignLoadSvgBuffer, vips_foreign_load_svg_buffer,
|
G_DEFINE_TYPE( VipsForeignLoadSvgBuffer, vips_foreign_load_svg_buffer,
|
||||||
vips_foreign_load_svg_get_type() );
|
vips_foreign_load_svg_get_type() );
|
||||||
|
|
||||||
#if LIBRSVG_CHECK_FEATURE(SVGZ) && defined(HAVE_ZLIB)
|
#ifdef HANDLE_SVGZ
|
||||||
static void *
|
static void *
|
||||||
vips_zalloc( void *opaque, unsigned items, unsigned size )
|
vips_foreign_load_svg_zalloc( void *opaque, unsigned items, unsigned size )
|
||||||
{
|
{
|
||||||
return( g_malloc0_n( items, size ) );
|
return( g_malloc0_n( items, size ) );
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
vips_zfree( void *opaque, void *ptr )
|
vips_foreign_load_svg_zfree( void *opaque, void *ptr )
|
||||||
{
|
{
|
||||||
return( g_free( ptr ) );
|
return( g_free( ptr ) );
|
||||||
}
|
}
|
||||||
#endif
|
#endif /*HANDLE_SVGZ*/
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
vips_foreign_load_svg_is_a_buffer( const void *buf, size_t len )
|
vips_foreign_load_svg_is_a_buffer( const void *buf, size_t len )
|
||||||
{
|
{
|
||||||
unsigned char *str = (unsigned char *) buf;
|
char *str;
|
||||||
|
|
||||||
|
#ifdef HANDLE_SVGZ
|
||||||
|
/* If the buffer looks like a zip, deflate to here and then search
|
||||||
|
* that for <svg.
|
||||||
|
*/
|
||||||
|
char obuf[224];
|
||||||
|
#endif /*HANDLE_SVGZ*/
|
||||||
|
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
#if LIBRSVG_CHECK_FEATURE(SVGZ) && defined(HAVE_ZLIB)
|
/* Start with str pointing at the argument buffer, swap to it pointing
|
||||||
|
* into obuf if we see zip data.
|
||||||
|
*/
|
||||||
|
str = (char *) buf;
|
||||||
|
|
||||||
|
#ifdef HANDLE_SVGZ
|
||||||
/* Check for SVGZ gzip signature and inflate.
|
/* Check for SVGZ gzip signature and inflate.
|
||||||
|
*
|
||||||
* Minimum gzip size is 18 bytes, starting with 1F 8B.
|
* Minimum gzip size is 18 bytes, starting with 1F 8B.
|
||||||
*/
|
*/
|
||||||
if( len >= 18 && str[0] == 0x1f && str[1] == 0x8b ) {
|
if( len >= 18 &&
|
||||||
|
str[0] == '\037' &&
|
||||||
|
str[1] == '\213' ) {
|
||||||
z_stream zs;
|
z_stream zs;
|
||||||
size_t opos = 0;
|
size_t opos;
|
||||||
unsigned char obuf[224];
|
|
||||||
|
|
||||||
zs.zalloc = (alloc_func) vips_zalloc;
|
zs.zalloc = (alloc_func) vips_foreign_load_svg_zalloc;
|
||||||
zs.zfree = (free_func) vips_zfree;
|
zs.zfree = (free_func) vips_foreign_load_svg_zfree;
|
||||||
zs.opaque = Z_NULL;
|
zs.opaque = Z_NULL;
|
||||||
zs.next_in = str;
|
zs.next_in = (unsigned char *) str;
|
||||||
zs.avail_in = len;
|
zs.avail_in = len;
|
||||||
|
|
||||||
if( inflateInit2(&zs, 15 | 32) != Z_OK ) {
|
/* There isn't really an error return from is_a_buffer()
|
||||||
vips_error( "svgload",
|
*/
|
||||||
"%s", _( "Zlib init failed" ) );
|
if( inflateInit2( &zs, 15 | 32 ) != Z_OK )
|
||||||
return( -1 );
|
return( FALSE );
|
||||||
}
|
|
||||||
|
|
||||||
|
opos = 0;
|
||||||
do {
|
do {
|
||||||
zs.avail_out = sizeof(obuf) - opos;
|
zs.avail_out = sizeof( obuf ) - opos;
|
||||||
zs.next_out = obuf + opos;
|
zs.next_out = (unsigned char *) obuf + opos;
|
||||||
if( inflate(&zs, Z_NO_FLUSH) < Z_OK ) {
|
if( inflate( &zs, Z_NO_FLUSH ) < Z_OK )
|
||||||
vips_error( "svgload",
|
return( FALSE );
|
||||||
"%s", _( "Zlib inflate failed" ) );
|
opos = sizeof( obuf ) - zs.avail_out;
|
||||||
return( -1 );
|
} while( opos < sizeof( obuf ) &&
|
||||||
}
|
zs.avail_in > 0 );
|
||||||
opos = sizeof(obuf) - zs.avail_out;
|
|
||||||
} while( opos < sizeof(obuf) && zs.avail_out == 0 );
|
|
||||||
|
|
||||||
inflateEnd(&zs);
|
inflateEnd( &zs );
|
||||||
|
|
||||||
str = obuf;
|
str = obuf;
|
||||||
len = opos;
|
len = opos;
|
||||||
}
|
}
|
||||||
#endif
|
#endif /*HANDLE_SVGZ*/
|
||||||
|
|
||||||
/* SVG documents are very freeform. They normally look like:
|
/* SVG documents are very freeform. They normally look like:
|
||||||
*
|
*
|
||||||
@ -456,14 +479,13 @@ vips_foreign_load_svg_is_a_buffer( const void *buf, size_t len )
|
|||||||
return( 0 );
|
return( 0 );
|
||||||
for( i = 0; i < 24; i++ )
|
for( i = 0; i < 24; i++ )
|
||||||
if( !isascii( str[i] ) )
|
if( !isascii( str[i] ) )
|
||||||
return( 0 );
|
return( FALSE );
|
||||||
|
|
||||||
for( i = 0; i < 200 && i < len - 5; i++ ) {
|
for( i = 0; i < 200 && i < len - 5; i++ )
|
||||||
if( strncmp( (const char *) str + i, "<svg", 4 ) == 0 )
|
if( strncasecmp( str + i, "<svg", 4 ) == 0 )
|
||||||
return( 1 );
|
return( TRUE );
|
||||||
}
|
|
||||||
|
|
||||||
return( 0 );
|
return( FALSE );
|
||||||
}
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
|
Loading…
Reference in New Issue
Block a user