From 0180a61be4cbca1ecfd95ab108055b455e5fde5d Mon Sep 17 00:00:00 2001 From: John Cupitt Date: Wed, 3 Jul 2013 21:39:28 +0100 Subject: [PATCH] move im_identity*() to a class --- ChangeLog | 2 +- libvips/create/Makefile.am | 1 + libvips/create/create.c | 2 + libvips/create/identity.c | 212 +++++++++++++++++++++++++++++ libvips/deprecated/vips7compat.c | 40 +++++- libvips/histogram/Makefile.am | 1 - libvips/histogram/im_identity.c | 174 ----------------------- libvips/include/vips/create.h | 2 + libvips/include/vips/histogram.h | 2 - libvips/include/vips/vips7compat.h | 2 + 10 files changed, 259 insertions(+), 179 deletions(-) create mode 100644 libvips/create/identity.c delete mode 100644 libvips/histogram/im_identity.c diff --git a/ChangeLog b/ChangeLog index 679ed0b9..4fdc1135 100644 --- a/ChangeLog +++ b/ChangeLog @@ -2,7 +2,7 @@ - added vips_matrixload() and vips_matrixsave(), load and save vips mat format - rename image arrays as image matrices ... INTERPRETATION_ARRAY -> INTERPRETATION_MATRIX etc. -- convert im_buildlut() to a class +- convert im_buildlut(), im_identity*() to classes 3/7/13 started 7.34.2 - lower priority for Matlab load to reduce segvs from Mat_Open(), thanks diff --git a/libvips/create/Makefile.am b/libvips/create/Makefile.am index 278d91ec..8f18d82f 100644 --- a/libvips/create/Makefile.am +++ b/libvips/create/Makefile.am @@ -4,6 +4,7 @@ libcreate_la_SOURCES = \ create.c \ pcreate.h \ buildlut.c \ + identity.c \ point.c \ point.h \ eye.c \ diff --git a/libvips/create/create.c b/libvips/create/create.c index 83481671..50d8ea8a 100644 --- a/libvips/create/create.c +++ b/libvips/create/create.c @@ -121,6 +121,7 @@ vips_create_operation_init( void ) extern GType vips_zone_get_type( void ); extern GType vips_sines_get_type( void ); extern GType vips_buildlut_get_type( void ); + extern GType vips_identity_get_type( void ); vips_black_get_type(); vips_gaussnoise_get_type(); @@ -133,5 +134,6 @@ vips_create_operation_init( void ) vips_zone_get_type(); vips_sines_get_type(); vips_buildlut_get_type(); + vips_identity_get_type(); } diff --git a/libvips/create/identity.c b/libvips/create/identity.c new file mode 100644 index 00000000..d30d72b5 --- /dev/null +++ b/libvips/create/identity.c @@ -0,0 +1,212 @@ +/* identity LUTs + * + * Copyright 1991, N. Dessipris. + * + * Author N. Dessipris + * Written on 11/03/1991 + * Updated on: + * 18/6/93 JC + * - im_outcheck() call added + * - ANSIfied + * 24/8/94 JC + * - im_identity_ushort() added + * 24/3/10 + * - gtkdoc + * 3/7/13 + * - redo as a class + */ + +/* + + 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 + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA + 02110-1301 USA + + */ + +/* + + These files are distributed with VIPS - http://www.vips.ecs.soton.ac.uk + + */ + +#ifdef HAVE_CONFIG_H +#include +#endif /*HAVE_CONFIG_H*/ +#include + +#include +#include +#include + +#include + +#include "pcreate.h" + +typedef struct _VipsIdentity { + VipsCreate parent_instance; + + int bands; + gboolean ushort; + int size; + +} VipsIdentity; + +typedef VipsCreateClass VipsIdentityClass; + +G_DEFINE_TYPE( VipsIdentity, vips_identity, VIPS_TYPE_CREATE ); + +#define IDENTITY( TYPE ) { \ + TYPE *q = (TYPE *) VIPS_REGION_ADDR( or, le, 0 ); \ + \ + for( x = le; x < ri; x++ ) { \ + for( i = 0; i < identity->bands; i++ ) \ + q[i] = x; \ + \ + q += identity->bands; \ + } \ +} + +static int +vips_identity_gen( VipsRegion *or, void *seq, void *a, void *b, + gboolean *stop ) +{ + VipsIdentity *identity = (VipsIdentity *) a; + VipsRect *r = &or->valid; + int le = r->left; + int ri = VIPS_RECT_RIGHT( r ); + + int x, i; + + if( identity->ushort ) { + IDENTITY( unsigned short ); + } + else { + IDENTITY( unsigned char ); + } + + return( 0 ); +} + +static int +vips_identity_build( VipsObject *object ) +{ + VipsCreate *create = VIPS_CREATE( object ); + VipsIdentity *identity = (VipsIdentity *) object; + + if( VIPS_OBJECT_CLASS( vips_identity_parent_class )->build( object ) ) + return( -1 ); + + vips_image_init_fields( create->out, + identity->ushort ? identity->size : 256, 1, identity->bands, + identity->ushort ? VIPS_FORMAT_USHORT : VIPS_FORMAT_UCHAR, + VIPS_CODING_NONE, VIPS_INTERPRETATION_HISTOGRAM, + 1.0, 1.0 ); + + vips_demand_hint( create->out, + VIPS_DEMAND_STYLE_ANY, NULL ); + + if( vips_image_generate( create->out, + NULL, vips_identity_gen, NULL, identity, NULL ) ) + return( -1 ); + + return( 0 ); +} + +static void +vips_identity_class_init( VipsIdentityClass *class ) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS( class ); + VipsObjectClass *vobject_class = VIPS_OBJECT_CLASS( class ); + + gobject_class->set_property = vips_object_set_property; + gobject_class->get_property = vips_object_get_property; + + vobject_class->nickname = "identity"; + vobject_class->description = + _( "make a 1D image where pixel values are indexes" ); + vobject_class->build = vips_identity_build; + + VIPS_ARG_INT( class, "bands", 3, + _( "Bands" ), + _( "Number of bands in LUT" ), + VIPS_ARGUMENT_OPTIONAL_INPUT, + G_STRUCT_OFFSET( VipsIdentity, bands ), + 1, 100000, 1 ); + + VIPS_ARG_BOOL( class, "ushort", 4, + _( "Ushort" ), + _( "Create a 16-bit LUT" ), + VIPS_ARGUMENT_OPTIONAL_INPUT, + G_STRUCT_OFFSET( VipsIdentity, ushort ), + FALSE ); + + VIPS_ARG_INT( class, "size", 5, + _( "Size" ), + _( "Size of 16-bit LUT" ), + VIPS_ARGUMENT_OPTIONAL_INPUT, + G_STRUCT_OFFSET( VipsIdentity, size ), + 1, 65536, 65536 ); + +} + +static void +vips_identity_init( VipsIdentity *identity ) +{ + identity->bands = 1; + identity->ushort = FALSE; + identity->size = 65536; +} + +/** + * vips_identity: + * @out: output image + * @...: %NULL-terminated list of optional named arguments + * + * Optional arguments: + * + * @bands: number of bands to create + * @ushort: %TRUE for an unsigned short identity + * @size: number of LUT elements for a ushort image + * + * Creates an identity lookup table, ie. one which will leave an image + * unchanged when applied with vips_maplut(). Each entry in the table has a + * value equal to its position. + * + * Use the arithmetic operations on these tables to make LUTs representing + * arbitrary functions. + * + * Normally LUTs are 8-bit. Set @ushort to create a 16-bit table. + * + * Normally 16-bit tables have 65536 entries. You can set this smaller with + * @size. + * + * See also: vips_xyz(), vips_maplut(). + * + * Returns: 0 on success, -1 on error + */ +int +vips_identity( VipsImage **out, ... ) +{ + va_list ap; + int result; + + va_start( ap, out ); + result = vips_call_split( "identity", ap, out ); + va_end( ap ); + + return( result ); +} diff --git a/libvips/deprecated/vips7compat.c b/libvips/deprecated/vips7compat.c index abd0ce4f..d528ba80 100644 --- a/libvips/deprecated/vips7compat.c +++ b/libvips/deprecated/vips7compat.c @@ -1477,7 +1477,45 @@ im_black( IMAGE *out, int x, int y, int bands ) } int -im_gaussnoise( IMAGE *out, int x, int y, double mean, double sigma ) +im_identity_ushort( VipsImage *lut, int bands, int sz ) +{ + VipsImage *t; + + if( vips_identity( &t, + "bands", bands, + "ushort", TRUE, + "size", sz, + NULL ) ) + return( -1 ); + if( vips_image_write( t, lut ) ) { + g_object_unref( t ); + return( -1 ); + } + g_object_unref( t ); + + return( 0 ); +} + +int +im_identity( VipsImage *lut, int bands ) +{ + VipsImage *t; + + if( vips_identity( &t, + "bands", bands, + NULL ) ) + return( -1 ); + if( vips_image_write( t, lut ) ) { + g_object_unref( t ); + return( -1 ); + } + g_object_unref( t ); + + return( 0 ); +} + +int +im_gaussnoise( VipsImage *out, int x, int y, double mean, double sigma ) { VipsImage *t; diff --git a/libvips/histogram/Makefile.am b/libvips/histogram/Makefile.am index a673b010..8d479334 100644 --- a/libvips/histogram/Makefile.am +++ b/libvips/histogram/Makefile.am @@ -15,7 +15,6 @@ libhistogram_la_SOURCES = \ im_histspec.c \ im_hsp.c \ im_mpercent.c \ - im_identity.c \ im_invertlut.c \ im_lhisteq.c \ im_maplut.c \ diff --git a/libvips/histogram/im_identity.c b/libvips/histogram/im_identity.c deleted file mode 100644 index 662b8a1a..00000000 --- a/libvips/histogram/im_identity.c +++ /dev/null @@ -1,174 +0,0 @@ -/* identity LUTs - * - * Copyright 1991, N. Dessipris. - * - * Author N. Dessipris - * Written on 11/03/1991 - * Updated on: - * 18/6/93 JC - * - im_outcheck() call added - * - ANSIfied - * 24/8/94 JC - * - im_identity_ushort() added - * 24/3/10 - * - gtkdoc - */ - -/* - - 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 - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA - 02110-1301 USA - - */ - -/* - - These files are distributed with VIPS - http://www.vips.ecs.soton.ac.uk - - */ - -#ifdef HAVE_CONFIG_H -#include -#endif /*HAVE_CONFIG_H*/ -#include - -#include -#include -#include - -#include - -/** - * im_identity: - * @lut: output image - * @bands: number of bands to create - * - * Creates a image file with Xsize=256, Ysize=1, Bands=@bands, - * BandFmt=IM_BANDFMT_UCHAR, Type=IM_TYPE_HISTOGRAM. - * - * The created image consist a @bands-bands linear lut and is the basis - * for building up look-up tables. - * - * See also: im_identity_ushort(), im_make_xy(). - * - * Returns: 0 on success, -1 on error - */ -int -im_identity( IMAGE *lut, int bands ) -{ - unsigned char *buf, *p; - int x, z; - - /* Check input args - */ - if( im_outcheck( lut ) ) - return( -1 ); - if( bands < 0 ) { - im_error( "im_identity", "%s", _( "bad bands" ) ); - return( -1 ); - } - - /* Set new image properly. - */ - im_initdesc( lut, - 256, 1, bands, IM_BBITS_BYTE, IM_BANDFMT_UCHAR, - IM_CODING_NONE, IM_TYPE_HISTOGRAM, 1.0, 1.0, 0, 0 ); - - /* Make output. - */ - if( im_setupout( lut ) ) - return( -1 ); - - /* Create output buffer. - */ - if( !(buf = (unsigned char *) im_malloc( lut, bands * 256 )) ) - return( -1 ); - - /* Write ramp. - */ - for( p = buf, x = 0; x < 256; x++ ) - for( z = 0; z < bands; z++ ) - *p++ = x; - - if( im_writeline( 0, lut, buf ) ) - return( -1 ); - - return( 0 ); -} - -/** - * im_identity_ushort: - * @lut: output image - * @bands: number of bands to create - * @sz: size of LUT to create - * - * As im_identity(), but make a ushort LUT. ushort LUTs can be up to 65536 - * elements - @sz is the number of elements required. - * - * The created image consist a @bands-bands linear lut and is the basis - * for building up look-up tables. - * - * See also: im_identity(), im_make_xy(). - * - * Returns: 0 on success, -1 on error - */ -int -im_identity_ushort( IMAGE *lut, int bands, int sz ) -{ - unsigned short *buf, *p; - int x, z; - - /* Check input args - */ - if( im_outcheck( lut ) ) - return( -1 ); - if( sz > 65536 || sz < 0 ) { - im_error( "im_identity_ushort", "%s", _( "bad size" ) ); - return( -1 ); - } - if( bands < 0 ) { - im_error( "im_identity_ushort", "%s", _( "bad bands" ) ); - return( -1 ); - } - - /* Set new image. - */ - im_initdesc( lut, - sz, 1, bands, IM_BBITS_SHORT, IM_BANDFMT_USHORT, - IM_CODING_NONE, IM_TYPE_HISTOGRAM, 1.0, 1.0, 0, 0 ); - - /* Make output. - */ - if( im_setupout( lut ) ) - return( -1 ); - - /* Create output buffer. - */ - if( !(buf = (unsigned short *) - im_malloc( lut, sz * bands * sizeof( unsigned short ) )) ) - return( -1 ); - - /* Write ramp. - */ - for( p = buf, x = 0; x < sz; x++ ) - for( z = 0; z < bands; z++ ) - *p++ = x; - if( im_writeline( 0, lut, (VipsPel *) buf ) ) - return( -1 ); - - return( 0 ); -} diff --git a/libvips/include/vips/create.h b/libvips/include/vips/create.h index 95a8104f..749a1f8e 100644 --- a/libvips/include/vips/create.h +++ b/libvips/include/vips/create.h @@ -62,6 +62,8 @@ int vips_zone( VipsImage **out, int width, int height, ... ) int vips_buildlut( VipsImage *in, VipsImage **out, ... ) __attribute__((sentinel)); +int vips_identity( VipsImage **out, ... ) + __attribute__((sentinel)); int im_benchmarkn( VipsImage *in, VipsImage *out, int n ); int im_benchmark2( VipsImage *in, double *out ); diff --git a/libvips/include/vips/histogram.h b/libvips/include/vips/histogram.h index 8aa15a53..b3113163 100644 --- a/libvips/include/vips/histogram.h +++ b/libvips/include/vips/histogram.h @@ -42,8 +42,6 @@ int im_histgr( VipsImage *in, VipsImage *out, int bandno ); int im_histnD( VipsImage *in, VipsImage *out, int bins ); int im_hist_indexed( VipsImage *index, VipsImage *value, VipsImage *out ); -int im_identity( VipsImage *lut, int bands ); -int im_identity_ushort( VipsImage *lut, int bands, int sz ); int im_invertlut( DOUBLEMASK *input, VipsImage *output, int lut_size ); int im_project( VipsImage *in, VipsImage *hout, VipsImage *vout ); diff --git a/libvips/include/vips/vips7compat.h b/libvips/include/vips/vips7compat.h index 12a64027..4b5a6d15 100644 --- a/libvips/include/vips/vips7compat.h +++ b/libvips/include/vips/vips7compat.h @@ -734,6 +734,8 @@ int im_fgrey( VipsImage *out, const int xsize, const int ysize ); int im_sines( VipsImage *out, int xsize, int ysize, double horfreq, double verfreq ); int im_buildlut( DOUBLEMASK *input, VipsImage *output ); +int im_identity( VipsImage *lut, int bands ); +int im_identity_ushort( VipsImage *lut, int bands, int sz ); int im_system( VipsImage *im, const char *cmd, char **out ); VipsImage *im_system_image( VipsImage *im,