Пример #1
0
/*
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%                                                                             %
%                                                                             %
%                                                                             %
%   V a l i d a t e I m a g e F o r m a t s O n D i s k                       %
%                                                                             %
%                                                                             %
%                                                                             %
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%  ValidateImageFormatsOnDisk() validates the ImageMagick image formats on disk
%  and returns the number of validation tests that passed and failed.
%
%  The format of the ValidateImageFormatsOnDisk method is:
%
%      unsigned long ValidateImageFormatsOnDisk(ImageInfo *image_info,
%        const char *reference_filename,const char *output_filename,
%        unsigned long *fail,ExceptionInfo *exception)
%
%  A description of each parameter follows:
%
%    o image_info: the image info.
%
%    o reference_filename: the reference image filename.
%
%    o output_filename: the output image filename.
%
%    o fail: return the number of validation tests that pass.
%
%    o exception: return any errors or warnings in this structure.
%
*/
static unsigned long ValidateImageFormatsOnDisk(ImageInfo *image_info,
  const char *reference_filename,const char *output_filename,
  unsigned long *fail,ExceptionInfo *exception)
{
  char
    size[MaxTextExtent];

  const MagickInfo
    *magick_info;

  double
    distortion,
    fuzz;

  Image
    *difference_image,
    *reference_image,
    *reconstruct_image;

  MagickBooleanType
    status;

  register long
    i,
    j;

  unsigned long
    test;

  test=0;
  (void) fprintf(stdout,"validate image formats on disk:\n");
  for (i=0; reference_formats[i].magick != (char *) NULL; i++)
  {
    magick_info=GetMagickInfo(reference_formats[i].magick,exception);
    if ((magick_info == (const MagickInfo *) NULL) ||
        (magick_info->decoder == (DecodeImageHandler *) NULL) ||
        (magick_info->encoder == (EncodeImageHandler *) NULL))
      continue;
    for (j=0; reference_types[j].type != UndefinedType; j++)
    {
      /*
        Generate reference image.
      */
      CatchException(exception);
      (void) fprintf(stdout,"  test %lu: %s/%s/%lu-bits",test++,
        reference_formats[i].magick,MagickOptionToMnemonic(MagickTypeOptions,
        reference_types[j].type),reference_types[j].depth);
      (void) CopyMagickString(image_info->filename,reference_filename,
        MaxTextExtent);
      reference_image=ReadImage(image_info,exception);
      if (reference_image == (Image *) NULL)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          continue;
        }
      /*
        Write reference image.
      */
      (void) FormatMagickString(size,MaxTextExtent,"%lux%lu",
        reference_image->columns,reference_image->rows);
      (void) CloneString(&image_info->size,size);
      image_info->depth=reference_types[j].depth;
      (void) FormatMagickString(reference_image->filename,MaxTextExtent,"%s:%s",
        reference_formats[i].magick,output_filename);
      status=SetImageType(reference_image,reference_types[j].type);
      InheritException(exception,&reference_image->exception);
      if (status == MagickFalse)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          reference_image=DestroyImage(reference_image);
          continue;
        }
      status=SetImageDepth(reference_image,reference_types[j].depth);
      InheritException(exception,&reference_image->exception);
      if (status == MagickFalse)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          reference_image=DestroyImage(reference_image);
          continue;
        }
      status=WriteImage(image_info,reference_image);
      InheritException(exception,&reference_image->exception);
      reference_image=DestroyImage(reference_image);
      if (status == MagickFalse)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          continue;
        }
      /*
        Read reference image.
      */
      (void) FormatMagickString(image_info->filename,MaxTextExtent,"%s:%s",
        reference_formats[i].magick,output_filename);
      reference_image=ReadImage(image_info,exception);
      if (reference_image == (Image *) NULL)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          continue;
        }
      /*
        Write reference image.
      */
      (void) FormatMagickString(reference_image->filename,MaxTextExtent,"%s:%s",
        reference_formats[i].magick,output_filename);
      reference_image->depth=reference_types[j].depth;
      status=WriteImage(image_info,reference_image);
      InheritException(exception,&reference_image->exception);
      if (status == MagickFalse)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          reference_image=DestroyImage(reference_image);
          continue;
        }
      /*
        Read reconstruct image.
      */
      (void) FormatMagickString(image_info->filename,MaxTextExtent,"%s:%s",
        reference_formats[i].magick,output_filename);
      reconstruct_image=ReadImage(image_info,exception);
      if (reconstruct_image == (Image *) NULL)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          reference_image=DestroyImage(reference_image);
          continue;
        }
      /*
        Compare reference to reconstruct image.
      */
      fuzz=0.0;
      if (reference_formats[i].fuzz != 0.0)
        fuzz=reference_formats[i].fuzz;
#if defined(MAGICKCORE_HDRI_SUPPORT)
      fuzz+=0.003;
#endif
      if (reference_image->colorspace != RGBColorspace)
        fuzz+=0.3;
      fuzz+=MagickEpsilon;
      difference_image=CompareImageChannels(reference_image,reconstruct_image,
        AllChannels,MeanSquaredErrorMetric,&distortion,exception);
      reconstruct_image=DestroyImage(reconstruct_image);
      reference_image=DestroyImage(reference_image);
      if (difference_image == (Image *) NULL)
        {
          (void) fprintf(stdout,"... fail @ %s/%s/%lu.\n",GetMagickModule());
          (*fail)++;
          continue;
        }
      difference_image=DestroyImage(difference_image);
      if ((distortion/QuantumRange) > fuzz)
        {
          (void) fprintf(stdout,"... fail (with distortion %g).\n",distortion/
            QuantumRange);
          (*fail)++;
          continue;
        }
      (void) fprintf(stdout,"... pass.\n");
    }
  }
  (void) fprintf(stdout,"  summary: %lu subtests; %lu passed; %lu failed.\n",
    test,test-(*fail),*fail);
  return(test);
}
Пример #2
0
/*
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%                                                                             %
%                                                                             %
%                                                                             %
%   W r i t e H I S T O G R A M I m a g e                                     %
%                                                                             %
%                                                                             %
%                                                                             %
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%  Method WriteHISTOGRAMImage writes an image to a file in Histogram format.
%  The image shows a histogram of the color (or gray) values in the image.  The
%  image consists of three overlaid histograms:  a red one for the red channel,
%  a green one for the green channel, and a blue one for the blue channel.  The
%  image comment contains a list of unique pixel values and the number of times
%  each occurs in the image.
%
%  This method is strongly based on a similar one written by
%  [email protected] which in turn is based on ppmhistmap of netpbm.
%
%  The format of the WriteHISTOGRAMImage method is:
%
%      unsigned int WriteHISTOGRAMImage(const ImageInfo *image_info,
%        Image *image)
%
%  A description of each parameter follows.
%
%    o status: Method WriteHISTOGRAMImage return True if the image is written.
%      False is returned is there is a memory shortage or if the image file
%      fails to write.
%
%    o image_info: Specifies a pointer to a ImageInfo structure.
%
%    o image:  A pointer to an Image structure.
%
%
*/
static unsigned int WriteHISTOGRAMImage(const ImageInfo *image_info,
  Image *image)
{
#define HistogramDensity  "256x200"

  char
    filename[MaxTextExtent];

  double
    scale;

  FILE
    *file;

  Image
    *histogram_image;

  long
    *blue,
    *green,
    maximum,
    *red;

  long
    y;

  RectangleInfo
    geometry;

  register const PixelPacket
    *p;

  register long
    x;

  register PixelPacket
    *q,
    *r;

  unsigned int
    status;

  unsigned long
    length;

  /*
    Allocate histogram image.
  */
  assert(image_info != (const ImageInfo *) NULL);
  assert(image_info->signature == MagickSignature);
  assert(image != (Image *) NULL);
  assert(image->signature == MagickSignature);
  (void) SetImageDepth(image,image->depth);
  SetGeometry(image,&geometry);
  if (image_info->density == (char *) NULL)
    (void) GetMagickGeometry(HistogramDensity,&geometry.x,&geometry.y,
      &geometry.width,&geometry.height);
  else
    (void) GetMagickGeometry(image_info->density,&geometry.x,&geometry.y,
      &geometry.width,&geometry.height);
  histogram_image=CloneImage(image,geometry.width,geometry.height,True,
    &image->exception);
  if (histogram_image == (Image *) NULL)
    ThrowWriterException(ResourceLimitError,MemoryAllocationFailed,image);
  (void) SetImageType(histogram_image,TrueColorType);
  /*
    Allocate histogram count arrays.
  */
  length=Max(ScaleQuantumToChar(MaxRGB)+1,histogram_image->columns);
  red=MagickAllocateMemory(long *,length*sizeof(long));
  green=MagickAllocateMemory(long *,length*sizeof(long));
  blue=MagickAllocateMemory(long *,length*sizeof(long));
  if ((red == (long *) NULL) || (green == (long *) NULL) ||
      (blue == (long *) NULL))
    {
      DestroyImage(histogram_image);
      ThrowWriterException(ResourceLimitError,MemoryAllocationFailed,image)
    }