fix matlab block test
This commit is contained in:
parent
cf97ea3ea1
commit
d17fd9b640
@ -7,7 +7,7 @@
|
||||
/*
|
||||
|
||||
This file is part of VIPS.
|
||||
|
||||
|
||||
VIPS is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU Lesser General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
@ -107,7 +107,7 @@ typedef struct _VipsForeignSaveJp2k {
|
||||
*/
|
||||
gboolean subsample;
|
||||
|
||||
/* If we converto RGB to YCC during save.
|
||||
/* If we convert RGB to YCC during save.
|
||||
*/
|
||||
gboolean save_as_ycc;
|
||||
|
||||
@ -118,7 +118,7 @@ typedef struct _VipsForeignSaveJp2k {
|
||||
|
||||
typedef VipsForeignSaveClass VipsForeignSaveJp2kClass;
|
||||
|
||||
G_DEFINE_ABSTRACT_TYPE( VipsForeignSaveJp2k, vips_foreign_save_jp2k,
|
||||
G_DEFINE_ABSTRACT_TYPE( VipsForeignSaveJp2k, vips_foreign_save_jp2k,
|
||||
VIPS_TYPE_FOREIGN_SAVE );
|
||||
|
||||
static void
|
||||
@ -160,25 +160,25 @@ vips_foreign_save_jp2k_target( VipsTarget *target )
|
||||
|
||||
/* FALSE means a write stream.
|
||||
*/
|
||||
if( !(stream = opj_stream_create( OPJ_J2K_STREAM_CHUNK_SIZE, FALSE )) )
|
||||
if( !(stream = opj_stream_create( OPJ_J2K_STREAM_CHUNK_SIZE, FALSE )) )
|
||||
return( NULL );
|
||||
|
||||
opj_stream_set_user_data( stream, target, NULL );
|
||||
opj_stream_set_write_function( stream,
|
||||
opj_stream_set_write_function( stream,
|
||||
vips_foreign_save_jp2k_write_target );
|
||||
|
||||
return( stream );
|
||||
}
|
||||
|
||||
static void
|
||||
static void
|
||||
vips_foreign_save_jp2k_error_callback( const char *msg, void *client )
|
||||
{
|
||||
vips_error( "jp2ksave", "%s", msg );
|
||||
vips_error( "jp2ksave", "%s", msg );
|
||||
}
|
||||
|
||||
/* The openjpeg info and warning callbacks are incredibly chatty.
|
||||
*/
|
||||
static void
|
||||
static void
|
||||
vips_foreign_save_jp2k_warning_callback( const char *msg, void *client )
|
||||
{
|
||||
#ifdef DEBUG
|
||||
@ -186,7 +186,7 @@ vips_foreign_save_jp2k_warning_callback( const char *msg, void *client )
|
||||
#endif /*DEBUG*/
|
||||
}
|
||||
|
||||
static void
|
||||
static void
|
||||
vips_foreign_save_jp2k_info_callback( const char *msg, void *client )
|
||||
{
|
||||
#ifdef DEBUG
|
||||
@ -199,9 +199,9 @@ vips_foreign_save_jp2k_attach_handlers( opj_codec_t *codec )
|
||||
{
|
||||
opj_set_info_handler( codec,
|
||||
vips_foreign_save_jp2k_info_callback, NULL );
|
||||
opj_set_warning_handler( codec,
|
||||
opj_set_warning_handler( codec,
|
||||
vips_foreign_save_jp2k_warning_callback, NULL );
|
||||
opj_set_error_handler( codec,
|
||||
opj_set_error_handler( codec,
|
||||
vips_foreign_save_jp2k_error_callback, NULL );
|
||||
}
|
||||
|
||||
@ -233,8 +233,8 @@ vips_foreign_save_jp2k_attach_handlers( opj_codec_t *codec )
|
||||
/* In-place RGB->YCC for a line of pels.
|
||||
*/
|
||||
static void
|
||||
vips_foreign_save_jp2k_rgb_to_ycc( VipsRegion *region,
|
||||
VipsRect *tile, int prec )
|
||||
vips_foreign_save_jp2k_rgb_to_ycc( VipsRegion *region,
|
||||
VipsRect *tile, int prec )
|
||||
{
|
||||
VipsImage *im = region->im;
|
||||
int offset = 1 << (prec - 1);
|
||||
@ -245,7 +245,7 @@ vips_foreign_save_jp2k_rgb_to_ycc( VipsRegion *region,
|
||||
g_assert( im->Bands == 3 );
|
||||
|
||||
for( y = 0; y < tile->height; y++ ) {
|
||||
VipsPel *q = VIPS_REGION_ADDR( region,
|
||||
VipsPel *q = VIPS_REGION_ADDR( region,
|
||||
tile->left, tile->top + y );
|
||||
|
||||
switch( im->BandFmt ) {
|
||||
@ -330,14 +330,14 @@ vips_foreign_save_jp2k_unpack_subsample( VipsRegion *region, VipsRect *tile,
|
||||
/* The number of pixels we write for this component. No
|
||||
* padding.
|
||||
*/
|
||||
int output_width = VIPS_ROUND_UINT(
|
||||
int output_width = VIPS_ROUND_UINT(
|
||||
(double) tile->width / comp->dx );
|
||||
int output_height = VIPS_ROUND_UINT(
|
||||
int output_height = VIPS_ROUND_UINT(
|
||||
(double) tile->height / comp->dy );;
|
||||
|
||||
for( y = 0; y < output_height; y++ ) {
|
||||
VipsPel *p = i * sizeof_element +
|
||||
VIPS_REGION_ADDR( region,
|
||||
VipsPel *p = i * sizeof_element +
|
||||
VIPS_REGION_ADDR( region,
|
||||
tile->left, tile->top + y * comp->dy );
|
||||
|
||||
/* Shrink a line of pels to q.
|
||||
@ -400,11 +400,11 @@ vips_foreign_save_jp2k_unpack( VipsRegion *region, VipsRect *tile,
|
||||
int x, y, i;
|
||||
|
||||
for( y = 0; y < tile->height; y++ ) {
|
||||
VipsPel *p = VIPS_REGION_ADDR( region,
|
||||
VipsPel *p = VIPS_REGION_ADDR( region,
|
||||
tile->left, tile->top + y );
|
||||
|
||||
for( i = 0; i < b; i++ ) {
|
||||
VipsPel *q = tile_buffer +
|
||||
VipsPel *q = tile_buffer +
|
||||
i * sizeof_tile + y * sizeof_line;
|
||||
|
||||
switch( im->BandFmt ) {
|
||||
@ -447,9 +447,9 @@ vips_foreign_save_jp2k_sizeof_tile( VipsForeignSaveJp2k *jp2k, VipsRect *tile )
|
||||
/* The number of pixels we write for this component. Round to
|
||||
* nearest, and we may have to write half-pixels at the edges.
|
||||
*/
|
||||
int output_width = VIPS_ROUND_UINT(
|
||||
int output_width = VIPS_ROUND_UINT(
|
||||
(double) tile->width / comp->dx );
|
||||
int output_height = VIPS_ROUND_UINT(
|
||||
int output_height = VIPS_ROUND_UINT(
|
||||
(double) tile->height / comp->dy );;
|
||||
|
||||
size += output_width * output_height * sizeof_element;
|
||||
@ -479,25 +479,25 @@ vips_foreign_save_jp2k_write_tiles( VipsForeignSaveJp2k *jp2k )
|
||||
tile.height = jp2k->tile_height;
|
||||
vips_rect_intersectrect( &tile, &jp2k->strip->valid, &tile );
|
||||
|
||||
if( jp2k->save_as_ycc )
|
||||
vips_foreign_save_jp2k_rgb_to_ycc( jp2k->strip,
|
||||
&tile, jp2k->image->comps[0].prec );
|
||||
if( jp2k->save_as_ycc )
|
||||
vips_foreign_save_jp2k_rgb_to_ycc( jp2k->strip,
|
||||
&tile, jp2k->image->comps[0].prec );
|
||||
|
||||
if( jp2k->subsample )
|
||||
vips_foreign_save_jp2k_unpack_subsample( jp2k->strip,
|
||||
&tile, jp2k->image,
|
||||
jp2k->tile_buffer, jp2k->accumulate );
|
||||
vips_foreign_save_jp2k_unpack_subsample( jp2k->strip,
|
||||
&tile, jp2k->image,
|
||||
jp2k->tile_buffer, jp2k->accumulate );
|
||||
else
|
||||
vips_foreign_save_jp2k_unpack( jp2k->strip,
|
||||
&tile, jp2k->image,
|
||||
vips_foreign_save_jp2k_unpack( jp2k->strip,
|
||||
&tile, jp2k->image,
|
||||
jp2k->tile_buffer );
|
||||
|
||||
sizeof_tile =
|
||||
sizeof_tile =
|
||||
vips_foreign_save_jp2k_sizeof_tile( jp2k, &tile );
|
||||
tile_index = tiles_across * tile.top / jp2k->tile_height +
|
||||
x / jp2k->tile_width;
|
||||
if( !opj_write_tile( jp2k->codec, tile_index,
|
||||
(VipsPel *) jp2k->tile_buffer, sizeof_tile,
|
||||
if( !opj_write_tile( jp2k->codec, tile_index,
|
||||
(VipsPel *) jp2k->tile_buffer, sizeof_tile,
|
||||
jp2k->stream ) )
|
||||
return( -1 );
|
||||
}
|
||||
@ -506,14 +506,14 @@ vips_foreign_save_jp2k_write_tiles( VipsForeignSaveJp2k *jp2k )
|
||||
}
|
||||
|
||||
static int
|
||||
vips_foreign_save_jp2k_write_block( VipsRegion *region, VipsRect *area,
|
||||
vips_foreign_save_jp2k_write_block( VipsRegion *region, VipsRect *area,
|
||||
void *a )
|
||||
{
|
||||
VipsForeignSaveJp2k *jp2k = (VipsForeignSaveJp2k *) a;
|
||||
VipsForeignSave *save = (VipsForeignSave *) jp2k;
|
||||
|
||||
#ifdef DEBUG_VERBOSE
|
||||
printf( "vips_foreign_save_jp2k_write_block: y = %d, nlines = %d\n",
|
||||
printf( "vips_foreign_save_jp2k_write_block: y = %d, nlines = %d\n",
|
||||
area->top, area->height );
|
||||
#endif /*DEBUG_VERBOSE*/
|
||||
|
||||
@ -525,20 +525,20 @@ vips_foreign_save_jp2k_write_block( VipsRegion *region, VipsRect *area,
|
||||
VipsRect image;
|
||||
|
||||
/* The intersection with the strip is the fresh pixels we
|
||||
* have.
|
||||
* have.
|
||||
*/
|
||||
vips_rect_intersectrect( area, to, &hit );
|
||||
|
||||
/* Write the new pixels into the strip.
|
||||
*/
|
||||
vips_region_copy( region, jp2k->strip,
|
||||
vips_region_copy( region, jp2k->strip,
|
||||
&hit, hit.left, hit.top );
|
||||
|
||||
/* Have we failed to reach the bottom of the strip? We must
|
||||
* have run out of fresh pixels, so we are done.
|
||||
*/
|
||||
if( VIPS_RECT_BOTTOM( &hit ) !=
|
||||
VIPS_RECT_BOTTOM( &jp2k->strip->valid ) )
|
||||
if( VIPS_RECT_BOTTOM( &hit ) !=
|
||||
VIPS_RECT_BOTTOM( &jp2k->strip->valid ) )
|
||||
break;
|
||||
|
||||
/* We have reached the bottom of the strip. Write this line of
|
||||
@ -578,7 +578,7 @@ vips_foreign_save_jp2k_write_block( VipsRegion *region, VipsRect *area,
|
||||
* that always allocates memory for each channel, and we don't want that when
|
||||
* we are doing tiled write.
|
||||
*/
|
||||
static opj_image_t *
|
||||
static opj_image_t *
|
||||
vips_opj_image_create( OPJ_UINT32 numcmpts,
|
||||
opj_image_cmptparm_t *cmptparms, OPJ_COLOR_SPACE clrspc,
|
||||
gboolean allocate )
|
||||
@ -610,7 +610,7 @@ vips_opj_image_create( OPJ_UINT32 numcmpts,
|
||||
comp->sgnd = cmptparms[compno].sgnd;
|
||||
|
||||
if( comp->h != 0 &&
|
||||
(OPJ_SIZE_T) comp->w > SIZE_MAX / comp->h /
|
||||
(OPJ_SIZE_T) comp->w > SIZE_MAX / comp->h /
|
||||
sizeof( OPJ_INT32 ) ) {
|
||||
opj_image_destroy( image );
|
||||
return( NULL );
|
||||
@ -619,7 +619,7 @@ vips_opj_image_create( OPJ_UINT32 numcmpts,
|
||||
/* Allocation is optional.
|
||||
*/
|
||||
if( allocate ) {
|
||||
size_t bytes = (size_t) comp->w * comp->h *
|
||||
size_t bytes = (size_t) comp->w * comp->h *
|
||||
sizeof( OPJ_INT32 );
|
||||
|
||||
comp->data = (OPJ_INT32*) opj_image_data_alloc( bytes );
|
||||
@ -635,8 +635,8 @@ vips_opj_image_create( OPJ_UINT32 numcmpts,
|
||||
}
|
||||
|
||||
static opj_image_t *
|
||||
vips_foreign_save_jp2k_new_image( VipsImage *im,
|
||||
int width, int height,
|
||||
vips_foreign_save_jp2k_new_image( VipsImage *im,
|
||||
int width, int height,
|
||||
gboolean subsample, gboolean save_as_ycc, gboolean allocate )
|
||||
{
|
||||
OPJ_COLOR_SPACE color_space;
|
||||
@ -709,7 +709,7 @@ vips_foreign_save_jp2k_new_image( VipsImage *im,
|
||||
comps[i].sgnd = !vips_band_format_isuint( im->BandFmt );
|
||||
}
|
||||
|
||||
image = vips_opj_image_create( im->Bands, comps, color_space,
|
||||
image = vips_opj_image_create( im->Bands, comps, color_space,
|
||||
allocate );
|
||||
image->x1 = width;
|
||||
image->y1 = height;
|
||||
@ -722,14 +722,14 @@ vips_foreign_save_jp2k_new_image( VipsImage *im,
|
||||
return( image );
|
||||
}
|
||||
|
||||
/* Compression profile derived from the BM's recommenadations, see:
|
||||
/* Compression profile derived from the BM's recommendations, see:
|
||||
*
|
||||
* https://purl.pt/24107/1/iPres2013_PDF/An%20Analysis%20of%20Contemporary%20JPEG2000%20Codecs%20for%20Image%20Format%20Migration.pdf
|
||||
*
|
||||
* Some of these settings (eg. numresolution) are overridden later.
|
||||
*/
|
||||
static void
|
||||
vips_foreign_save_jp2k_set_profile( opj_cparameters_t *parameters,
|
||||
vips_foreign_save_jp2k_set_profile( opj_cparameters_t *parameters,
|
||||
gboolean lossless, int Q )
|
||||
{
|
||||
if( lossless )
|
||||
@ -758,7 +758,7 @@ vips_foreign_save_jp2k_set_profile( opj_cparameters_t *parameters,
|
||||
parameters->csty = 1;
|
||||
|
||||
parameters->res_spec = 7;
|
||||
for( i = 0; i < parameters->res_spec; i++ ) {
|
||||
for( i = 0; i < parameters->res_spec; i++ ) {
|
||||
parameters->prch_init[i] = 256;
|
||||
parameters->prcw_init[i] = 256;
|
||||
parameters->tcp_distoratio[i] = Q + 10 * i;
|
||||
@ -815,17 +815,17 @@ vips_foreign_save_jp2k_build( VipsObject *object )
|
||||
break;
|
||||
}
|
||||
|
||||
if( jp2k->subsample )
|
||||
if( jp2k->subsample )
|
||||
jp2k->save_as_ycc = TRUE;
|
||||
|
||||
/* Set parameters for compressor.
|
||||
*/
|
||||
*/
|
||||
opj_set_default_encoder_parameters( &jp2k->parameters );
|
||||
|
||||
/* Set compression profile.
|
||||
*/
|
||||
vips_foreign_save_jp2k_set_profile( &jp2k->parameters,
|
||||
jp2k->lossless, jp2k->Q );
|
||||
vips_foreign_save_jp2k_set_profile( &jp2k->parameters,
|
||||
jp2k->lossless, jp2k->Q );
|
||||
|
||||
/* Always tile.
|
||||
*/
|
||||
@ -840,11 +840,11 @@ vips_foreign_save_jp2k_build( VipsObject *object )
|
||||
/* Number of layers to write. Smallest layer is c. 2^5 on the smallest
|
||||
* axis.
|
||||
*/
|
||||
jp2k->parameters.numresolution = VIPS_MAX( 1,
|
||||
log( VIPS_MIN( save->ready->Xsize, save->ready->Ysize ) ) /
|
||||
jp2k->parameters.numresolution = VIPS_MAX( 1,
|
||||
log( VIPS_MIN( save->ready->Xsize, save->ready->Ysize ) ) /
|
||||
log( 2 ) - 5 );
|
||||
#ifdef DEBUG
|
||||
printf( "vips_foreign_save_jp2k_build: numresolutions = %d\n",
|
||||
printf( "vips_foreign_save_jp2k_build: numresolutions = %d\n",
|
||||
jp2k->parameters.numresolution );
|
||||
#endif /*DEBUG*/
|
||||
|
||||
@ -853,14 +853,14 @@ vips_foreign_save_jp2k_build( VipsObject *object )
|
||||
|
||||
jp2k->codec = opj_create_compress( OPJ_CODEC_J2K );
|
||||
vips_foreign_save_jp2k_attach_handlers( jp2k->codec );
|
||||
/* FALSE means don't alloc memory for image planes (we write in
|
||||
/* FALSE means don't alloc memory for image planes (we write in
|
||||
* tiles, not whole images).
|
||||
*/
|
||||
if( !(jp2k->image = vips_foreign_save_jp2k_new_image( save->ready,
|
||||
save->ready->Xsize, save->ready->Ysize,
|
||||
save->ready->Xsize, save->ready->Ysize,
|
||||
jp2k->subsample, jp2k->save_as_ycc, FALSE )) )
|
||||
return( -1 );
|
||||
if( !opj_setup_encoder( jp2k->codec, &jp2k->parameters, jp2k->image ) )
|
||||
if( !opj_setup_encoder( jp2k->codec, &jp2k->parameters, jp2k->image ) )
|
||||
return( -1 );
|
||||
|
||||
opj_codec_set_threads( jp2k->codec, vips_concurrency_get() );
|
||||
@ -898,10 +898,10 @@ vips_foreign_save_jp2k_build( VipsObject *object )
|
||||
strip_position.top = 0;
|
||||
strip_position.width = save->ready->Xsize;
|
||||
strip_position.height = jp2k->tile_height;
|
||||
if( vips_region_buffer( jp2k->strip, &strip_position ) )
|
||||
if( vips_region_buffer( jp2k->strip, &strip_position ) )
|
||||
return( -1 );
|
||||
|
||||
/* Write data.
|
||||
/* Write data.
|
||||
*/
|
||||
if( vips_sink_disc( save->ready,
|
||||
vips_foreign_save_jp2k_write_block, jp2k ) )
|
||||
@ -935,26 +935,26 @@ vips_foreign_save_jp2k_class_init( VipsForeignSaveJp2kClass *class )
|
||||
|
||||
save_class->saveable = VIPS_SAVEABLE_ANY;
|
||||
|
||||
VIPS_ARG_INT( class, "tile_width", 11,
|
||||
_( "Tile width" ),
|
||||
VIPS_ARG_INT( class, "tile_width", 11,
|
||||
_( "Tile width" ),
|
||||
_( "Tile width in pixels" ),
|
||||
VIPS_ARGUMENT_OPTIONAL_INPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2k, tile_width ),
|
||||
1, 32768, 512 );
|
||||
|
||||
VIPS_ARG_INT( class, "tile_height", 12,
|
||||
_( "Tile height" ),
|
||||
VIPS_ARG_INT( class, "tile_height", 12,
|
||||
_( "Tile height" ),
|
||||
_( "Tile height in pixels" ),
|
||||
VIPS_ARGUMENT_OPTIONAL_INPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2k, tile_height ),
|
||||
1, 32768, 512 );
|
||||
|
||||
VIPS_ARG_BOOL( class, "lossless", 13,
|
||||
_( "Lossless" ),
|
||||
VIPS_ARG_BOOL( class, "lossless", 13,
|
||||
_( "Lossless" ),
|
||||
_( "Enable lossless compression" ),
|
||||
VIPS_ARGUMENT_OPTIONAL_INPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2k, lossless ),
|
||||
FALSE );
|
||||
FALSE );
|
||||
|
||||
VIPS_ARG_ENUM( class, "subsample_mode", 19,
|
||||
_( "Subsample mode" ),
|
||||
@ -962,10 +962,10 @@ vips_foreign_save_jp2k_class_init( VipsForeignSaveJp2kClass *class )
|
||||
VIPS_ARGUMENT_OPTIONAL_INPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2k, subsample_mode ),
|
||||
VIPS_TYPE_FOREIGN_SUBSAMPLE,
|
||||
VIPS_FOREIGN_SUBSAMPLE_AUTO );
|
||||
VIPS_FOREIGN_SUBSAMPLE_OFF );
|
||||
|
||||
VIPS_ARG_INT( class, "Q", 14,
|
||||
_( "Q" ),
|
||||
VIPS_ARG_INT( class, "Q", 14,
|
||||
_( "Q" ),
|
||||
_( "Q factor" ),
|
||||
VIPS_ARGUMENT_OPTIONAL_INPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2k, Q ),
|
||||
@ -983,7 +983,7 @@ vips_foreign_save_jp2k_init( VipsForeignSaveJp2k *jp2k )
|
||||
*/
|
||||
jp2k->Q = 48;
|
||||
|
||||
jp2k->subsample_mode = VIPS_FOREIGN_SUBSAMPLE_AUTO;
|
||||
jp2k->subsample_mode = VIPS_FOREIGN_SUBSAMPLE_OFF;
|
||||
}
|
||||
|
||||
typedef struct _VipsForeignSaveJp2kFile {
|
||||
@ -991,13 +991,13 @@ typedef struct _VipsForeignSaveJp2kFile {
|
||||
|
||||
/* Filename for save.
|
||||
*/
|
||||
char *filename;
|
||||
char *filename;
|
||||
|
||||
} VipsForeignSaveJp2kFile;
|
||||
|
||||
typedef VipsForeignSaveJp2kClass VipsForeignSaveJp2kFileClass;
|
||||
|
||||
G_DEFINE_TYPE( VipsForeignSaveJp2kFile, vips_foreign_save_jp2k_file,
|
||||
G_DEFINE_TYPE( VipsForeignSaveJp2kFile, vips_foreign_save_jp2k_file,
|
||||
vips_foreign_save_jp2k_get_type() );
|
||||
|
||||
static int
|
||||
@ -1028,10 +1028,10 @@ vips_foreign_save_jp2k_file_class_init( VipsForeignSaveJp2kFileClass *class )
|
||||
object_class->nickname = "jp2ksave";
|
||||
object_class->build = vips_foreign_save_jp2k_file_build;
|
||||
|
||||
VIPS_ARG_STRING( class, "filename", 1,
|
||||
VIPS_ARG_STRING( class, "filename", 1,
|
||||
_( "Filename" ),
|
||||
_( "Filename to load from" ),
|
||||
VIPS_ARGUMENT_REQUIRED_INPUT,
|
||||
VIPS_ARGUMENT_REQUIRED_INPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2kFile, filename ),
|
||||
NULL );
|
||||
|
||||
@ -1053,14 +1053,14 @@ typedef struct _VipsForeignSaveJp2kBuffer {
|
||||
|
||||
typedef VipsForeignSaveJp2kClass VipsForeignSaveJp2kBufferClass;
|
||||
|
||||
G_DEFINE_TYPE( VipsForeignSaveJp2kBuffer, vips_foreign_save_jp2k_buffer,
|
||||
G_DEFINE_TYPE( VipsForeignSaveJp2kBuffer, vips_foreign_save_jp2k_buffer,
|
||||
vips_foreign_save_jp2k_get_type() );
|
||||
|
||||
static int
|
||||
vips_foreign_save_jp2k_buffer_build( VipsObject *object )
|
||||
{
|
||||
VipsForeignSaveJp2k *jp2k = (VipsForeignSaveJp2k *) object;
|
||||
VipsForeignSaveJp2kBuffer *buffer =
|
||||
VipsForeignSaveJp2kBuffer *buffer =
|
||||
(VipsForeignSaveJp2kBuffer *) object;
|
||||
|
||||
VipsBlob *blob;
|
||||
@ -1080,7 +1080,7 @@ vips_foreign_save_jp2k_buffer_build( VipsObject *object )
|
||||
}
|
||||
|
||||
static void
|
||||
vips_foreign_save_jp2k_buffer_class_init(
|
||||
vips_foreign_save_jp2k_buffer_class_init(
|
||||
VipsForeignSaveJp2kBufferClass *class )
|
||||
{
|
||||
GObjectClass *gobject_class = G_OBJECT_CLASS( class );
|
||||
@ -1092,10 +1092,10 @@ vips_foreign_save_jp2k_buffer_class_init(
|
||||
object_class->nickname = "jp2ksave_buffer";
|
||||
object_class->build = vips_foreign_save_jp2k_buffer_build;
|
||||
|
||||
VIPS_ARG_BOXED( class, "buffer", 1,
|
||||
VIPS_ARG_BOXED( class, "buffer", 1,
|
||||
_( "Buffer" ),
|
||||
_( "Buffer to save to" ),
|
||||
VIPS_ARGUMENT_REQUIRED_OUTPUT,
|
||||
VIPS_ARGUMENT_REQUIRED_OUTPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2kBuffer, buf ),
|
||||
VIPS_TYPE_BLOB );
|
||||
|
||||
@ -1114,14 +1114,14 @@ typedef struct _VipsForeignSaveJp2kTarget {
|
||||
|
||||
typedef VipsForeignSaveJp2kClass VipsForeignSaveJp2kTargetClass;
|
||||
|
||||
G_DEFINE_TYPE( VipsForeignSaveJp2kTarget, vips_foreign_save_jp2k_target,
|
||||
G_DEFINE_TYPE( VipsForeignSaveJp2kTarget, vips_foreign_save_jp2k_target,
|
||||
vips_foreign_save_jp2k_get_type() );
|
||||
|
||||
static int
|
||||
vips_foreign_save_jp2k_target_build( VipsObject *object )
|
||||
{
|
||||
VipsForeignSaveJp2k *jp2k = (VipsForeignSaveJp2k *) object;
|
||||
VipsForeignSaveJp2kTarget *target =
|
||||
VipsForeignSaveJp2kTarget *target =
|
||||
(VipsForeignSaveJp2kTarget *) object;
|
||||
|
||||
if( target->target ) {
|
||||
@ -1137,7 +1137,7 @@ vips_foreign_save_jp2k_target_build( VipsObject *object )
|
||||
}
|
||||
|
||||
static void
|
||||
vips_foreign_save_jp2k_target_class_init(
|
||||
vips_foreign_save_jp2k_target_class_init(
|
||||
VipsForeignSaveJp2kTargetClass *class )
|
||||
{
|
||||
GObjectClass *gobject_class = G_OBJECT_CLASS( class );
|
||||
@ -1152,7 +1152,7 @@ vips_foreign_save_jp2k_target_class_init(
|
||||
VIPS_ARG_OBJECT( class, "target", 1,
|
||||
_( "Target" ),
|
||||
_( "Target to save to" ),
|
||||
VIPS_ARGUMENT_REQUIRED_INPUT,
|
||||
VIPS_ARGUMENT_REQUIRED_INPUT,
|
||||
G_STRUCT_OFFSET( VipsForeignSaveJp2kTarget, target ),
|
||||
VIPS_TYPE_TARGET );
|
||||
|
||||
@ -1176,7 +1176,7 @@ typedef struct _TileCompress {
|
||||
* subsampling.
|
||||
*/
|
||||
static void
|
||||
vips_foreign_save_jp2k_unpack_subsample_image( VipsRegion *region,
|
||||
vips_foreign_save_jp2k_unpack_subsample_image( VipsRegion *region,
|
||||
VipsRect *tile, opj_image_t *image, VipsPel *accumulate )
|
||||
{
|
||||
VipsImage *im = region->im;
|
||||
@ -1193,14 +1193,14 @@ vips_foreign_save_jp2k_unpack_subsample_image( VipsRegion *region,
|
||||
/* The number of pixels we write for this component. Lines
|
||||
* align to scanlines on comp.
|
||||
*/
|
||||
int output_width = VIPS_ROUND_UINT(
|
||||
int output_width = VIPS_ROUND_UINT(
|
||||
(double) comp->w / comp->dx );
|
||||
int output_height = VIPS_ROUND_UINT(
|
||||
int output_height = VIPS_ROUND_UINT(
|
||||
(double) comp->h / comp->dy );
|
||||
|
||||
for( y = 0; y < output_height; y++ ) {
|
||||
VipsPel *p = i * sizeof_element +
|
||||
VIPS_REGION_ADDR( region,
|
||||
VipsPel *p = i * sizeof_element +
|
||||
VIPS_REGION_ADDR( region,
|
||||
tile->left, tile->top + y * comp->dy );
|
||||
|
||||
/* Shrink a line of pels to q.
|
||||
@ -1253,12 +1253,12 @@ vips_foreign_save_jp2k_unpack_image( VipsRegion *region, VipsRect *tile,
|
||||
int x, y, i;
|
||||
|
||||
for( y = 0; y < tile->height; y++ ) {
|
||||
VipsPel *p = VIPS_REGION_ADDR( region,
|
||||
VipsPel *p = VIPS_REGION_ADDR( region,
|
||||
tile->left, tile->top + y );
|
||||
|
||||
for( i = 0; i < b; i++ ) {
|
||||
opj_image_comp_t *comp = &image->comps[i];
|
||||
int *q = comp->data + y * comp->w;
|
||||
int *q = comp->data + y * comp->w;
|
||||
|
||||
switch( im->BandFmt ) {
|
||||
case VIPS_FORMAT_CHAR:
|
||||
@ -1294,14 +1294,14 @@ vips__foreign_load_jp2k_compress_free( TileCompress *compress )
|
||||
}
|
||||
|
||||
/* Compress area @tile within @region and write to @target as a @tile_width by
|
||||
* @tile_height jp2k compressed image. This is called from eg. vips2tiff to
|
||||
* @tile_height jp2k compressed image. This is called from eg. vips2tiff to
|
||||
* write jp2k-compressed tiles.
|
||||
*
|
||||
* You'd think we could reuse things like the encoder between calls but ...
|
||||
* nope, openjpeg does not allow that.
|
||||
*/
|
||||
int
|
||||
vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
VipsRect *tile, VipsTarget *target,
|
||||
int tile_width, int tile_height,
|
||||
gboolean save_as_ycc, gboolean subsample, gboolean lossless, int Q )
|
||||
@ -1321,7 +1321,7 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
|
||||
/* Set compression profile.
|
||||
*/
|
||||
vips_foreign_save_jp2k_set_profile( ¶meters, lossless, Q );
|
||||
vips_foreign_save_jp2k_set_profile( ¶meters, lossless, Q );
|
||||
|
||||
/* Makes three band images smaller, somehow.
|
||||
*/
|
||||
@ -1339,7 +1339,7 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
/* We need a line of sums for chroma subsample. At worst, gint64.
|
||||
*/
|
||||
sizeof_line = sizeof( gint64 ) * tile->width;
|
||||
if( !(compress.accumulate =
|
||||
if( !(compress.accumulate =
|
||||
VIPS_ARRAY( NULL, sizeof_line, VipsPel )) ) {
|
||||
vips__foreign_load_jp2k_compress_free( &compress );
|
||||
return( -1 );
|
||||
@ -1347,7 +1347,7 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
|
||||
compress.codec = opj_create_compress( OPJ_CODEC_J2K );
|
||||
vips_foreign_save_jp2k_attach_handlers( compress.codec );
|
||||
if( !opj_setup_encoder( compress.codec,
|
||||
if( !opj_setup_encoder( compress.codec,
|
||||
¶meters, compress.image ) ) {
|
||||
vips__foreign_load_jp2k_compress_free( &compress );
|
||||
return( -1 );
|
||||
@ -1355,26 +1355,26 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
|
||||
opj_codec_set_threads( compress.codec, vips_concurrency_get() );
|
||||
|
||||
if( save_as_ycc )
|
||||
vips_foreign_save_jp2k_rgb_to_ycc( region,
|
||||
if( save_as_ycc )
|
||||
vips_foreign_save_jp2k_rgb_to_ycc( region,
|
||||
tile, compress.image->comps[0].prec );
|
||||
|
||||
/* we need to unpack to the int arrays on comps[i].data
|
||||
*/
|
||||
if( subsample )
|
||||
vips_foreign_save_jp2k_unpack_subsample_image( region,
|
||||
tile, compress.image,
|
||||
compress.accumulate );
|
||||
tile, compress.image,
|
||||
compress.accumulate );
|
||||
else
|
||||
vips_foreign_save_jp2k_unpack_image( region,
|
||||
tile, compress.image );
|
||||
tile, compress.image );
|
||||
|
||||
if( !(compress.stream = vips_foreign_save_jp2k_target( target )) ) {
|
||||
vips__foreign_load_jp2k_compress_free( &compress );
|
||||
return( -1 );
|
||||
}
|
||||
|
||||
if( !opj_start_compress( compress.codec,
|
||||
if( !opj_start_compress( compress.codec,
|
||||
compress.image, compress.stream ) ) {
|
||||
vips__foreign_load_jp2k_compress_free( &compress );
|
||||
return( -1 );
|
||||
@ -1395,12 +1395,12 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
#else /*!HAVE_LIBOPENJP2*/
|
||||
|
||||
int
|
||||
vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
VipsRect *tile, VipsTarget *target,
|
||||
int tile_width, int tile_height,
|
||||
gboolean save_as_ycc, gboolean subsample, gboolean lossless, int Q )
|
||||
{
|
||||
vips_error( "jp2k",
|
||||
vips_error( "jp2k",
|
||||
"%s", _( "libvips built without JPEG2000 support" ) );
|
||||
return( -1 );
|
||||
}
|
||||
@ -1409,8 +1409,8 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
|
||||
/**
|
||||
* vips_jp2ksave: (method)
|
||||
* @in: image to save
|
||||
* @filename: file to write to
|
||||
* @in: image to save
|
||||
* @filename: file to write to
|
||||
* @...: %NULL-terminated list of optional named arguments
|
||||
*
|
||||
* Optional arguments:
|
||||
@ -1421,7 +1421,7 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
* * @tile_height: %gint for tile size
|
||||
* * @subsample_mode: #VipsForeignSubsample, chroma subsampling mode
|
||||
*
|
||||
* Write a VIPS image to a file in JPEG2000 format.
|
||||
* Write a VIPS image to a file in JPEG2000 format.
|
||||
* The saver supports 8, 16 and 32-bit int pixel
|
||||
* values, signed and unsigned. It supports greyscale, RGB, CMYK and
|
||||
* multispectral images.
|
||||
@ -1433,8 +1433,8 @@ vips__foreign_load_jp2k_compress( VipsRegion *region,
|
||||
*
|
||||
* Use @tile_width and @tile_height to set the tile size. The default is 512.
|
||||
*
|
||||
* Chroma subsampling is normally automatically disabled for Q >= 90. You can
|
||||
* force the subsampling mode with @subsample_mode.
|
||||
* Chroma subsampling is normally disabled for compatibility. Set
|
||||
* @subsample_mode to auto to enable chroma subsample for Q < 90.
|
||||
*
|
||||
* This operation always writes a pyramid.
|
||||
*
|
||||
@ -1457,7 +1457,7 @@ vips_jp2ksave( VipsImage *in, const char *filename, ... )
|
||||
|
||||
/**
|
||||
* vips_jp2ksave_buffer: (method)
|
||||
* @in: image to save
|
||||
* @in: image to save
|
||||
* @buf: (array length=len) (element-type guint8): return output buffer here
|
||||
* @len: (type gsize): return output length here
|
||||
* @...: %NULL-terminated list of optional named arguments
|
||||
@ -1483,19 +1483,19 @@ vips_jp2ksave_buffer( VipsImage *in, void **buf, size_t *len, ... )
|
||||
VipsArea *area;
|
||||
int result;
|
||||
|
||||
area = NULL;
|
||||
area = NULL;
|
||||
|
||||
va_start( ap, len );
|
||||
result = vips_call_split( "jp2ksave_buffer", ap, in, &area );
|
||||
va_end( ap );
|
||||
|
||||
if( !result &&
|
||||
area ) {
|
||||
area ) {
|
||||
if( buf ) {
|
||||
*buf = area->data;
|
||||
area->free_fn = NULL;
|
||||
}
|
||||
if( len )
|
||||
if( len )
|
||||
*len = area->length;
|
||||
|
||||
vips_area_unref( area );
|
||||
@ -1506,7 +1506,7 @@ vips_jp2ksave_buffer( VipsImage *in, void **buf, size_t *len, ... )
|
||||
|
||||
/**
|
||||
* vips_jp2ksave_target: (method)
|
||||
* @in: image to save
|
||||
* @in: image to save
|
||||
* @target: save image to this target
|
||||
* @...: %NULL-terminated list of optional named arguments
|
||||
*
|
||||
|
@ -204,7 +204,7 @@ if test_supported matload; then
|
||||
# test blocked and untrusted
|
||||
printf "testing VIPS_BLOCK_UNTRUSTED with matio ... "
|
||||
export VIPS_BLOCK_UNTRUSTED=1
|
||||
if vips matload $matlab $tmp/block.png; then
|
||||
if $vips copy $matlab $tmp/block.png; then
|
||||
echo "failed to block matload"
|
||||
exit 1
|
||||
fi
|
||||
|
Loading…
Reference in New Issue
Block a user