MagickCore  7.0.3
image.c
Go to the documentation of this file.
1 /*
2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3 % %
4 % %
5 % %
6 % IIIII M M AAA GGGG EEEEE %
7 % I MM MM A A G E %
8 % I M M M AAAAA G GG EEE %
9 % I M M A A G G E %
10 % IIIII M M A A GGGG EEEEE %
11 % %
12 % %
13 % MagickCore Image Methods %
14 % %
15 % Software Design %
16 % Cristy %
17 % July 1992 %
18 % %
19 % %
20 % Copyright 1999-2019 ImageMagick Studio LLC, a non-profit organization %
21 % dedicated to making software imaging solutions freely available. %
22 % %
23 % You may not use this file except in compliance with the License. You may %
24 % obtain a copy of the License at %
25 % %
26 % https://imagemagick.org/script/license.php %
27 % %
28 % Unless required by applicable law or agreed to in writing, software %
29 % distributed under the License is distributed on an "AS IS" BASIS, %
30 % WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. %
31 % See the License for the specific language governing permissions and %
32 % limitations under the License. %
33 % %
34 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
35 %
36 %
37 %
38 */
39 
40 /*
41  Include declarations.
42 */
43 #include "MagickCore/studio.h"
44 #include "MagickCore/animate.h"
45 #include "MagickCore/artifact.h"
46 #include "MagickCore/attribute.h"
47 #include "MagickCore/blob.h"
49 #include "MagickCore/cache.h"
51 #include "MagickCore/cache-view.h"
52 #include "MagickCore/channel.h"
53 #include "MagickCore/client.h"
54 #include "MagickCore/color.h"
56 #include "MagickCore/colormap.h"
57 #include "MagickCore/colorspace.h"
59 #include "MagickCore/composite.h"
61 #include "MagickCore/compress.h"
62 #include "MagickCore/constitute.h"
63 #include "MagickCore/delegate.h"
64 #include "MagickCore/display.h"
65 #include "MagickCore/draw.h"
66 #include "MagickCore/enhance.h"
67 #include "MagickCore/exception.h"
69 #include "MagickCore/gem.h"
70 #include "MagickCore/geometry.h"
71 #include "MagickCore/histogram.h"
73 #include "MagickCore/list.h"
74 #include "MagickCore/magic.h"
75 #include "MagickCore/magick.h"
77 #include "MagickCore/memory_.h"
79 #include "MagickCore/module.h"
80 #include "MagickCore/monitor.h"
82 #include "MagickCore/option.h"
83 #include "MagickCore/paint.h"
85 #include "MagickCore/profile.h"
86 #include "MagickCore/property.h"
87 #include "MagickCore/quantize.h"
88 #include "MagickCore/random_.h"
89 #include "MagickCore/resource_.h"
90 #include "MagickCore/segment.h"
91 #include "MagickCore/semaphore.h"
93 #include "MagickCore/statistic.h"
94 #include "MagickCore/string_.h"
97 #include "MagickCore/threshold.h"
98 #include "MagickCore/timer.h"
100 #include "MagickCore/token.h"
102 #include "MagickCore/utility.h"
104 #include "MagickCore/version.h"
106 
107 /*
108  Constant declaration.
109 */
110 const char
111  BackgroundColor[] = "#ffffff", /* white */
112  BorderColor[] = "#dfdfdf", /* gray */
113  DefaultTileFrame[] = "15x15+3+3",
114  DefaultTileGeometry[] = "120x120+4+3>",
115  DefaultTileLabel[] = "%f\n%G\n%b",
116  ForegroundColor[] = "#000", /* black */
117  LoadImageTag[] = "Load/Image",
118  LoadImagesTag[] = "Load/Images",
119  MatteColor[] = "#bdbdbd", /* gray */
120  PSDensityGeometry[] = "72.0x72.0",
121  PSPageGeometry[] = "612x792",
122  SaveImageTag[] = "Save/Image",
123  SaveImagesTag[] = "Save/Images",
124  TransparentColor[] = "#00000000"; /* transparent black */
125 
126 const double
128 
129 /*
130 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
131 % %
132 % %
133 % %
134 % A c q u i r e I m a g e %
135 % %
136 % %
137 % %
138 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
139 %
140 % AcquireImage() returns a pointer to an image structure initialized to
141 % default values.
142 %
143 % The format of the AcquireImage method is:
144 %
145 % Image *AcquireImage(const ImageInfo *image_info,ExceptionInfo *exception)
146 %
147 % A description of each parameter follows:
148 %
149 % o image_info: Many of the image default values are set from this
150 % structure. For example, filename, compression, depth, background color,
151 % and others.
152 %
153 % o exception: return any errors or warnings in this structure.
154 %
155 */
158 {
159  const char
160  *option;
161 
162  Image
163  *image;
164 
166  flags;
167 
168  /*
169  Allocate image structure.
170  */
171  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
172  image=(Image *) AcquireCriticalMemory(sizeof(*image));
173  (void) memset(image,0,sizeof(*image));
174  /*
175  Initialize Image structure.
176  */
177  (void) CopyMagickString(image->magick,"MIFF",MagickPathExtent);
178  image->storage_class=DirectClass;
180  image->colorspace=sRGBColorspace;
182  image->gamma=1.000f/2.200f;
183  image->chromaticity.red_primary.x=0.6400f;
184  image->chromaticity.red_primary.y=0.3300f;
185  image->chromaticity.red_primary.z=0.0300f;
186  image->chromaticity.green_primary.x=0.3000f;
187  image->chromaticity.green_primary.y=0.6000f;
188  image->chromaticity.green_primary.z=0.1000f;
189  image->chromaticity.blue_primary.x=0.1500f;
190  image->chromaticity.blue_primary.y=0.0600f;
191  image->chromaticity.blue_primary.z=0.7900f;
192  image->chromaticity.white_point.x=0.3127f;
193  image->chromaticity.white_point.y=0.3290f;
194  image->chromaticity.white_point.z=0.3583f;
195  image->interlace=NoInterlace;
197  image->compose=OverCompositeOp;
199  exception);
201  &image->background_color,exception);
203  exception);
205  &image->transparent_color,exception);
206  GetTimerInfo(&image->timer);
207  image->cache=AcquirePixelCache(0);
210  image->blob=CloneBlobInfo((BlobInfo *) NULL);
211  image->timestamp=GetMagickTime();
212  image->debug=IsEventLogging();
213  image->reference_count=1;
216  if (image_info == (ImageInfo *) NULL)
217  return(image);
218  /*
219  Transfer image info.
220  */
221  SetBlobExempt(image,image_info->file != (FILE *) NULL ? MagickTrue :
222  MagickFalse);
223  (void) CopyMagickString(image->filename,image_info->filename,
225  (void) CopyMagickString(image->magick_filename,image_info->filename,
227  (void) CopyMagickString(image->magick,image_info->magick,MagickPathExtent);
228  if (image_info->size != (char *) NULL)
229  {
230  (void) ParseAbsoluteGeometry(image_info->size,&image->extract_info);
231  image->columns=image->extract_info.width;
232  image->rows=image->extract_info.height;
233  image->offset=image->extract_info.x;
234  image->extract_info.x=0;
235  image->extract_info.y=0;
236  }
237  if (image_info->extract != (char *) NULL)
238  {
240  geometry;
241 
242  (void) memset(&geometry,0,sizeof(geometry));
243  flags=ParseAbsoluteGeometry(image_info->extract,&geometry);
244  if (((flags & XValue) != 0) || ((flags & YValue) != 0))
245  {
246  image->extract_info=geometry;
247  Swap(image->columns,image->extract_info.width);
248  Swap(image->rows,image->extract_info.height);
249  }
250  }
251  image->compression=image_info->compression;
252  image->quality=image_info->quality;
253  image->endian=image_info->endian;
254  image->interlace=image_info->interlace;
255  image->units=image_info->units;
256  if (image_info->density != (char *) NULL)
257  {
259  geometry_info;
260 
261  flags=ParseGeometry(image_info->density,&geometry_info);
262  if ((flags & RhoValue) != 0)
263  image->resolution.x=geometry_info.rho;
264  image->resolution.y=image->resolution.x;
265  if ((flags & SigmaValue) != 0)
266  image->resolution.y=geometry_info.sigma;
267  }
268  if (image_info->page != (char *) NULL)
269  {
270  char
271  *geometry;
272 
273  image->page=image->extract_info;
274  geometry=GetPageGeometry(image_info->page);
275  (void) ParseAbsoluteGeometry(geometry,&image->page);
276  geometry=DestroyString(geometry);
277  }
278  if (image_info->depth != 0)
279  image->depth=image_info->depth;
280  image->dither=image_info->dither;
281  image->matte_color=image_info->matte_color;
282  image->background_color=image_info->background_color;
283  image->border_color=image_info->border_color;
284  image->transparent_color=image_info->transparent_color;
285  image->ping=image_info->ping;
286  image->progress_monitor=image_info->progress_monitor;
287  image->client_data=image_info->client_data;
288  if (image_info->cache != (void *) NULL)
289  ClonePixelCacheMethods(image->cache,image_info->cache);
290  /*
291  Set all global options that map to per-image settings.
292  */
293  (void) SyncImageSettings(image_info,image,exception);
294  /*
295  Global options that are only set for new images.
296  */
297  option=GetImageOption(image_info,"delay");
298  if (option != (const char *) NULL)
299  {
301  geometry_info;
302 
303  flags=ParseGeometry(option,&geometry_info);
304  if ((flags & GreaterValue) != 0)
305  {
306  if (image->delay > (size_t) floor(geometry_info.rho+0.5))
307  image->delay=(size_t) floor(geometry_info.rho+0.5);
308  }
309  else
310  if ((flags & LessValue) != 0)
311  {
312  if (image->delay < (size_t) floor(geometry_info.rho+0.5))
313  image->ticks_per_second=(ssize_t) floor(geometry_info.sigma+0.5);
314  }
315  else
316  image->delay=(size_t) floor(geometry_info.rho+0.5);
317  if ((flags & SigmaValue) != 0)
318  image->ticks_per_second=(ssize_t) floor(geometry_info.sigma+0.5);
319  }
320  option=GetImageOption(image_info,"dispose");
321  if (option != (const char *) NULL)
323  MagickFalse,option);
324  return(image);
325 }
326 
327 /*
328 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
329 % %
330 % %
331 % %
332 % A c q u i r e I m a g e I n f o %
333 % %
334 % %
335 % %
336 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
337 %
338 % AcquireImageInfo() allocates the ImageInfo structure.
339 %
340 % The format of the AcquireImageInfo method is:
341 %
342 % ImageInfo *AcquireImageInfo(void)
343 %
344 */
346 {
347  ImageInfo
348  *image_info;
349 
350  image_info=(ImageInfo *) AcquireCriticalMemory(sizeof(*image_info));
351  GetImageInfo(image_info);
352  return(image_info);
353 }
354 
355 /*
356 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
357 % %
358 % %
359 % %
360 % A c q u i r e N e x t I m a g e %
361 % %
362 % %
363 % %
364 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
365 %
366 % AcquireNextImage() initializes the next image in a sequence to
367 % default values. The next member of image points to the newly allocated
368 % image. If there is a memory shortage, next is assigned NULL.
369 %
370 % The format of the AcquireNextImage method is:
371 %
372 % void AcquireNextImage(const ImageInfo *image_info,Image *image,
373 % ExceptionInfo *exception)
374 %
375 % A description of each parameter follows:
376 %
377 % o image_info: Many of the image default values are set from this
378 % structure. For example, filename, compression, depth, background color,
379 % and others.
380 %
381 % o image: the image.
382 %
383 % o exception: return any errors or warnings in this structure.
384 %
385 */
388 {
389  /*
390  Allocate image structure.
391  */
392  assert(image != (Image *) NULL);
393  assert(image->signature == MagickCoreSignature);
394  if (image->debug != MagickFalse)
395  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
396  image->next=AcquireImage(image_info,exception);
397  if (GetNextImageInList(image) == (Image *) NULL)
398  return;
401  if (image_info != (ImageInfo *) NULL)
402  (void) CopyMagickString(GetNextImageInList(image)->filename,
403  image_info->filename,MagickPathExtent);
405  image->next->blob=ReferenceBlob(image->blob);
406  image->next->endian=image->endian;
407  image->next->scene=image->scene+1;
408  image->next->previous=image;
409 }
410 
411 /*
412 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
413 % %
414 % %
415 % %
416 % A p p e n d I m a g e s %
417 % %
418 % %
419 % %
420 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
421 %
422 % AppendImages() takes all images from the current image pointer to the end
423 % of the image list and appends them to each other top-to-bottom if the
424 % stack parameter is true, otherwise left-to-right.
425 %
426 % The current gravity setting effects how the image is justified in the
427 % final image.
428 %
429 % The format of the AppendImages method is:
430 %
431 % Image *AppendImages(const Image *images,const MagickBooleanType stack,
432 % ExceptionInfo *exception)
433 %
434 % A description of each parameter follows:
435 %
436 % o images: the image sequence.
437 %
438 % o stack: A value other than 0 stacks the images top-to-bottom.
439 %
440 % o exception: return any errors or warnings in this structure.
441 %
442 */
445 {
446 #define AppendImageTag "Append/Image"
447 
448  CacheView
449  *append_view;
450 
451  Image
452  *append_image;
453 
455  homogeneous_colorspace,
456  status;
457 
459  n;
460 
461  PixelTrait
462  alpha_trait;
463 
465  geometry;
466 
467  register const Image
468  *next;
469 
470  size_t
471  depth,
472  height,
473  number_images,
474  width;
475 
476  ssize_t
477  x_offset,
478  y,
479  y_offset;
480 
481  /*
482  Compute maximum area of appended area.
483  */
484  assert(images != (Image *) NULL);
485  assert(images->signature == MagickCoreSignature);
486  if (images->debug != MagickFalse)
487  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",images->filename);
488  assert(exception != (ExceptionInfo *) NULL);
489  assert(exception->signature == MagickCoreSignature);
490  alpha_trait=images->alpha_trait;
491  number_images=1;
492  width=images->columns;
493  height=images->rows;
494  depth=images->depth;
495  homogeneous_colorspace=MagickTrue;
496  next=GetNextImageInList(images);
497  for ( ; next != (Image *) NULL; next=GetNextImageInList(next))
498  {
499  if (next->depth > depth)
500  depth=next->depth;
501  if (next->colorspace != images->colorspace)
502  homogeneous_colorspace=MagickFalse;
503  if (next->alpha_trait != UndefinedPixelTrait)
504  alpha_trait=BlendPixelTrait;
505  number_images++;
506  if (stack != MagickFalse)
507  {
508  if (next->columns > width)
509  width=next->columns;
510  height+=next->rows;
511  continue;
512  }
513  width+=next->columns;
514  if (next->rows > height)
515  height=next->rows;
516  }
517  /*
518  Append images.
519  */
520  append_image=CloneImage(images,width,height,MagickTrue,exception);
521  if (append_image == (Image *) NULL)
522  return((Image *) NULL);
523  if (SetImageStorageClass(append_image,DirectClass,exception) == MagickFalse)
524  {
525  append_image=DestroyImage(append_image);
526  return((Image *) NULL);
527  }
528  if (homogeneous_colorspace == MagickFalse)
529  (void) SetImageColorspace(append_image,sRGBColorspace,exception);
530  append_image->depth=depth;
531  append_image->alpha_trait=alpha_trait;
532  append_image->page=images->page;
533  (void) SetImageBackgroundColor(append_image,exception);
534  status=MagickTrue;
535  x_offset=0;
536  y_offset=0;
537  next=images;
538  append_view=AcquireAuthenticCacheView(append_image,exception);
539  for (n=0; n < (MagickOffsetType) number_images; n++)
540  {
541  CacheView
542  *image_view;
543 
545  proceed;
546 
547  SetGeometry(append_image,&geometry);
548  GravityAdjustGeometry(next->columns,next->rows,next->gravity,&geometry);
549  if (stack != MagickFalse)
550  x_offset-=geometry.x;
551  else
552  y_offset-=geometry.y;
553  image_view=AcquireVirtualCacheView(next,exception);
554 #if defined(MAGICKCORE_OPENMP_SUPPORT)
555  #pragma omp parallel for schedule(static) shared(status) \
556  magick_number_threads(next,next,next->rows,1)
557 #endif
558  for (y=0; y < (ssize_t) next->rows; y++)
559  {
561  sync;
562 
563  PixelInfo
564  pixel;
565 
566  register const Quantum
567  *magick_restrict p;
568 
569  register Quantum
570  *magick_restrict q;
571 
572  register ssize_t
573  x;
574 
575  if (status == MagickFalse)
576  continue;
577  p=GetCacheViewVirtualPixels(image_view,0,y,next->columns,1,exception);
578  q=QueueCacheViewAuthenticPixels(append_view,x_offset,y+y_offset,
579  next->columns,1,exception);
580  if ((p == (const Quantum *) NULL) || (q == (Quantum *) NULL))
581  {
582  status=MagickFalse;
583  continue;
584  }
585  GetPixelInfo(next,&pixel);
586  for (x=0; x < (ssize_t) next->columns; x++)
587  {
588  GetPixelInfoPixel(next,p,&pixel);
589  SetPixelViaPixelInfo(append_image,&pixel,q);
590  p+=GetPixelChannels(next);
591  q+=GetPixelChannels(append_image);
592  }
593  sync=SyncCacheViewAuthenticPixels(append_view,exception);
594  if (sync == MagickFalse)
595  status=MagickFalse;
596  }
597  image_view=DestroyCacheView(image_view);
598  if (stack == MagickFalse)
599  {
600  x_offset+=(ssize_t) next->columns;
601  y_offset=0;
602  }
603  else
604  {
605  x_offset=0;
606  y_offset+=(ssize_t) next->rows;
607  }
608  proceed=SetImageProgress(append_image,AppendImageTag,n,number_images);
609  if (proceed == MagickFalse)
610  break;
611  next=GetNextImageInList(next);
612  }
613  append_view=DestroyCacheView(append_view);
614  if (status == MagickFalse)
615  append_image=DestroyImage(append_image);
616  return(append_image);
617 }
618 
619 /*
620 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
621 % %
622 % %
623 % %
624 % C a t c h I m a g e E x c e p t i o n %
625 % %
626 % %
627 % %
628 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
629 %
630 % CatchImageException() returns if no exceptions are found in the image
631 % sequence, otherwise it determines the most severe exception and reports
632 % it as a warning or error depending on the severity.
633 %
634 % The format of the CatchImageException method is:
635 %
636 % ExceptionType CatchImageException(Image *image)
637 %
638 % A description of each parameter follows:
639 %
640 % o image: An image sequence.
641 %
642 */
644 {
646  *exception;
647 
649  severity;
650 
651  assert(image != (const Image *) NULL);
652  assert(image->signature == MagickCoreSignature);
653  if (image->debug != MagickFalse)
654  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
655  exception=AcquireExceptionInfo();
656  CatchException(exception);
657  severity=exception->severity;
658  exception=DestroyExceptionInfo(exception);
659  return(severity);
660 }
661 
662 /*
663 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
664 % %
665 % %
666 % %
667 % C l i p I m a g e P a t h %
668 % %
669 % %
670 % %
671 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
672 %
673 % ClipImagePath() sets the image clip mask based any clipping path information
674 % if it exists.
675 %
676 % The format of the ClipImagePath method is:
677 %
678 % MagickBooleanType ClipImagePath(Image *image,const char *pathname,
679 % const MagickBooleanType inside,ExceptionInfo *exception)
680 %
681 % A description of each parameter follows:
682 %
683 % o image: the image.
684 %
685 % o pathname: name of clipping path resource. If name is preceded by #, use
686 % clipping path numbered by name.
687 %
688 % o inside: if non-zero, later operations take effect inside clipping path.
689 % Otherwise later operations take effect outside clipping path.
690 %
691 % o exception: return any errors or warnings in this structure.
692 %
693 */
694 
696 {
697  return(ClipImagePath(image,"#1",MagickTrue,exception));
698 }
699 
702 {
703 #define ClipImagePathTag "ClipPath/Image"
704 
705  char
706  *property;
707 
708  const char
709  *value;
710 
711  Image
712  *clip_mask;
713 
714  ImageInfo
715  *image_info;
716 
717  assert(image != (const Image *) NULL);
718  assert(image->signature == MagickCoreSignature);
719  if (image->debug != MagickFalse)
720  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
721  assert(pathname != NULL);
722  property=AcquireString(pathname);
723  (void) FormatLocaleString(property,MagickPathExtent,"8BIM:1999,2998:%s",
724  pathname);
725  value=GetImageProperty(image,property,exception);
726  property=DestroyString(property);
727  if (value == (const char *) NULL)
728  {
729  ThrowFileException(exception,OptionError,"NoClipPathDefined",
730  image->filename);
731  return(MagickFalse);
732  }
733  image_info=AcquireImageInfo();
734  (void) CopyMagickString(image_info->filename,image->filename,
736  (void) ConcatenateMagickString(image_info->filename,pathname,
738  clip_mask=BlobToImage(image_info,value,strlen(value),exception);
739  image_info=DestroyImageInfo(image_info);
740  if (clip_mask == (Image *) NULL)
741  return(MagickFalse);
742  if (clip_mask->storage_class == PseudoClass)
743  {
744  (void) SyncImage(clip_mask,exception);
745  if (SetImageStorageClass(clip_mask,DirectClass,exception) == MagickFalse)
746  return(MagickFalse);
747  }
748  if (inside == MagickFalse)
749  (void) NegateImage(clip_mask,MagickFalse,exception);
751  "8BIM:1999,2998:%s\nPS",pathname);
752  (void) SetImageMask(image,WritePixelMask,clip_mask,exception);
753  clip_mask=DestroyImage(clip_mask);
754  return(MagickTrue);
755 }
756 
757 /*
758 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
759 % %
760 % %
761 % %
762 % C l o n e I m a g e %
763 % %
764 % %
765 % %
766 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
767 %
768 % CloneImage() copies an image and returns the copy as a new image object.
769 %
770 % If the specified columns and rows is 0, an exact copy of the image is
771 % returned, otherwise the pixel data is undefined and must be initialized
772 % with the QueueAuthenticPixels() and SyncAuthenticPixels() methods. On
773 % failure, a NULL image is returned and exception describes the reason for the
774 % failure.
775 %
776 % The format of the CloneImage method is:
777 %
778 % Image *CloneImage(const Image *image,const size_t columns,
779 % const size_t rows,const MagickBooleanType orphan,
780 % ExceptionInfo *exception)
781 %
782 % A description of each parameter follows:
783 %
784 % o image: the image.
785 %
786 % o columns: the number of columns in the cloned image.
787 %
788 % o rows: the number of rows in the cloned image.
789 %
790 % o detach: With a value other than 0, the cloned image is detached from
791 % its parent I/O stream.
792 %
793 % o exception: return any errors or warnings in this structure.
794 %
795 */
796 MagickExport Image *CloneImage(const Image *image,const size_t columns,
797  const size_t rows,const MagickBooleanType detach,ExceptionInfo *exception)
798 {
799  Image
800  *clone_image;
801 
802  double
803  scale;
804 
805  size_t
806  length;
807 
808  /*
809  Clone the image.
810  */
811  assert(image != (const Image *) NULL);
812  assert(image->signature == MagickCoreSignature);
813  if (image->debug != MagickFalse)
814  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
815  assert(exception != (ExceptionInfo *) NULL);
816  assert(exception->signature == MagickCoreSignature);
817  if ((image->columns == 0) || (image->rows == 0))
818  {
820  "NegativeOrZeroImageSize","`%s'",image->filename);
821  return((Image *) NULL);
822  }
823  clone_image=(Image *) AcquireCriticalMemory(sizeof(*clone_image));
824  (void) memset(clone_image,0,sizeof(*clone_image));
825  clone_image->signature=MagickCoreSignature;
826  clone_image->storage_class=image->storage_class;
827  clone_image->number_channels=image->number_channels;
828  clone_image->number_meta_channels=image->number_meta_channels;
829  clone_image->metacontent_extent=image->metacontent_extent;
830  clone_image->colorspace=image->colorspace;
831  clone_image->alpha_trait=image->alpha_trait;
832  clone_image->channels=image->channels;
833  clone_image->mask_trait=image->mask_trait;
834  clone_image->columns=image->columns;
835  clone_image->rows=image->rows;
836  clone_image->dither=image->dither;
837  clone_image->image_info=CloneImageInfo(image->image_info);
838  (void) CloneImageProfiles(clone_image,image);
839  (void) CloneImageProperties(clone_image,image);
840  (void) CloneImageArtifacts(clone_image,image);
841  GetTimerInfo(&clone_image->timer);
842  if (image->ascii85 != (void *) NULL)
843  Ascii85Initialize(clone_image);
844  clone_image->extent=image->extent;
845  clone_image->magick_columns=image->magick_columns;
846  clone_image->magick_rows=image->magick_rows;
847  clone_image->type=image->type;
848  clone_image->channel_mask=image->channel_mask;
849  clone_image->channel_map=ClonePixelChannelMap(image->channel_map);
850  (void) CopyMagickString(clone_image->magick_filename,image->magick_filename,
852  (void) CopyMagickString(clone_image->magick,image->magick,MagickPathExtent);
853  (void) CopyMagickString(clone_image->filename,image->filename,
855  clone_image->progress_monitor=image->progress_monitor;
856  clone_image->client_data=image->client_data;
857  clone_image->reference_count=1;
858  clone_image->next=image->next;
859  clone_image->previous=image->previous;
860  clone_image->list=NewImageList();
861  if (detach == MagickFalse)
862  clone_image->blob=ReferenceBlob(image->blob);
863  else
864  {
865  clone_image->next=NewImageList();
866  clone_image->previous=NewImageList();
867  clone_image->blob=CloneBlobInfo((BlobInfo *) NULL);
868  }
869  clone_image->ping=image->ping;
870  clone_image->debug=IsEventLogging();
871  clone_image->semaphore=AcquireSemaphoreInfo();
872  if (image->colormap != (PixelInfo *) NULL)
873  {
874  /*
875  Allocate and copy the image colormap.
876  */
877  clone_image->colors=image->colors;
878  length=(size_t) image->colors;
879  clone_image->colormap=(PixelInfo *) AcquireQuantumMemory(length+1,
880  sizeof(*clone_image->colormap));
881  if (clone_image->colormap == (PixelInfo *) NULL)
882  {
883  clone_image=DestroyImage(clone_image);
884  ThrowImageException(ResourceLimitError,"MemoryAllocationFailed");
885  }
886  (void) memcpy(clone_image->colormap,image->colormap,length*
887  sizeof(*clone_image->colormap));
888  }
889  if ((columns == 0) || (rows == 0))
890  {
891  if (image->montage != (char *) NULL)
892  (void) CloneString(&clone_image->montage,image->montage);
893  if (image->directory != (char *) NULL)
894  (void) CloneString(&clone_image->directory,image->directory);
895  clone_image->cache=ReferencePixelCache(image->cache);
896  return(clone_image);
897  }
898  scale=1.0;
899  if (image->columns != 0)
900  scale=(double) columns/(double) image->columns;
901  clone_image->page.width=(size_t) floor(scale*image->page.width+0.5);
902  clone_image->page.x=(ssize_t) ceil(scale*image->page.x-0.5);
903  clone_image->tile_offset.x=(ssize_t) ceil(scale*image->tile_offset.x-0.5);
904  scale=1.0;
905  if (image->rows != 0)
906  scale=(double) rows/(double) image->rows;
907  clone_image->page.height=(size_t) floor(scale*image->page.height+0.5);
908  clone_image->page.y=(ssize_t) ceil(scale*image->page.y-0.5);
909  clone_image->tile_offset.y=(ssize_t) ceil(scale*image->tile_offset.y-0.5);
910  clone_image->cache=ClonePixelCache(image->cache);
911  if (SetImageExtent(clone_image,columns,rows,exception) == MagickFalse)
912  clone_image=DestroyImage(clone_image);
913  return(clone_image);
914 }
915 
916 /*
917 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
918 % %
919 % %
920 % %
921 % C l o n e I m a g e I n f o %
922 % %
923 % %
924 % %
925 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
926 %
927 % CloneImageInfo() makes a copy of the given image info structure. If
928 % NULL is specified, a new image info structure is created initialized to
929 % default values.
930 %
931 % The format of the CloneImageInfo method is:
932 %
933 % ImageInfo *CloneImageInfo(const ImageInfo *image_info)
934 %
935 % A description of each parameter follows:
936 %
937 % o image_info: the image info.
938 %
939 */
941 {
942  ImageInfo
943  *clone_info;
944 
945  clone_info=AcquireImageInfo();
946  if (image_info == (ImageInfo *) NULL)
947  return(clone_info);
948  clone_info->compression=image_info->compression;
949  clone_info->temporary=image_info->temporary;
950  clone_info->adjoin=image_info->adjoin;
951  clone_info->antialias=image_info->antialias;
952  clone_info->scene=image_info->scene;
953  clone_info->number_scenes=image_info->number_scenes;
954  clone_info->depth=image_info->depth;
955  if (image_info->size != (char *) NULL)
956  (void) CloneString(&clone_info->size,image_info->size);
957  if (image_info->extract != (char *) NULL)
958  (void) CloneString(&clone_info->extract,image_info->extract);
959  if (image_info->scenes != (char *) NULL)
960  (void) CloneString(&clone_info->scenes,image_info->scenes);
961  if (image_info->page != (char *) NULL)
962  (void) CloneString(&clone_info->page,image_info->page);
963  clone_info->interlace=image_info->interlace;
964  clone_info->endian=image_info->endian;
965  clone_info->units=image_info->units;
966  clone_info->quality=image_info->quality;
967  if (image_info->sampling_factor != (char *) NULL)
968  (void) CloneString(&clone_info->sampling_factor,
969  image_info->sampling_factor);
970  if (image_info->server_name != (char *) NULL)
971  (void) CloneString(&clone_info->server_name,image_info->server_name);
972  if (image_info->font != (char *) NULL)
973  (void) CloneString(&clone_info->font,image_info->font);
974  if (image_info->texture != (char *) NULL)
975  (void) CloneString(&clone_info->texture,image_info->texture);
976  if (image_info->density != (char *) NULL)
977  (void) CloneString(&clone_info->density,image_info->density);
978  clone_info->pointsize=image_info->pointsize;
979  clone_info->fuzz=image_info->fuzz;
980  clone_info->matte_color=image_info->matte_color;
981  clone_info->background_color=image_info->background_color;
982  clone_info->border_color=image_info->border_color;
983  clone_info->transparent_color=image_info->transparent_color;
984  clone_info->dither=image_info->dither;
985  clone_info->monochrome=image_info->monochrome;
986  clone_info->colorspace=image_info->colorspace;
987  clone_info->type=image_info->type;
988  clone_info->orientation=image_info->orientation;
989  clone_info->ping=image_info->ping;
990  clone_info->verbose=image_info->verbose;
991  clone_info->progress_monitor=image_info->progress_monitor;
992  clone_info->client_data=image_info->client_data;
993  clone_info->cache=image_info->cache;
994  if (image_info->cache != (void *) NULL)
995  clone_info->cache=ReferencePixelCache(image_info->cache);
996  if (image_info->profile != (void *) NULL)
997  clone_info->profile=(void *) CloneStringInfo((StringInfo *)
998  image_info->profile);
999  SetImageInfoFile(clone_info,image_info->file);
1000  SetImageInfoBlob(clone_info,image_info->blob,image_info->length);
1001  clone_info->stream=image_info->stream;
1002  clone_info->custom_stream=image_info->custom_stream;
1003  (void) CopyMagickString(clone_info->magick,image_info->magick,
1005  (void) CopyMagickString(clone_info->unique,image_info->unique,
1007  (void) CopyMagickString(clone_info->filename,image_info->filename,
1009  clone_info->channel=image_info->channel;
1010  (void) CloneImageOptions(clone_info,image_info);
1011  clone_info->debug=IsEventLogging();
1012  clone_info->signature=image_info->signature;
1013  return(clone_info);
1014 }
1015 
1016 /*
1017 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1018 % %
1019 % %
1020 % %
1021 % C o p y I m a g e P i x e l s %
1022 % %
1023 % %
1024 % %
1025 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1026 %
1027 % CopyImagePixels() copies pixels from the source image as defined by the
1028 % geometry the destination image at the specified offset.
1029 %
1030 % The format of the CopyImagePixels method is:
1031 %
1032 % MagickBooleanType CopyImagePixels(Image *image,const Image *source_image,
1033 % const RectangleInfo *geometry,const OffsetInfo *offset,
1034 % ExceptionInfo *exception);
1035 %
1036 % A description of each parameter follows:
1037 %
1038 % o image: the destination image.
1039 %
1040 % o source_image: the source image.
1041 %
1042 % o geometry: define the dimensions of the source pixel rectangle.
1043 %
1044 % o offset: define the offset in the destination image.
1045 %
1046 % o exception: return any errors or warnings in this structure.
1047 %
1048 */
1050  const Image *source_image,const RectangleInfo *geometry,
1051  const OffsetInfo *offset,ExceptionInfo *exception)
1052 {
1053 #define CopyImageTag "Copy/Image"
1054 
1055  CacheView
1056  *image_view,
1057  *source_view;
1058 
1060  status;
1061 
1063  progress;
1064 
1065  ssize_t
1066  y;
1067 
1068  assert(image != (Image *) NULL);
1069  if (image->debug != MagickFalse)
1070  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1071  assert(source_image != (Image *) NULL);
1072  assert(geometry != (RectangleInfo *) NULL);
1073  assert(offset != (OffsetInfo *) NULL);
1074  if ((offset->x < 0) || (offset->y < 0) ||
1075  ((ssize_t) (offset->x+geometry->width) > (ssize_t) image->columns) ||
1076  ((ssize_t) (offset->y+geometry->height) > (ssize_t) image->rows))
1077  ThrowBinaryException(OptionError,"GeometryDoesNotContainImage",
1078  image->filename);
1079  if (SetImageStorageClass(image,DirectClass,exception) == MagickFalse)
1080  return(MagickFalse);
1081  /*
1082  Copy image pixels.
1083  */
1084  status=MagickTrue;
1085  progress=0;
1086  source_view=AcquireVirtualCacheView(source_image,exception);
1087  image_view=AcquireAuthenticCacheView(image,exception);
1088 #if defined(MAGICKCORE_OPENMP_SUPPORT)
1089  #pragma omp parallel for schedule(static) shared(progress,status) \
1090  magick_number_threads(image,source_image,geometry->height,1)
1091 #endif
1092  for (y=0; y < (ssize_t) geometry->height; y++)
1093  {
1095  sync;
1096 
1097  register const Quantum
1098  *magick_restrict p;
1099 
1100  register ssize_t
1101  x;
1102 
1103  register Quantum
1104  *magick_restrict q;
1105 
1106  if (status == MagickFalse)
1107  continue;
1108  p=GetCacheViewVirtualPixels(source_view,geometry->x,y+geometry->y,
1109  geometry->width,1,exception);
1110  q=QueueCacheViewAuthenticPixels(image_view,offset->x,y+offset->y,
1111  geometry->width,1,exception);
1112  if ((p == (const Quantum *) NULL) || (q == (Quantum *) NULL))
1113  {
1114  status=MagickFalse;
1115  continue;
1116  }
1117  for (x=0; x < (ssize_t) geometry->width; x++)
1118  {
1119  register ssize_t
1120  i;
1121 
1122  for (i=0; i < (ssize_t) GetPixelChannels(image); i++)
1123  {
1124  PixelChannel channel = GetPixelChannelChannel(image,i);
1125  PixelTrait traits = GetPixelChannelTraits(image,channel);
1126  PixelTrait source_traits=GetPixelChannelTraits(source_image,channel);
1127  if ((traits == UndefinedPixelTrait) ||
1128  ((traits & UpdatePixelTrait) == 0) ||
1129  (source_traits == UndefinedPixelTrait))
1130  continue;
1131  SetPixelChannel(image,channel,p[i],q);
1132  }
1133  p+=GetPixelChannels(source_image);
1134  q+=GetPixelChannels(image);
1135  }
1136  sync=SyncCacheViewAuthenticPixels(image_view,exception);
1137  if (sync == MagickFalse)
1138  status=MagickFalse;
1139  if (image->progress_monitor != (MagickProgressMonitor) NULL)
1140  {
1142  proceed;
1143 
1144 #if defined(MAGICKCORE_OPENMP_SUPPORT)
1145  #pragma omp atomic
1146 #endif
1147  progress++;
1148  proceed=SetImageProgress(image,CopyImageTag,progress,image->rows);
1149  if (proceed == MagickFalse)
1150  status=MagickFalse;
1151  }
1152  }
1153  source_view=DestroyCacheView(source_view);
1154  image_view=DestroyCacheView(image_view);
1155  return(status);
1156 }
1157 
1158 /*
1159 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1160 % %
1161 % %
1162 % %
1163 % D e s t r o y I m a g e %
1164 % %
1165 % %
1166 % %
1167 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1168 %
1169 % DestroyImage() dereferences an image, deallocating memory associated with
1170 % the image if the reference count becomes zero.
1171 %
1172 % The format of the DestroyImage method is:
1173 %
1174 % Image *DestroyImage(Image *image)
1175 %
1176 % A description of each parameter follows:
1177 %
1178 % o image: the image.
1179 %
1180 */
1182 {
1184  destroy;
1185 
1186  /*
1187  Dereference image.
1188  */
1189  assert(image != (Image *) NULL);
1190  assert(image->signature == MagickCoreSignature);
1191  if (image->debug != MagickFalse)
1192  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1193  destroy=MagickFalse;
1194  LockSemaphoreInfo(image->semaphore);
1195  image->reference_count--;
1196  if (image->reference_count == 0)
1197  destroy=MagickTrue;
1199  if (destroy == MagickFalse)
1200  return((Image *) NULL);
1201  /*
1202  Destroy image.
1203  */
1204  DestroyImagePixels(image);
1206  if (image->montage != (char *) NULL)
1207  image->montage=DestroyString(image->montage);
1208  if (image->directory != (char *) NULL)
1209  image->directory=DestroyString(image->directory);
1210  if (image->colormap != (PixelInfo *) NULL)
1212  if (image->geometry != (char *) NULL)
1213  image->geometry=DestroyString(image->geometry);
1214  DestroyImageProfiles(image);
1215  DestroyImageProperties(image);
1216  DestroyImageArtifacts(image);
1217  if (image->ascii85 != (Ascii85Info *) NULL)
1219  if (image->image_info != (ImageInfo *) NULL)
1220  image->image_info=DestroyImageInfo(image->image_info);
1221  DestroyBlob(image);
1222  if (image->semaphore != (SemaphoreInfo *) NULL)
1224  image->signature=(~MagickCoreSignature);
1225  image=(Image *) RelinquishMagickMemory(image);
1226  return(image);
1227 }
1228 
1229 /*
1230 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1231 % %
1232 % %
1233 % %
1234 % D e s t r o y I m a g e I n f o %
1235 % %
1236 % %
1237 % %
1238 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1239 %
1240 % DestroyImageInfo() deallocates memory associated with an ImageInfo
1241 % structure.
1242 %
1243 % The format of the DestroyImageInfo method is:
1244 %
1245 % ImageInfo *DestroyImageInfo(ImageInfo *image_info)
1246 %
1247 % A description of each parameter follows:
1248 %
1249 % o image_info: the image info.
1250 %
1251 */
1253 {
1254  assert(image_info != (ImageInfo *) NULL);
1255  assert(image_info->signature == MagickCoreSignature);
1256  if (image_info->debug != MagickFalse)
1258  image_info->filename);
1259  if (image_info->size != (char *) NULL)
1260  image_info->size=DestroyString(image_info->size);
1261  if (image_info->extract != (char *) NULL)
1262  image_info->extract=DestroyString(image_info->extract);
1263  if (image_info->scenes != (char *) NULL)
1264  image_info->scenes=DestroyString(image_info->scenes);
1265  if (image_info->page != (char *) NULL)
1266  image_info->page=DestroyString(image_info->page);
1267  if (image_info->sampling_factor != (char *) NULL)
1268  image_info->sampling_factor=DestroyString(
1269  image_info->sampling_factor);
1270  if (image_info->server_name != (char *) NULL)
1271  image_info->server_name=DestroyString(
1272  image_info->server_name);
1273  if (image_info->font != (char *) NULL)
1274  image_info->font=DestroyString(image_info->font);
1275  if (image_info->texture != (char *) NULL)
1276  image_info->texture=DestroyString(image_info->texture);
1277  if (image_info->density != (char *) NULL)
1278  image_info->density=DestroyString(image_info->density);
1279  if (image_info->cache != (void *) NULL)
1280  image_info->cache=DestroyPixelCache(image_info->cache);
1281  if (image_info->profile != (StringInfo *) NULL)
1282  image_info->profile=(void *) DestroyStringInfo((StringInfo *)
1283  image_info->profile);
1284  DestroyImageOptions(image_info);
1285  image_info->signature=(~MagickCoreSignature);
1286  image_info=(ImageInfo *) RelinquishMagickMemory(image_info);
1287  return(image_info);
1288 }
1289 
1290 /*
1291 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1292 % %
1293 % %
1294 % %
1295 + D i s a s s o c i a t e I m a g e S t r e a m %
1296 % %
1297 % %
1298 % %
1299 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1300 %
1301 % DisassociateImageStream() disassociates the image stream. It checks if the
1302 % blob of the specified image is referenced by other images. If the reference
1303 % count is higher then 1 a new blob is assigned to the specified image.
1304 %
1305 % The format of the DisassociateImageStream method is:
1306 %
1307 % void DisassociateImageStream(const Image *image)
1308 %
1309 % A description of each parameter follows:
1310 %
1311 % o image: the image.
1312 %
1313 */
1315 {
1316  assert(image != (Image *) NULL);
1317  assert(image->signature == MagickCoreSignature);
1318  if (image->debug != MagickFalse)
1319  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1320  DisassociateBlob(image);
1321 }
1322 
1323 /*
1324 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1325 % %
1326 % %
1327 % %
1328 % G e t I m a g e I n f o %
1329 % %
1330 % %
1331 % %
1332 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1333 %
1334 % GetImageInfo() initializes image_info to default values.
1335 %
1336 % The format of the GetImageInfo method is:
1337 %
1338 % void GetImageInfo(ImageInfo *image_info)
1339 %
1340 % A description of each parameter follows:
1341 %
1342 % o image_info: the image info.
1343 %
1344 */
1346 {
1347  char
1348  *synchronize;
1349 
1351  *exception;
1352 
1353  /*
1354  File and image dimension members.
1355  */
1356  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1357  assert(image_info != (ImageInfo *) NULL);
1358  (void) memset(image_info,0,sizeof(*image_info));
1359  image_info->adjoin=MagickTrue;
1360  image_info->interlace=NoInterlace;
1361  image_info->channel=DefaultChannels;
1363  image_info->antialias=MagickTrue;
1364  image_info->dither=MagickTrue;
1365  synchronize=GetEnvironmentValue("MAGICK_SYNCHRONIZE");
1366  if (synchronize != (const char *) NULL)
1367  {
1368  image_info->synchronize=IsStringTrue(synchronize);
1369  synchronize=DestroyString(synchronize);
1370  }
1371  exception=AcquireExceptionInfo();
1373  &image_info->background_color,exception);
1375  &image_info->border_color,exception);
1377  exception);
1379  &image_info->transparent_color,exception);
1380  exception=DestroyExceptionInfo(exception);
1381  image_info->debug=IsEventLogging();
1382  image_info->signature=MagickCoreSignature;
1383 }
1384 
1385 /*
1386 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1387 % %
1388 % %
1389 % %
1390 % G e t I m a g e I n f o F i l e %
1391 % %
1392 % %
1393 % %
1394 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1395 %
1396 % GetImageInfoFile() returns the image info file member.
1397 %
1398 % The format of the GetImageInfoFile method is:
1399 %
1400 % FILE *GetImageInfoFile(const ImageInfo *image_info)
1401 %
1402 % A description of each parameter follows:
1403 %
1404 % o image_info: the image info.
1405 %
1406 */
1407 MagickExport FILE *GetImageInfoFile(const ImageInfo *image_info)
1408 {
1409  return(image_info->file);
1410 }
1411 
1412 /*
1413 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1414 % %
1415 % %
1416 % %
1417 % G e t I m a g e M a s k %
1418 % %
1419 % %
1420 % %
1421 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1422 %
1423 % GetImageMask() returns the mask associated with the image.
1424 %
1425 % The format of the GetImageMask method is:
1426 %
1427 % Image *GetImageMask(const Image *image,const PixelMask type,
1428 % ExceptionInfo *exception)
1429 %
1430 % A description of each parameter follows:
1431 %
1432 % o image: the image.
1433 %
1434 % o type: the mask type, ReadPixelMask or WritePixelMask.
1435 %
1436 */
1439 {
1440  CacheView
1441  *mask_view,
1442  *image_view;
1443 
1444  Image
1445  *mask_image;
1446 
1448  status;
1449 
1450  ssize_t
1451  y;
1452 
1453  /*
1454  Get image mask.
1455  */
1456  assert(image != (Image *) NULL);
1457  if (image->debug != MagickFalse)
1458  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1459  assert(image->signature == MagickCoreSignature);
1460  switch (type)
1461  {
1462  case ReadPixelMask:
1463  {
1464  if ((image->channels & ReadMaskChannel) == 0)
1465  return((Image *) NULL);
1466  break;
1467  }
1468  case WritePixelMask:
1469  {
1470  if ((image->channels & WriteMaskChannel) == 0)
1471  return((Image *) NULL);
1472  break;
1473  }
1474  default:
1475  {
1476  if ((image->channels & CompositeMaskChannel) == 0)
1477  return((Image *) NULL);
1478  break;
1479  }
1480  }
1481  mask_image=AcquireImage((ImageInfo *) NULL,exception);
1482  status=SetImageExtent(mask_image,image->columns,image->rows,exception);
1483  if (status == MagickFalse)
1484  return(DestroyImage(mask_image));
1485  status=MagickTrue;
1486  mask_image->alpha_trait=UndefinedPixelTrait;
1487  (void) SetImageColorspace(mask_image,GRAYColorspace,exception);
1488  image_view=AcquireVirtualCacheView(image,exception);
1489  mask_view=AcquireAuthenticCacheView(mask_image,exception);
1490  for (y=0; y < (ssize_t) image->rows; y++)
1491  {
1492  register const Quantum
1493  *magick_restrict p;
1494 
1495  register Quantum
1496  *magick_restrict q;
1497 
1498  register ssize_t
1499  x;
1500 
1501  if (status == MagickFalse)
1502  continue;
1503  p=GetCacheViewVirtualPixels(image_view,0,y,image->columns,1,exception);
1504  q=GetCacheViewAuthenticPixels(mask_view,0,y,mask_image->columns,1,
1505  exception);
1506  if ((p == (const Quantum *) NULL) || (q == (Quantum *) NULL))
1507  {
1508  status=MagickFalse;
1509  continue;
1510  }
1511  for (x=0; x < (ssize_t) image->columns; x++)
1512  {
1513  switch (type)
1514  {
1515  case ReadPixelMask:
1516  {
1517  SetPixelGray(mask_image,GetPixelReadMask(image,p),q);
1518  break;
1519  }
1520  case WritePixelMask:
1521  {
1522  SetPixelGray(mask_image,GetPixelWriteMask(image,p),q);
1523  break;
1524  }
1525  default:
1526  {
1527  SetPixelGray(mask_image,GetPixelCompositeMask(image,p),q);
1528  break;
1529  }
1530  }
1531  p+=GetPixelChannels(image);
1532  q+=GetPixelChannels(mask_image);
1533  }
1534  if (SyncCacheViewAuthenticPixels(mask_view,exception) == MagickFalse)
1535  status=MagickFalse;
1536  }
1537  mask_view=DestroyCacheView(mask_view);
1538  image_view=DestroyCacheView(image_view);
1539  if (status == MagickFalse)
1540  mask_image=DestroyImage(mask_image);
1541  return(mask_image);
1542 }
1543 
1544 /*
1545 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1546 % %
1547 % %
1548 % %
1549 + G e t I m a g e R e f e r e n c e C o u n t %
1550 % %
1551 % %
1552 % %
1553 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1554 %
1555 % GetImageReferenceCount() returns the image reference count.
1556 %
1557 % The format of the GetReferenceCount method is:
1558 %
1559 % ssize_t GetImageReferenceCount(Image *image)
1560 %
1561 % A description of each parameter follows:
1562 %
1563 % o image: the image.
1564 %
1565 */
1567 {
1568  ssize_t
1569  reference_count;
1570 
1571  assert(image != (Image *) NULL);
1572  assert(image->signature == MagickCoreSignature);
1573  if (image->debug != MagickFalse)
1574  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1575  LockSemaphoreInfo(image->semaphore);
1576  reference_count=image->reference_count;
1578  return(reference_count);
1579 }
1580 
1581 /*
1582 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1583 % %
1584 % %
1585 % %
1586 % G e t I m a g e V i r t u a l P i x e l M e t h o d %
1587 % %
1588 % %
1589 % %
1590 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1591 %
1592 % GetImageVirtualPixelMethod() gets the "virtual pixels" method for the
1593 % image. A virtual pixel is any pixel access that is outside the boundaries
1594 % of the image cache.
1595 %
1596 % The format of the GetImageVirtualPixelMethod() method is:
1597 %
1598 % VirtualPixelMethod GetImageVirtualPixelMethod(const Image *image)
1599 %
1600 % A description of each parameter follows:
1601 %
1602 % o image: the image.
1603 %
1604 */
1606 {
1607  assert(image != (Image *) NULL);
1608  assert(image->signature == MagickCoreSignature);
1609  if (image->debug != MagickFalse)
1610  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1611  return(GetPixelCacheVirtualMethod(image));
1612 }
1613 
1614 /*
1615 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1616 % %
1617 % %
1618 % %
1619 % I n t e r p r e t I m a g e F i l e n a m e %
1620 % %
1621 % %
1622 % %
1623 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1624 %
1625 % InterpretImageFilename() interprets embedded characters in an image filename.
1626 % The filename length is returned.
1627 %
1628 % The format of the InterpretImageFilename method is:
1629 %
1630 % size_t InterpretImageFilename(const ImageInfo *image_info,Image *image,
1631 % const char *format,int value,char *filename,ExceptionInfo *exception)
1632 %
1633 % A description of each parameter follows.
1634 %
1635 % o image_info: the image info..
1636 %
1637 % o image: the image.
1638 %
1639 % o format: A filename describing the format to use to write the numeric
1640 % argument. Only the first numeric format identifier is replaced.
1641 %
1642 % o value: Numeric value to substitute into format filename.
1643 %
1644 % o filename: return the formatted filename in this character buffer.
1645 %
1646 % o exception: return any errors or warnings in this structure.
1647 %
1648 */
1650  Image *image,const char *format,int value,char *filename,
1652 {
1653  char
1654  *q;
1655 
1656  int
1657  c;
1658 
1660  canonical;
1661 
1662  register const char
1663  *p;
1664 
1665  ssize_t
1666  field_width,
1667  offset;
1668 
1669  canonical=MagickFalse;
1670  offset=0;
1671  (void) CopyMagickString(filename,format,MagickPathExtent);
1672  for (p=strchr(format,'%'); p != (char *) NULL; p=strchr(p+1,'%'))
1673  {
1674  q=(char *) p+1;
1675  if (*q == '%')
1676  {
1677  p=q+1;
1678  continue;
1679  }
1680  field_width=0;
1681  if (*q == '0')
1682  field_width=(ssize_t) strtol(q,&q,10);
1683  switch (*q)
1684  {
1685  case 'd':
1686  case 'o':
1687  case 'x':
1688  {
1689  q++;
1690  c=(*q);
1691  *q='\0';
1692  (void) FormatLocaleString(filename+(p-format-offset),(size_t)
1693  (MagickPathExtent-(p-format-offset)),p,value);
1694  offset+=(4-field_width);
1695  *q=c;
1696  (void) ConcatenateMagickString(filename,q,MagickPathExtent);
1697  canonical=MagickTrue;
1698  if (*(q-1) != '%')
1699  break;
1700  p++;
1701  break;
1702  }
1703  case '[':
1704  {
1705  char
1706  pattern[MagickPathExtent];
1707 
1708  const char
1709  *option;
1710 
1711  register char
1712  *r;
1713 
1714  register ssize_t
1715  i;
1716 
1717  ssize_t
1718  depth;
1719 
1720  /*
1721  Image option.
1722  */
1723  if (strchr(p,']') == (char *) NULL)
1724  break;
1725  depth=1;
1726  r=q+1;
1727  for (i=0; (i < (MagickPathExtent-1L)) && (*r != '\0'); i++)
1728  {
1729  if (*r == '[')
1730  depth++;
1731  if (*r == ']')
1732  depth--;
1733  if (depth <= 0)
1734  break;
1735  pattern[i]=(*r++);
1736  }
1737  pattern[i]='\0';
1738  if (LocaleNCompare(pattern,"filename:",9) != 0)
1739  break;
1740  option=(const char *) NULL;
1741  if (image != (Image *) NULL)
1742  option=GetImageProperty(image,pattern,exception);
1743  if ((option == (const char *) NULL) && (image != (Image *) NULL))
1744  option=GetImageArtifact(image,pattern);
1745  if ((option == (const char *) NULL) &&
1746  (image_info != (ImageInfo *) NULL))
1747  option=GetImageOption(image_info,pattern);
1748  if (option == (const char *) NULL)
1749  break;
1750  q--;
1751  c=(*q);
1752  *q='\0';
1753  (void) CopyMagickString(filename+(p-format-offset),option,(size_t)
1754  (MagickPathExtent-(p-format-offset)));
1755  offset+=strlen(pattern)-strlen(option)+3;
1756  *q=c;
1757  (void) ConcatenateMagickString(filename,r+1,MagickPathExtent);
1758  canonical=MagickTrue;
1759  if (*(q-1) != '%')
1760  break;
1761  p++;
1762  break;
1763  }
1764  default:
1765  break;
1766  }
1767  }
1768  for (q=filename; *q != '\0'; q++)
1769  if ((*q == '%') && (*(q+1) == '%'))
1770  {
1771  (void) CopyMagickString(q,q+1,(size_t) (MagickPathExtent-(q-filename)));
1772  canonical=MagickTrue;
1773  }
1774  if (canonical == MagickFalse)
1775  (void) CopyMagickString(filename,format,MagickPathExtent);
1776  return(strlen(filename));
1777 }
1778 
1779 /*
1780 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1781 % %
1782 % %
1783 % %
1784 % I s H i g h D y n a m i c R a n g e I m a g e %
1785 % %
1786 % %
1787 % %
1788 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1789 %
1790 % IsHighDynamicRangeImage() returns MagickTrue if any pixel component is
1791 % non-integer or exceeds the bounds of the quantum depth (e.g. for Q16
1792 % 0..65535.
1793 %
1794 % The format of the IsHighDynamicRangeImage method is:
1795 %
1796 % MagickBooleanType IsHighDynamicRangeImage(const Image *image,
1797 % ExceptionInfo *exception)
1798 %
1799 % A description of each parameter follows:
1800 %
1801 % o image: the image.
1802 %
1803 % o exception: return any errors or warnings in this structure.
1804 %
1805 */
1808 {
1809 #if !defined(MAGICKCORE_HDRI_SUPPORT)
1810  (void) image;
1811  (void) exception;
1812  return(MagickFalse);
1813 #else
1814  CacheView
1815  *image_view;
1816 
1818  status;
1819 
1820  ssize_t
1821  y;
1822 
1823  assert(image != (Image *) NULL);
1824  assert(image->signature == MagickCoreSignature);
1825  if (image->debug != MagickFalse)
1826  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1827  status=MagickTrue;
1828  image_view=AcquireVirtualCacheView(image,exception);
1829 #if defined(MAGICKCORE_OPENMP_SUPPORT)
1830  #pragma omp parallel for schedule(static) shared(status) \
1831  magick_number_threads(image,image,image->rows,1)
1832 #endif
1833  for (y=0; y < (ssize_t) image->rows; y++)
1834  {
1835  register const Quantum
1836  *p;
1837 
1838  register ssize_t
1839  x;
1840 
1841  if (status == MagickFalse)
1842  continue;
1843  p=GetCacheViewVirtualPixels(image_view,0,y,image->columns,1,exception);
1844  if (p == (const Quantum *) NULL)
1845  {
1846  status=MagickFalse;
1847  continue;
1848  }
1849  for (x=0; x < (ssize_t) image->columns; x++)
1850  {
1851  register ssize_t
1852  i;
1853 
1854  for (i=0; i < (ssize_t) GetPixelChannels(image); i++)
1855  {
1856  double
1857  pixel;
1858 
1859  PixelTrait
1860  traits;
1861 
1862  traits=GetPixelChannelTraits(image,(PixelChannel) i);
1863  if (traits == UndefinedPixelTrait)
1864  continue;
1865  pixel=(double) p[i];
1866  if ((pixel < 0.0) || (pixel > QuantumRange) ||
1867  (pixel != (double) ((QuantumAny) pixel)))
1868  break;
1869  }
1870  p+=GetPixelChannels(image);
1871  if (i < (ssize_t) GetPixelChannels(image))
1872  status=MagickFalse;
1873  }
1874  if (x < (ssize_t) image->columns)
1875  status=MagickFalse;
1876  }
1877  image_view=DestroyCacheView(image_view);
1878  return(status != MagickFalse ? MagickFalse : MagickTrue);
1879 #endif
1880 }
1881 
1882 /*
1883 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1884 % %
1885 % %
1886 % %
1887 % I s I m a g e O b j e c t %
1888 % %
1889 % %
1890 % %
1891 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1892 %
1893 % IsImageObject() returns MagickTrue if the image sequence contains a valid
1894 % set of image objects.
1895 %
1896 % The format of the IsImageObject method is:
1897 %
1898 % MagickBooleanType IsImageObject(const Image *image)
1899 %
1900 % A description of each parameter follows:
1901 %
1902 % o image: the image.
1903 %
1904 */
1906 {
1907  register const Image
1908  *p;
1909 
1910  assert(image != (Image *) NULL);
1911  if (image->debug != MagickFalse)
1912  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1913  for (p=image; p != (Image *) NULL; p=GetNextImageInList(p))
1914  if (p->signature != MagickCoreSignature)
1915  return(MagickFalse);
1916  return(MagickTrue);
1917 }
1918 
1919 /*
1920 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1921 % %
1922 % %
1923 % %
1924 % I s T a i n t I m a g e %
1925 % %
1926 % %
1927 % %
1928 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1929 %
1930 % IsTaintImage() returns MagickTrue any pixel in the image has been altered
1931 % since it was first constituted.
1932 %
1933 % The format of the IsTaintImage method is:
1934 %
1935 % MagickBooleanType IsTaintImage(const Image *image)
1936 %
1937 % A description of each parameter follows:
1938 %
1939 % o image: the image.
1940 %
1941 */
1943 {
1944  char
1945  magick[MagickPathExtent],
1946  filename[MagickPathExtent];
1947 
1948  register const Image
1949  *p;
1950 
1951  assert(image != (Image *) NULL);
1952  if (image->debug != MagickFalse)
1953  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1954  assert(image->signature == MagickCoreSignature);
1955  (void) CopyMagickString(magick,image->magick,MagickPathExtent);
1956  (void) CopyMagickString(filename,image->filename,MagickPathExtent);
1957  for (p=image; p != (Image *) NULL; p=GetNextImageInList(p))
1958  {
1959  if (p->taint != MagickFalse)
1960  return(MagickTrue);
1961  if (LocaleCompare(p->magick,magick) != 0)
1962  return(MagickTrue);
1963  if (LocaleCompare(p->filename,filename) != 0)
1964  return(MagickTrue);
1965  }
1966  return(MagickFalse);
1967 }
1968 
1969 /*
1970 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1971 % %
1972 % %
1973 % %
1974 % M o d i f y I m a g e %
1975 % %
1976 % %
1977 % %
1978 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1979 %
1980 % ModifyImage() ensures that there is only a single reference to the image
1981 % to be modified, updating the provided image pointer to point to a clone of
1982 % the original image if necessary.
1983 %
1984 % The format of the ModifyImage method is:
1985 %
1986 % MagickBooleanType ModifyImage(Image *image,ExceptionInfo *exception)
1987 %
1988 % A description of each parameter follows:
1989 %
1990 % o image: the image.
1991 %
1992 % o exception: return any errors or warnings in this structure.
1993 %
1994 */
1997 {
1998  Image
1999  *clone_image;
2000 
2001  assert(image != (Image **) NULL);
2002  assert(*image != (Image *) NULL);
2003  assert((*image)->signature == MagickCoreSignature);
2004  if ((*image)->debug != MagickFalse)
2005  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",(*image)->filename);
2006  if (GetImageReferenceCount(*image) <= 1)
2007  return(MagickTrue);
2008  clone_image=CloneImage(*image,0,0,MagickTrue,exception);
2009  LockSemaphoreInfo((*image)->semaphore);
2010  (*image)->reference_count--;
2011  UnlockSemaphoreInfo((*image)->semaphore);
2012  *image=clone_image;
2013  return(MagickTrue);
2014 }
2015 
2016 /*
2017 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2018 % %
2019 % %
2020 % %
2021 % N e w M a g i c k I m a g e %
2022 % %
2023 % %
2024 % %
2025 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2026 %
2027 % NewMagickImage() creates a blank image canvas of the specified size and
2028 % background color.
2029 %
2030 % The format of the NewMagickImage method is:
2031 %
2032 % Image *NewMagickImage(const ImageInfo *image_info,const size_t width,
2033 % const size_t height,const PixelInfo *background,
2034 % ExceptionInfo *exception)
2035 %
2036 % A description of each parameter follows:
2037 %
2038 % o image: the image.
2039 %
2040 % o width: the image width.
2041 %
2042 % o height: the image height.
2043 %
2044 % o background: the image color.
2045 %
2046 % o exception: return any errors or warnings in this structure.
2047 %
2048 */
2050  const size_t width,const size_t height,const PixelInfo *background,
2052 {
2053  CacheView
2054  *image_view;
2055 
2056  Image
2057  *image;
2058 
2060  status;
2061 
2062  ssize_t
2063  y;
2064 
2065  assert(image_info != (const ImageInfo *) NULL);
2066  if (image_info->debug != MagickFalse)
2067  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2068  assert(image_info->signature == MagickCoreSignature);
2069  assert(background != (const PixelInfo *) NULL);
2070  image=AcquireImage(image_info,exception);
2071  image->columns=width;
2072  image->rows=height;
2073  image->colorspace=background->colorspace;
2074  image->alpha_trait=background->alpha_trait;
2075  image->fuzz=background->fuzz;
2076  image->depth=background->depth;
2077  status=MagickTrue;
2078  image_view=AcquireAuthenticCacheView(image,exception);
2079 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2080  #pragma omp parallel for schedule(static) shared(status) \
2081  magick_number_threads(image,image,image->rows,1)
2082 #endif
2083  for (y=0; y < (ssize_t) image->rows; y++)
2084  {
2085  register Quantum
2086  *magick_restrict q;
2087 
2088  register ssize_t
2089  x;
2090 
2091  if (status == MagickFalse)
2092  continue;
2093  q=QueueCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2094  if (q == (Quantum *) NULL)
2095  {
2096  status=MagickFalse;
2097  continue;
2098  }
2099  for (x=0; x < (ssize_t) image->columns; x++)
2100  {
2101  SetPixelViaPixelInfo(image,background,q);
2102  q+=GetPixelChannels(image);
2103  }
2104  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2105  status=MagickFalse;
2106  }
2107  image_view=DestroyCacheView(image_view);
2108  if (status == MagickFalse)
2109  image=DestroyImage(image);
2110  return(image);
2111 }
2112 
2113 /*
2114 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2115 % %
2116 % %
2117 % %
2118 % R e f e r e n c e I m a g e %
2119 % %
2120 % %
2121 % %
2122 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2123 %
2124 % ReferenceImage() increments the reference count associated with an image
2125 % returning a pointer to the image.
2126 %
2127 % The format of the ReferenceImage method is:
2128 %
2129 % Image *ReferenceImage(Image *image)
2130 %
2131 % A description of each parameter follows:
2132 %
2133 % o image: the image.
2134 %
2135 */
2137 {
2138  assert(image != (Image *) NULL);
2139  if (image->debug != MagickFalse)
2140  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2141  assert(image->signature == MagickCoreSignature);
2142  LockSemaphoreInfo(image->semaphore);
2143  image->reference_count++;
2145  return(image);
2146 }
2147 
2148 /*
2149 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2150 % %
2151 % %
2152 % %
2153 % R e s e t I m a g e P a g e %
2154 % %
2155 % %
2156 % %
2157 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2158 %
2159 % ResetImagePage() resets the image page canvas and position.
2160 %
2161 % The format of the ResetImagePage method is:
2162 %
2163 % MagickBooleanType ResetImagePage(Image *image,const char *page)
2164 %
2165 % A description of each parameter follows:
2166 %
2167 % o image: the image.
2168 %
2169 % o page: the relative page specification.
2170 %
2171 */
2173 {
2175  flags;
2176 
2178  geometry;
2179 
2180  assert(image != (Image *) NULL);
2181  assert(image->signature == MagickCoreSignature);
2182  if (image->debug != MagickFalse)
2183  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
2184  flags=ParseAbsoluteGeometry(page,&geometry);
2185  if ((flags & WidthValue) != 0)
2186  {
2187  if ((flags & HeightValue) == 0)
2188  geometry.height=geometry.width;
2189  image->page.width=geometry.width;
2190  image->page.height=geometry.height;
2191  }
2192  if ((flags & AspectValue) != 0)
2193  {
2194  if ((flags & XValue) != 0)
2195  image->page.x+=geometry.x;
2196  if ((flags & YValue) != 0)
2197  image->page.y+=geometry.y;
2198  }
2199  else
2200  {
2201  if ((flags & XValue) != 0)
2202  {
2203  image->page.x=geometry.x;
2204  if ((image->page.width == 0) && (geometry.x > 0))
2205  image->page.width=image->columns+geometry.x;
2206  }
2207  if ((flags & YValue) != 0)
2208  {
2209  image->page.y=geometry.y;
2210  if ((image->page.height == 0) && (geometry.y > 0))
2211  image->page.height=image->rows+geometry.y;
2212  }
2213  }
2214  return(MagickTrue);
2215 }
2216 
2217 /*
2218 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2219 % %
2220 % %
2221 % %
2222 % R e s e t I m a g e P i x e l s %
2223 % %
2224 % %
2225 % %
2226 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2227 %
2228 % ResetImagePixels() reset the image pixels, that is, all the pixel components
2229 % are zereod.
2230 %
2231 % The format of the SetImage method is:
2232 %
2233 % MagickBooleanType ResetImagePixels(Image *image,
2234 % ExceptionInfo *exception)
2235 %
2236 % A description of each parameter follows:
2237 %
2238 % o image: the image.
2239 %
2240 % o exception: return any errors or warnings in this structure.
2241 %
2242 */
2245 {
2246  CacheView
2247  *image_view;
2248 
2250  status;
2251 
2252  size_t
2253  length;
2254 
2255  ssize_t
2256  y;
2257 
2258  void
2259  *pixels;
2260 
2261  assert(image != (Image *) NULL);
2262  if (image->debug != MagickFalse)
2263  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2264  assert(image->signature == MagickCoreSignature);
2265  pixels=AcquirePixelCachePixels(image,&length,exception);
2266  if (pixels != (void *) NULL)
2267  {
2268  /*
2269  Reset in-core image pixels.
2270  */
2271  (void) memset(pixels,0,length);
2272  return(MagickTrue);
2273  }
2274  /*
2275  Reset image pixels.
2276  */
2277  status=MagickTrue;
2278  image_view=AcquireAuthenticCacheView(image,exception);
2279 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2280  #pragma omp parallel for schedule(static) shared(status) \
2281  magick_number_threads(image,image,image->rows,1)
2282 #endif
2283  for (y=0; y < (ssize_t) image->rows; y++)
2284  {
2285  register Quantum
2286  *magick_restrict q;
2287 
2288  register ssize_t
2289  x;
2290 
2291  if (status == MagickFalse)
2292  continue;
2293  q=QueueCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2294  if (q == (Quantum *) NULL)
2295  {
2296  status=MagickFalse;
2297  continue;
2298  }
2299  for (x=0; x < (ssize_t) image->columns; x++)
2300  {
2301  (void) memset(q,0,GetPixelChannels(image)*sizeof(Quantum));
2302  q+=GetPixelChannels(image);
2303  }
2304  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2305  status=MagickFalse;
2306  }
2307  image_view=DestroyCacheView(image_view);
2308  return(status);
2309 }
2310 
2311 /*
2312 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2313 % %
2314 % %
2315 % %
2316 % S e t I m a g e A l p h a %
2317 % %
2318 % %
2319 % %
2320 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2321 %
2322 % SetImageAlpha() sets the alpha levels of the image.
2323 %
2324 % The format of the SetImageAlpha method is:
2325 %
2326 % MagickBooleanType SetImageAlpha(Image *image,const Quantum alpha,
2327 % ExceptionInfo *exception)
2328 %
2329 % A description of each parameter follows:
2330 %
2331 % o image: the image.
2332 %
2333 % o alpha: the level of transparency: 0 is fully transparent and QuantumRange
2334 % is fully opaque.
2335 %
2336 % o exception: return any errors or warnings in this structure.
2337 %
2338 */
2341 {
2342  CacheView
2343  *image_view;
2344 
2346  status;
2347 
2348  ssize_t
2349  y;
2350 
2351  assert(image != (Image *) NULL);
2352  if (image->debug != MagickFalse)
2353  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2354  assert(image->signature == MagickCoreSignature);
2356  status=MagickTrue;
2357  image_view=AcquireAuthenticCacheView(image,exception);
2358 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2359  #pragma omp parallel for schedule(static) shared(status) \
2360  magick_number_threads(image,image,image->rows,1)
2361 #endif
2362  for (y=0; y < (ssize_t) image->rows; y++)
2363  {
2364  register Quantum
2365  *magick_restrict q;
2366 
2367  register ssize_t
2368  x;
2369 
2370  if (status == MagickFalse)
2371  continue;
2372  q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2373  if (q == (Quantum *) NULL)
2374  {
2375  status=MagickFalse;
2376  continue;
2377  }
2378  for (x=0; x < (ssize_t) image->columns; x++)
2379  {
2380  SetPixelAlpha(image,alpha,q);
2381  q+=GetPixelChannels(image);
2382  }
2383  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2384  status=MagickFalse;
2385  }
2386  image_view=DestroyCacheView(image_view);
2387  return(status);
2388 }
2389 
2390 /*
2391 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2392 % %
2393 % %
2394 % %
2395 % S e t I m a g e B a c k g r o u n d C o l o r %
2396 % %
2397 % %
2398 % %
2399 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2400 %
2401 % SetImageBackgroundColor() initializes the image pixels to the image
2402 % background color. The background color is defined by the background_color
2403 % member of the image structure.
2404 %
2405 % The format of the SetImage method is:
2406 %
2407 % MagickBooleanType SetImageBackgroundColor(Image *image,
2408 % ExceptionInfo *exception)
2409 %
2410 % A description of each parameter follows:
2411 %
2412 % o image: the image.
2413 %
2414 % o exception: return any errors or warnings in this structure.
2415 %
2416 */
2419 {
2420  CacheView
2421  *image_view;
2422 
2424  status;
2425 
2426  PixelInfo
2427  background;
2428 
2429  ssize_t
2430  y;
2431 
2432  assert(image != (Image *) NULL);
2433  if (image->debug != MagickFalse)
2434  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2435  assert(image->signature == MagickCoreSignature);
2436  if (SetImageStorageClass(image,DirectClass,exception) == MagickFalse)
2437  return(MagickFalse);
2438  if ((image->background_color.alpha != OpaqueAlpha) &&
2439  (image->alpha_trait == UndefinedPixelTrait))
2440  (void) SetImageAlphaChannel(image,OnAlphaChannel,exception);
2441  ConformPixelInfo(image,&image->background_color,&background,exception);
2442  /*
2443  Set image background color.
2444  */
2445  status=MagickTrue;
2446  image_view=AcquireAuthenticCacheView(image,exception);
2447  for (y=0; y < (ssize_t) image->rows; y++)
2448  {
2449  register Quantum
2450  *magick_restrict q;
2451 
2452  register ssize_t
2453  x;
2454 
2455  if (status == MagickFalse)
2456  continue;
2457  q=QueueCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2458  if (q == (Quantum *) NULL)
2459  {
2460  status=MagickFalse;
2461  continue;
2462  }
2463  for (x=0; x < (ssize_t) image->columns; x++)
2464  {
2465  SetPixelViaPixelInfo(image,&background,q);
2466  q+=GetPixelChannels(image);
2467  }
2468  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2469  status=MagickFalse;
2470  }
2471  image_view=DestroyCacheView(image_view);
2472  return(status);
2473 }
2474 
2475 /*
2476 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2477 % %
2478 % %
2479 % %
2480 % S e t I m a g e C h a n n e l M a s k %
2481 % %
2482 % %
2483 % %
2484 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2485 %
2486 % SetImageChannelMask() sets the image channel mask from the specified channel
2487 % mask.
2488 %
2489 % The format of the SetImageChannelMask method is:
2490 %
2491 % ChannelType SetImageChannelMask(Image *image,
2492 % const ChannelType channel_mask)
2493 %
2494 % A description of each parameter follows:
2495 %
2496 % o image: the image.
2497 %
2498 % o channel_mask: the channel mask.
2499 %
2500 */
2502  const ChannelType channel_mask)
2503 {
2504  return(SetPixelChannelMask(image,channel_mask));
2505 }
2506 
2507 /*
2508 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2509 % %
2510 % %
2511 % %
2512 % S e t I m a g e C o l o r %
2513 % %
2514 % %
2515 % %
2516 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2517 %
2518 % SetImageColor() set the entire image canvas to the specified color.
2519 %
2520 % The format of the SetImageColor method is:
2521 %
2522 % MagickBooleanType SetImageColor(Image *image,const PixelInfo *color,
2523 % ExeptionInfo *exception)
2524 %
2525 % A description of each parameter follows:
2526 %
2527 % o image: the image.
2528 %
2529 % o background: the image color.
2530 %
2531 % o exception: return any errors or warnings in this structure.
2532 %
2533 */
2535  const PixelInfo *color,ExceptionInfo *exception)
2536 {
2537  CacheView
2538  *image_view;
2539 
2541  status;
2542 
2543  ssize_t
2544  y;
2545 
2546  assert(image != (Image *) NULL);
2547  if (image->debug != MagickFalse)
2548  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2549  assert(image->signature == MagickCoreSignature);
2550  assert(color != (const PixelInfo *) NULL);
2551  image->colorspace=color->colorspace;
2552  image->alpha_trait=color->alpha_trait;
2553  image->fuzz=color->fuzz;
2554  image->depth=color->depth;
2555  status=MagickTrue;
2556  image_view=AcquireAuthenticCacheView(image,exception);
2557 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2558  #pragma omp parallel for schedule(static) shared(status) \
2559  magick_number_threads(image,image,image->rows,1)
2560 #endif
2561  for (y=0; y < (ssize_t) image->rows; y++)
2562  {
2563  register Quantum
2564  *magick_restrict q;
2565 
2566  register ssize_t
2567  x;
2568 
2569  if (status == MagickFalse)
2570  continue;
2571  q=QueueCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2572  if (q == (Quantum *) NULL)
2573  {
2574  status=MagickFalse;
2575  continue;
2576  }
2577  for (x=0; x < (ssize_t) image->columns; x++)
2578  {
2579  SetPixelViaPixelInfo(image,color,q);
2580  q+=GetPixelChannels(image);
2581  }
2582  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2583  status=MagickFalse;
2584  }
2585  image_view=DestroyCacheView(image_view);
2586  return(status);
2587 }
2588 
2589 /*
2590 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2591 % %
2592 % %
2593 % %
2594 % S e t I m a g e S t o r a g e C l a s s %
2595 % %
2596 % %
2597 % %
2598 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2599 %
2600 % SetImageStorageClass() sets the image class: DirectClass for true color
2601 % images or PseudoClass for colormapped images.
2602 %
2603 % The format of the SetImageStorageClass method is:
2604 %
2605 % MagickBooleanType SetImageStorageClass(Image *image,
2606 % const ClassType storage_class,ExceptionInfo *exception)
2607 %
2608 % A description of each parameter follows:
2609 %
2610 % o image: the image.
2611 %
2612 % o storage_class: The image class.
2613 %
2614 % o exception: return any errors or warnings in this structure.
2615 %
2616 */
2618  const ClassType storage_class,ExceptionInfo *exception)
2619 {
2620  assert(image != (Image *) NULL);
2621  assert(image->signature == MagickCoreSignature);
2622  if (image->debug != MagickFalse)
2623  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
2624  assert(exception != (ExceptionInfo *) NULL);
2625  assert(exception->signature == MagickCoreSignature);
2626  image->storage_class=storage_class;
2627  return(SyncImagePixelCache(image,exception));
2628 }
2629 
2630 /*
2631 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2632 % %
2633 % %
2634 % %
2635 % S e t I m a g e E x t e n t %
2636 % %
2637 % %
2638 % %
2639 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2640 %
2641 % SetImageExtent() sets the image size (i.e. columns & rows).
2642 %
2643 % The format of the SetImageExtent method is:
2644 %
2645 % MagickBooleanType SetImageExtent(Image *image,const size_t columns,
2646 % const size_t rows,ExceptionInfo *exception)
2647 %
2648 % A description of each parameter follows:
2649 %
2650 % o image: the image.
2651 %
2652 % o columns: The image width in pixels.
2653 %
2654 % o rows: The image height in pixels.
2655 %
2656 % o exception: return any errors or warnings in this structure.
2657 %
2658 */
2660  const size_t rows,ExceptionInfo *exception)
2661 {
2662  if ((columns == 0) || (rows == 0))
2663  ThrowBinaryException(ImageError,"NegativeOrZeroImageSize",image->filename);
2664  image->columns=columns;
2665  image->rows=rows;
2666  if ((image->depth == 0) || (image->depth > (8*sizeof(MagickSizeType))))
2667  ThrowBinaryException(ImageError,"ImageDepthNotSupported",image->filename);
2668  return(SyncImagePixelCache(image,exception));
2669 }
2670 
2671 /*
2672 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2673 % %
2674 % %
2675 % %
2676 + S e t I m a g e I n f o %
2677 % %
2678 % %
2679 % %
2680 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2681 %
2682 % SetImageInfo() initializes the 'magick' field of the ImageInfo structure.
2683 % It is set to a type of image format based on the prefix or suffix of the
2684 % filename. For example, 'ps:image' returns PS indicating a Postscript image.
2685 % JPEG is returned for this filename: 'image.jpg'. The filename prefix has
2686 % precendence over the suffix. Use an optional index enclosed in brackets
2687 % after a file name to specify a desired scene of a multi-resolution image
2688 % format like Photo CD (e.g. img0001.pcd[4]). A True (non-zero) return value
2689 % indicates success.
2690 %
2691 % The format of the SetImageInfo method is:
2692 %
2693 % MagickBooleanType SetImageInfo(ImageInfo *image_info,
2694 % const unsigned int frames,ExceptionInfo *exception)
2695 %
2696 % A description of each parameter follows:
2697 %
2698 % o image_info: the image info.
2699 %
2700 % o frames: the number of images you intend to write.
2701 %
2702 % o exception: return any errors or warnings in this structure.
2703 %
2704 */
2706  const unsigned int frames,ExceptionInfo *exception)
2707 {
2708  char
2709  component[MagickPathExtent],
2710  magic[MagickPathExtent],
2711  *q;
2712 
2713  const MagicInfo
2714  *magic_info;
2715 
2716  const MagickInfo
2717  *magick_info;
2718 
2720  *sans_exception;
2721 
2722  Image
2723  *image;
2724 
2726  status;
2727 
2728  register const char
2729  *p;
2730 
2731  ssize_t
2732  count;
2733 
2734  /*
2735  Look for 'image.format' in filename.
2736  */
2737  assert(image_info != (ImageInfo *) NULL);
2738  assert(image_info->signature == MagickCoreSignature);
2739  if (image_info->debug != MagickFalse)
2741  image_info->filename);
2742  *component='\0';
2743  GetPathComponent(image_info->filename,SubimagePath,component);
2744  if (*component != '\0')
2745  {
2746  /*
2747  Look for scene specification (e.g. img0001.pcd[4]).
2748  */
2749  if (IsSceneGeometry(component,MagickFalse) == MagickFalse)
2750  {
2751  if (IsGeometry(component) != MagickFalse)
2752  (void) CloneString(&image_info->extract,component);
2753  }
2754  else
2755  {
2756  size_t
2757  first,
2758  last;
2759 
2760  (void) CloneString(&image_info->scenes,component);
2761  image_info->scene=StringToUnsignedLong(image_info->scenes);
2762  image_info->number_scenes=image_info->scene;
2763  p=image_info->scenes;
2764  for (q=(char *) image_info->scenes; *q != '\0'; p++)
2765  {
2766  while ((isspace((int) ((unsigned char) *p)) != 0) || (*p == ','))
2767  p++;
2768  first=(size_t) strtol(p,&q,10);
2769  last=first;
2770  while (isspace((int) ((unsigned char) *q)) != 0)
2771  q++;
2772  if (*q == '-')
2773  last=(size_t) strtol(q+1,&q,10);
2774  if (first > last)
2775  Swap(first,last);
2776  if (first < image_info->scene)
2777  image_info->scene=first;
2778  if (last > image_info->number_scenes)
2779  image_info->number_scenes=last;
2780  p=q;
2781  }
2782  image_info->number_scenes-=image_info->scene-1;
2783  }
2784  }
2785  *component='\0';
2786  if (*image_info->magick == '\0')
2787  GetPathComponent(image_info->filename,ExtensionPath,component);
2788 #if defined(MAGICKCORE_ZLIB_DELEGATE)
2789  if (*component != '\0')
2790  if ((LocaleCompare(component,"gz") == 0) ||
2791  (LocaleCompare(component,"Z") == 0) ||
2792  (LocaleCompare(component,"svgz") == 0) ||
2793  (LocaleCompare(component,"wmz") == 0))
2794  {
2795  char
2796  path[MagickPathExtent];
2797 
2798  (void) CopyMagickString(path,image_info->filename,MagickPathExtent);
2799  path[strlen(path)-strlen(component)-1]='\0';
2800  GetPathComponent(path,ExtensionPath,component);
2801  }
2802 #endif
2803 #if defined(MAGICKCORE_BZLIB_DELEGATE)
2804  if (*component != '\0')
2805  if (LocaleCompare(component,"bz2") == 0)
2806  {
2807  char
2808  path[MagickPathExtent];
2809 
2810  (void) CopyMagickString(path,image_info->filename,MagickPathExtent);
2811  path[strlen(path)-strlen(component)-1]='\0';
2812  GetPathComponent(path,ExtensionPath,component);
2813  }
2814 #endif
2815  image_info->affirm=MagickFalse;
2816  sans_exception=AcquireExceptionInfo();
2817  if ((*component != '\0') && (IsGlob(component) == MagickFalse))
2818  {
2820  format_type;
2821 
2822  register ssize_t
2823  i;
2824 
2825  static const char
2826  *format_type_formats[] =
2827  {
2828  "AUTOTRACE",
2829  "BROWSE",
2830  "DCRAW",
2831  "EDIT",
2832  "LAUNCH",
2833  "MPEG:DECODE",
2834  "MPEG:ENCODE",
2835  "PRINT",
2836  "PS:ALPHA",
2837  "PS:CMYK",
2838  "PS:COLOR",
2839  "PS:GRAY",
2840  "PS:MONO",
2841  "SCAN",
2842  "SHOW",
2843  "WIN",
2844  (char *) NULL
2845  };
2846 
2847  /*
2848  User specified image format.
2849  */
2850  (void) CopyMagickString(magic,component,MagickPathExtent);
2851  LocaleUpper(magic);
2852  /*
2853  Look for explicit image formats.
2854  */
2855  format_type=UndefinedFormatType;
2856  magick_info=GetMagickInfo(magic,sans_exception);
2857  if ((magick_info != (const MagickInfo *) NULL) &&
2858  (magick_info->format_type != UndefinedFormatType))
2859  format_type=magick_info->format_type;
2860  i=0;
2861  while ((format_type == UndefinedFormatType) &&
2862  (format_type_formats[i] != (char *) NULL))
2863  {
2864  if ((*magic == *format_type_formats[i]) &&
2865  (LocaleCompare(magic,format_type_formats[i]) == 0))
2866  format_type=ExplicitFormatType;
2867  i++;
2868  }
2869  if (format_type == UndefinedFormatType)
2870  (void) CopyMagickString(image_info->magick,magic,MagickPathExtent);
2871  else
2872  if (format_type == ExplicitFormatType)
2873  {
2874  image_info->affirm=MagickTrue;
2875  (void) CopyMagickString(image_info->magick,magic,MagickPathExtent);
2876  }
2877  if (LocaleCompare(magic,"RGB") == 0)
2878  image_info->affirm=MagickFalse; /* maybe SGI disguised as RGB */
2879  }
2880  /*
2881  Look for explicit 'format:image' in filename.
2882  */
2883  *magic='\0';
2884  GetPathComponent(image_info->filename,MagickPath,magic);
2885  if (*magic == '\0')
2886  {
2887  (void) CopyMagickString(magic,image_info->magick,MagickPathExtent);
2888  magick_info=GetMagickInfo(magic,sans_exception);
2889  if (frames == 0)
2890  GetPathComponent(image_info->filename,CanonicalPath,component);
2891  else
2892  GetPathComponent(image_info->filename,SubcanonicalPath,component);
2893  (void) CopyMagickString(image_info->filename,component,MagickPathExtent);
2894  }
2895  else
2896  {
2897  const DelegateInfo
2898  *delegate_info;
2899 
2900  /*
2901  User specified image format.
2902  */
2903  LocaleUpper(magic);
2904  magick_info=GetMagickInfo(magic,sans_exception);
2905  delegate_info=GetDelegateInfo(magic,"*",sans_exception);
2906  if (delegate_info == (const DelegateInfo *) NULL)
2907  delegate_info=GetDelegateInfo("*",magic,sans_exception);
2908  if (((magick_info != (const MagickInfo *) NULL) ||
2909  (delegate_info != (const DelegateInfo *) NULL)) &&
2910  (IsMagickConflict(magic) == MagickFalse))
2911  {
2912  image_info->affirm=MagickTrue;
2913  (void) CopyMagickString(image_info->magick,magic,MagickPathExtent);
2914  GetPathComponent(image_info->filename,CanonicalPath,component);
2915  (void) CopyMagickString(image_info->filename,component,
2917  }
2918  }
2919  sans_exception=DestroyExceptionInfo(sans_exception);
2920  if ((magick_info == (const MagickInfo *) NULL) ||
2921  (GetMagickEndianSupport(magick_info) == MagickFalse))
2922  image_info->endian=UndefinedEndian;
2923  if ((image_info->adjoin != MagickFalse) && (frames > 1))
2924  {
2925  /*
2926  Test for multiple image support (e.g. image%02d.png).
2927  */
2928  (void) InterpretImageFilename(image_info,(Image *) NULL,
2929  image_info->filename,(int) image_info->scene,component,exception);
2930  if ((LocaleCompare(component,image_info->filename) != 0) &&
2931  (strchr(component,'%') == (char *) NULL))
2932  image_info->adjoin=MagickFalse;
2933  }
2934  if ((image_info->adjoin != MagickFalse) && (frames > 0))
2935  {
2936  /*
2937  Some image formats do not support multiple frames per file.
2938  */
2939  magick_info=GetMagickInfo(magic,exception);
2940  if (magick_info != (const MagickInfo *) NULL)
2941  if (GetMagickAdjoin(magick_info) == MagickFalse)
2942  image_info->adjoin=MagickFalse;
2943  }
2944  if (image_info->affirm != MagickFalse)
2945  return(MagickTrue);
2946  if (frames == 0)
2947  {
2948  unsigned char
2949  *magick;
2950 
2951  size_t
2952  magick_size;
2953 
2954  /*
2955  Determine the image format from the first few bytes of the file.
2956  */
2957  magick_size=GetMagicPatternExtent(exception);
2958  if (magick_size == 0)
2959  return(MagickFalse);
2960  image=AcquireImage(image_info,exception);
2961  (void) CopyMagickString(image->filename,image_info->filename,
2963  status=OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
2964  if (status == MagickFalse)
2965  {
2966  image=DestroyImage(image);
2967  return(MagickFalse);
2968  }
2969  if ((IsBlobSeekable(image) == MagickFalse) ||
2970  (IsBlobExempt(image) != MagickFalse))
2971  {
2972  /*
2973  Copy image to seekable temporary file.
2974  */
2975  *component='\0';
2976  status=ImageToFile(image,component,exception);
2977  (void) CloseBlob(image);
2978  if (status == MagickFalse)
2979  {
2980  image=DestroyImage(image);
2981  return(MagickFalse);
2982  }
2983  SetImageInfoFile(image_info,(FILE *) NULL);
2984  (void) CopyMagickString(image->filename,component,MagickPathExtent);
2985  status=OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
2986  if (status == MagickFalse)
2987  {
2988  image=DestroyImage(image);
2989  return(MagickFalse);
2990  }
2991  (void) CopyMagickString(image_info->filename,component,
2993  image_info->temporary=MagickTrue;
2994  }
2995  magick=(unsigned char *) AcquireMagickMemory(magick_size);
2996  if (magick == (unsigned char *) NULL)
2997  {
2998  (void) CloseBlob(image);
2999  image=DestroyImage(image);
3000  return(MagickFalse);
3001  }
3002  (void) memset(magick,0,magick_size);
3003  count=ReadBlob(image,magick_size,magick);
3004  (void) SeekBlob(image,-((MagickOffsetType) count),SEEK_CUR);
3005  (void) CloseBlob(image);
3006  image=DestroyImage(image);
3007  /*
3008  Check magic cache.
3009  */
3010  sans_exception=AcquireExceptionInfo();
3011  magic_info=GetMagicInfo(magick,(size_t) count,sans_exception);
3012  magick=(unsigned char *) RelinquishMagickMemory(magick);
3013  if ((magic_info != (const MagicInfo *) NULL) &&
3014  (GetMagicName(magic_info) != (char *) NULL))
3015  {
3016  /*
3017  Try to use magick_info that was determined earlier by the extension
3018  */
3019  if ((magick_info != (const MagickInfo *) NULL) &&
3020  (GetMagickUseExtension(magick_info) != MagickFalse) &&
3021  (LocaleCompare(magick_info->module,GetMagicName(
3022  magic_info)) == 0))
3023  (void) CopyMagickString(image_info->magick,magick_info->name,
3025  else
3026  {
3027  (void) CopyMagickString(image_info->magick,GetMagicName(
3028  magic_info),MagickPathExtent);
3029  magick_info=GetMagickInfo(image_info->magick,sans_exception);
3030  }
3031  if ((magick_info == (const MagickInfo *) NULL) ||
3032  (GetMagickEndianSupport(magick_info) == MagickFalse))
3033  image_info->endian=UndefinedEndian;
3034  sans_exception=DestroyExceptionInfo(sans_exception);
3035  return(MagickTrue);
3036  }
3037  magick_info=GetMagickInfo(image_info->magick,sans_exception);
3038  if ((magick_info == (const MagickInfo *) NULL) ||
3039  (GetMagickEndianSupport(magick_info) == MagickFalse))
3040  image_info->endian=UndefinedEndian;
3041  sans_exception=DestroyExceptionInfo(sans_exception);
3042  }
3043  return(MagickTrue);
3044 }
3045 
3046 /*
3047 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3048 % %
3049 % %
3050 % %
3051 % S e t I m a g e I n f o B l o b %
3052 % %
3053 % %
3054 % %
3055 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3056 %
3057 % SetImageInfoBlob() sets the image info blob member.
3058 %
3059 % The format of the SetImageInfoBlob method is:
3060 %
3061 % void SetImageInfoBlob(ImageInfo *image_info,const void *blob,
3062 % const size_t length)
3063 %
3064 % A description of each parameter follows:
3065 %
3066 % o image_info: the image info.
3067 %
3068 % o blob: the blob.
3069 %
3070 % o length: the blob length.
3071 %
3072 */
3073 MagickExport void SetImageInfoBlob(ImageInfo *image_info,const void *blob,
3074  const size_t length)
3075 {
3076  assert(image_info != (ImageInfo *) NULL);
3077  assert(image_info->signature == MagickCoreSignature);
3078  if (image_info->debug != MagickFalse)
3080  image_info->filename);
3081  image_info->blob=(void *) blob;
3082  image_info->length=length;
3083 }
3084 
3085 /*
3086 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3087 % %
3088 % %
3089 % %
3090 % S e t I m a g e I n f o C u s t o m S t r e a m %
3091 % %
3092 % %
3093 % %
3094 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3095 %
3096 % SetImageInfoCustomStream() sets the image info custom stream handlers.
3097 %
3098 % The format of the SetImageInfoCustomStream method is:
3099 %
3100 % void SetImageInfoCustomStream(ImageInfo *image_info,
3101 % CustomStreamInfo *custom_stream)
3102 %
3103 % A description of each parameter follows:
3104 %
3105 % o image_info: the image info.
3106 %
3107 % o custom_stream: your custom stream methods.
3108 %
3109 */
3111  CustomStreamInfo *custom_stream)
3112 {
3113  assert(image_info != (ImageInfo *) NULL);
3114  assert(image_info->signature == MagickCoreSignature);
3115  if (image_info->debug != MagickFalse)
3117  image_info->filename);
3118  image_info->custom_stream=(CustomStreamInfo *) custom_stream;
3119 }
3120 
3121 /*
3122 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3123 % %
3124 % %
3125 % %
3126 % S e t I m a g e I n f o F i l e %
3127 % %
3128 % %
3129 % %
3130 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3131 %
3132 % SetImageInfoFile() sets the image info file member.
3133 %
3134 % The format of the SetImageInfoFile method is:
3135 %
3136 % void SetImageInfoFile(ImageInfo *image_info,FILE *file)
3137 %
3138 % A description of each parameter follows:
3139 %
3140 % o image_info: the image info.
3141 %
3142 % o file: the file.
3143 %
3144 */
3145 MagickExport void SetImageInfoFile(ImageInfo *image_info,FILE *file)
3146 {
3147  assert(image_info != (ImageInfo *) NULL);
3148  assert(image_info->signature == MagickCoreSignature);
3149  if (image_info->debug != MagickFalse)
3151  image_info->filename);
3152  image_info->file=file;
3153 }
3154 
3155 /*
3156 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3157 % %
3158 % %
3159 % %
3160 % S e t I m a g e M a s k %
3161 % %
3162 % %
3163 % %
3164 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3165 %
3166 % SetImageMask() associates a mask with the image. The mask must be the same
3167 % dimensions as the image.
3168 %
3169 % The format of the SetImageMask method is:
3170 %
3171 % MagickBooleanType SetImageMask(Image *image,const PixelMask type,
3172 % const Image *mask,ExceptionInfo *exception)
3173 %
3174 % A description of each parameter follows:
3175 %
3176 % o image: the image.
3177 %
3178 % o type: the mask type, ReadPixelMask or WritePixelMask.
3179 %
3180 % o mask: the image mask.
3181 %
3182 % o exception: return any errors or warnings in this structure.
3183 %
3184 */
3186  const Image *mask,ExceptionInfo *exception)
3187 {
3188  CacheView
3189  *mask_view,
3190  *image_view;
3191 
3193  status;
3194 
3195  ssize_t
3196  y;
3197 
3198  /*
3199  Set image mask.
3200  */
3201  assert(image != (Image *) NULL);
3202  if (image->debug != MagickFalse)
3203  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3204  assert(image->signature == MagickCoreSignature);
3205  if (mask == (const Image *) NULL)
3206  {
3207  switch (type)
3208  {
3209  case ReadPixelMask:
3210  {
3211  image->channels=(ChannelType) (image->channels & ~ReadMaskChannel);
3212  break;
3213  }
3214  case WritePixelMask:
3215  {
3216  image->channels=(ChannelType) (image->channels & ~WriteMaskChannel);
3217  }
3218  default:
3219  {
3220  image->channels=(ChannelType) (image->channels & ~CompositeMaskChannel);
3221  break;
3222  }
3223  }
3224  return(SyncImagePixelCache(image,exception));
3225  }
3226  switch (type)
3227  {
3228  case ReadPixelMask:
3229  {
3230  image->channels=(ChannelType) (image->channels | ReadMaskChannel);
3231  break;
3232  }
3233  case WritePixelMask:
3234  {
3235  image->channels=(ChannelType) (image->channels | WriteMaskChannel);
3236  break;
3237  }
3238  default:
3239  {
3240  image->channels=(ChannelType) (image->channels | CompositeMaskChannel);
3241  break;
3242  }
3243  }
3244  if (SyncImagePixelCache(image,exception) == MagickFalse)
3245  return(MagickFalse);
3246  status=MagickTrue;
3248  mask_view=AcquireVirtualCacheView(mask,exception);
3249  image_view=AcquireAuthenticCacheView(image,exception);
3250 #if defined(MAGICKCORE_OPENMP_SUPPORT)
3251  #pragma omp parallel for schedule(static) shared(status) \
3252  magick_number_threads(mask,image,image->rows,1)
3253 #endif
3254  for (y=0; y < (ssize_t) image->rows; y++)
3255  {
3256  register const Quantum
3257  *magick_restrict p;
3258 
3259  register Quantum
3260  *magick_restrict q;
3261 
3262  register ssize_t
3263  x;
3264 
3265  if (status == MagickFalse)
3266  continue;
3267  p=GetCacheViewVirtualPixels(mask_view,0,y,mask->columns,1,exception);
3268  q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
3269  if ((p == (const Quantum *) NULL) || (q == (Quantum *) NULL))
3270  {
3271  status=MagickFalse;
3272  continue;
3273  }
3274  for (x=0; x < (ssize_t) image->columns; x++)
3275  {
3277  intensity;
3278 
3279  intensity=0.0;
3280  if ((x < (ssize_t) mask->columns) && (y < (ssize_t) mask->rows))
3281  intensity=GetPixelIntensity(mask,p);
3282  switch (type)
3283  {
3284  case ReadPixelMask:
3285  {
3286  SetPixelReadMask(image,ClampToQuantum(intensity),q);
3287  break;
3288  }
3289  case WritePixelMask:
3290  {
3291  SetPixelWriteMask(image,ClampToQuantum(intensity),q);
3292  break;
3293  }
3294  default:
3295  {
3296  SetPixelCompositeMask(image,ClampToQuantum(intensity),q);
3297  break;
3298  }
3299  }
3300  p+=GetPixelChannels(mask);
3301  q+=GetPixelChannels(image);
3302  }
3303  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
3304  status=MagickFalse;
3305  }
3307  mask_view=DestroyCacheView(mask_view);
3308  image_view=DestroyCacheView(image_view);
3309  return(status);
3310 }
3311 
3312 /*
3313 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3314 % %
3315 % %
3316 % %
3317 % S e t I m a g e R e g i o n M a s k %
3318 % %
3319 % %
3320 % %
3321 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3322 %
3323 % SetImageRegionMask() associates a mask with the image as defined by the
3324 % specified region.
3325 %
3326 % The format of the SetImageRegionMask method is:
3327 %
3328 % MagickBooleanType SetImageRegionMask(Image *image,const PixelMask type,
3329 % const RectangleInfo *region,ExceptionInfo *exception)
3330 %
3331 % A description of each parameter follows:
3332 %
3333 % o image: the image.
3334 %
3335 % o type: the mask type, ReadPixelMask or WritePixelMask.
3336 %
3337 % o geometry: the mask region.
3338 %
3339 % o exception: return any errors or warnings in this structure.
3340 %
3341 */
3343  const PixelMask type,const RectangleInfo *region,ExceptionInfo *exception)
3344 {
3345  CacheView
3346  *image_view;
3347 
3349  status;
3350 
3351  ssize_t
3352  y;
3353 
3354  /*
3355  Set image mask as defined by the region.
3356  */
3357  assert(image != (Image *) NULL);
3358  if (image->debug != MagickFalse)
3359  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3360  assert(image->signature == MagickCoreSignature);
3361  if (region == (const RectangleInfo *) NULL)
3362  {
3363  switch (type)
3364  {
3365  case ReadPixelMask:
3366  {
3367  image->channels=(ChannelType) (image->channels & ~ReadMaskChannel);
3368  break;
3369  }
3370  case WritePixelMask:
3371  {
3372  image->channels=(ChannelType) (image->channels & ~WriteMaskChannel);
3373  break;
3374  }
3375  default:
3376  {
3377  image->channels=(ChannelType) (image->channels & ~CompositeMaskChannel);
3378  break;
3379  }
3380  }
3381  return(SyncImagePixelCache(image,exception));
3382  }
3383  switch (type)
3384  {
3385  case ReadPixelMask:
3386  {
3387  image->channels=(ChannelType) (image->channels | ReadMaskChannel);
3388  break;
3389  }
3390  case WritePixelMask:
3391  {
3392  image->channels=(ChannelType) (image->channels | WriteMaskChannel);
3393  break;
3394  }
3395  default:
3396  {
3397  image->channels=(ChannelType) (image->channels | CompositeMaskChannel);
3398  break;
3399  }
3400  }
3401  if (SyncImagePixelCache(image,exception) == MagickFalse)
3402  return(MagickFalse);
3403  status=MagickTrue;
3405  image_view=AcquireAuthenticCacheView(image,exception);
3406 #if defined(MAGICKCORE_OPENMP_SUPPORT)
3407  #pragma omp parallel for schedule(static) shared(status) \
3408  magick_number_threads(image,image,image->rows,1)
3409 #endif
3410  for (y=0; y < (ssize_t) image->rows; y++)
3411  {
3412  register Quantum
3413  *magick_restrict q;
3414 
3415  register ssize_t
3416  x;
3417 
3418  if (status == MagickFalse)
3419  continue;
3420  q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
3421  if (q == (Quantum *) NULL)
3422  {
3423  status=MagickFalse;
3424  continue;
3425  }
3426  for (x=0; x < (ssize_t) image->columns; x++)
3427  {
3428  Quantum
3429  pixel;
3430 
3431  pixel=QuantumRange;
3432  if (((x >= region->x) && (x < (region->x+(ssize_t) region->width))) &&
3433  ((y >= region->y) && (y < (region->y+(ssize_t) region->height))))
3434  pixel=(Quantum) 0;
3435  switch (type)
3436  {
3437  case ReadPixelMask:
3438  {
3439  SetPixelReadMask(image,pixel,q);
3440  break;
3441  }
3442  case WritePixelMask:
3443  {
3444  SetPixelWriteMask(image,pixel,q);
3445  break;
3446  }
3447  default:
3448  {
3449  SetPixelCompositeMask(image,pixel,q);
3450  break;
3451  }
3452  }
3453  q+=GetPixelChannels(image);
3454  }
3455  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
3456  status=MagickFalse;
3457  }
3459  image_view=DestroyCacheView(image_view);
3460  return(status);
3461 }
3462 
3463 /*
3464 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3465 % %
3466 % %
3467 % %
3468 % S e t I m a g e V i r t u a l P i x e l M e t h o d %
3469 % %
3470 % %
3471 % %
3472 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3473 %
3474 % SetImageVirtualPixelMethod() sets the "virtual pixels" method for the
3475 % image and returns the previous setting. A virtual pixel is any pixel access
3476 % that is outside the boundaries of the image cache.
3477 %
3478 % The format of the SetImageVirtualPixelMethod() method is:
3479 %
3480 % VirtualPixelMethod SetImageVirtualPixelMethod(Image *image,
3481 % const VirtualPixelMethod virtual_pixel_method,ExceptionInfo *exception)
3482 %
3483 % A description of each parameter follows:
3484 %
3485 % o image: the image.
3486 %
3487 % o virtual_pixel_method: choose the type of virtual pixel.
3488 %
3489 % o exception: return any errors or warnings in this structure.
3490 %
3491 */
3493  const VirtualPixelMethod virtual_pixel_method,ExceptionInfo *exception)
3494 {
3495  assert(image != (const Image *) NULL);
3496  assert(image->signature == MagickCoreSignature);
3497  if (image->debug != MagickFalse)
3498  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
3499  return(SetPixelCacheVirtualMethod(image,virtual_pixel_method,exception));
3500 }
3501 
3502 /*
3503 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3504 % %
3505 % %
3506 % %
3507 % S m u s h I m a g e s %
3508 % %
3509 % %
3510 % %
3511 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3512 %
3513 % SmushImages() takes all images from the current image pointer to the end
3514 % of the image list and smushes them to each other top-to-bottom if the
3515 % stack parameter is true, otherwise left-to-right.
3516 %
3517 % The current gravity setting now effects how the image is justified in the
3518 % final image.
3519 %
3520 % The format of the SmushImages method is:
3521 %
3522 % Image *SmushImages(const Image *images,const MagickBooleanType stack,
3523 % ExceptionInfo *exception)
3524 %
3525 % A description of each parameter follows:
3526 %
3527 % o images: the image sequence.
3528 %
3529 % o stack: A value other than 0 stacks the images top-to-bottom.
3530 %
3531 % o offset: minimum distance in pixels between images.
3532 %
3533 % o exception: return any errors or warnings in this structure.
3534 %
3535 */
3536 
3537 static ssize_t SmushXGap(const Image *smush_image,const Image *images,
3538  const ssize_t offset,ExceptionInfo *exception)
3539 {
3540  CacheView
3541  *left_view,
3542  *right_view;
3543 
3544  const Image
3545  *left_image,
3546  *right_image;
3547 
3549  left_geometry,
3550  right_geometry;
3551 
3552  register const Quantum
3553  *p;
3554 
3555  register ssize_t
3556  i,
3557  y;
3558 
3559  size_t
3560  gap;
3561 
3562  ssize_t
3563  x;
3564 
3565  if (images->previous == (Image *) NULL)
3566  return(0);
3567  right_image=images;
3568  SetGeometry(smush_image,&right_geometry);
3569  GravityAdjustGeometry(right_image->columns,right_image->rows,
3570  right_image->gravity,&right_geometry);
3571  left_image=images->previous;
3572  SetGeometry(smush_image,&left_geometry);
3573  GravityAdjustGeometry(left_image->columns,left_image->rows,
3574  left_image->gravity,&left_geometry);
3575  gap=right_image->columns;
3576  left_view=AcquireVirtualCacheView(left_image,exception);
3577  right_view=AcquireVirtualCacheView(right_image,exception);
3578  for (y=0; y < (ssize_t) smush_image->rows; y++)
3579  {
3580  for (x=(ssize_t) left_image->columns-1; x > 0; x--)
3581  {
3582  p=GetCacheViewVirtualPixels(left_view,x,left_geometry.y+y,1,1,exception);
3583  if ((p == (const Quantum *) NULL) ||
3584  (GetPixelAlpha(left_image,p) != TransparentAlpha) ||
3585  ((left_image->columns-x-1) >= gap))
3586  break;
3587  }
3588  i=(ssize_t) left_image->columns-x-1;
3589  for (x=0; x < (ssize_t) right_image->columns; x++)
3590  {
3591  p=GetCacheViewVirtualPixels(right_view,x,right_geometry.y+y,1,1,
3592  exception);
3593  if ((p == (const Quantum *) NULL) ||
3594  (GetPixelAlpha(right_image,p) != TransparentAlpha) ||
3595  ((x+i) >= (ssize_t) gap))
3596  break;
3597  }
3598  if ((x+i) < (ssize_t) gap)
3599  gap=(size_t) (x+i);
3600  }
3601  right_view=DestroyCacheView(right_view);
3602  left_view=DestroyCacheView(left_view);
3603  if (y < (ssize_t) smush_image->rows)
3604  return(offset);
3605  return((ssize_t) gap-offset);
3606 }
3607 
3608 static ssize_t SmushYGap(const Image *smush_image,const Image *images,
3609  const ssize_t offset,ExceptionInfo *exception)
3610 {
3611  CacheView
3612  *bottom_view,
3613  *top_view;
3614 
3615  const Image
3616  *bottom_image,
3617  *top_image;
3618 
3620  bottom_geometry,
3621  top_geometry;
3622 
3623  register const Quantum
3624  *p;
3625 
3626  register ssize_t
3627  i,
3628  x;
3629 
3630  size_t
3631  gap;
3632 
3633  ssize_t
3634  y;
3635 
3636  if (images->previous == (Image *) NULL)
3637  return(0);
3638  bottom_image=images;
3639  SetGeometry(smush_image,&bottom_geometry);
3640  GravityAdjustGeometry(bottom_image->columns,bottom_image->rows,
3641  bottom_image->gravity,&bottom_geometry);
3642  top_image=images->previous;
3643  SetGeometry(smush_image,&top_geometry);
3644  GravityAdjustGeometry(top_image->columns,top_image->rows,top_image->gravity,
3645  &top_geometry);
3646  gap=bottom_image->rows;
3647  top_view=AcquireVirtualCacheView(top_image,exception);
3648  bottom_view=AcquireVirtualCacheView(bottom_image,exception);
3649  for (x=0; x < (ssize_t) smush_image->columns; x++)
3650  {
3651  for (y=(ssize_t) top_image->rows-1; y > 0; y--)
3652  {
3653  p=GetCacheViewVirtualPixels(top_view,top_geometry.x+x,y,1,1,exception);
3654  if ((p == (const Quantum *) NULL) ||
3655  (GetPixelAlpha(top_image,p) != TransparentAlpha) ||
3656  ((top_image->rows-y-1) >= gap))
3657  break;
3658  }
3659  i=(ssize_t) top_image->rows-y-1;
3660  for (y=0; y < (ssize_t) bottom_image->rows; y++)
3661  {
3662  p=GetCacheViewVirtualPixels(bottom_view,bottom_geometry.x+x,y,1,1,
3663  exception);
3664  if ((p == (const Quantum *) NULL) ||
3665  (GetPixelAlpha(bottom_image,p) != TransparentAlpha) ||
3666  ((y+i) >= (ssize_t) gap))
3667  break;
3668  }
3669  if ((y+i) < (ssize_t) gap)
3670  gap=(size_t) (y+i);
3671  }
3672  bottom_view=DestroyCacheView(bottom_view);
3673  top_view=DestroyCacheView(top_view);
3674  if (x < (ssize_t) smush_image->columns)
3675  return(offset);
3676  return((ssize_t) gap-offset);
3677 }
3678 
3680  const MagickBooleanType stack,const ssize_t offset,ExceptionInfo *exception)
3681 {
3682 #define SmushImageTag "Smush/Image"
3683 
3684  const Image
3685  *image;
3686 
3687  Image
3688  *smush_image;
3689 
3691  proceed,
3692  status;
3693 
3695  n;
3696 
3697  PixelTrait
3698  alpha_trait;
3699 
3701  geometry;
3702 
3703  register const Image
3704  *next;
3705 
3706  size_t
3707  height,
3708  number_images,
3709  width;
3710 
3711  ssize_t
3712  x_offset,
3713  y_offset;
3714 
3715  /*
3716  Compute maximum area of smushed area.
3717  */
3718  assert(images != (Image *) NULL);
3719  assert(images->signature == MagickCoreSignature);
3720  if (images->debug != MagickFalse)
3721  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",images->filename);
3722  assert(exception != (ExceptionInfo *) NULL);
3723  assert(exception->signature == MagickCoreSignature);
3724  image=images;
3725  alpha_trait=image->alpha_trait;
3726  number_images=1;
3727  width=image->columns;
3728  height=image->rows;
3729  next=GetNextImageInList(image);
3730  for ( ; next != (Image *) NULL; next=GetNextImageInList(next))
3731  {
3732  if (next->alpha_trait != UndefinedPixelTrait)
3733  alpha_trait=BlendPixelTrait;
3734  number_images++;
3735  if (stack != MagickFalse)
3736  {
3737  if (next->columns > width)
3738  width=next->columns;
3739  height+=next->rows;
3740  if (next->previous != (Image *) NULL)
3741  height+=offset;
3742  continue;
3743  }
3744  width+=next->columns;
3745  if (next->previous != (Image *) NULL)
3746  width+=offset;
3747  if (next->rows > height)
3748  height=next->rows;
3749  }
3750  /*
3751  Smush images.
3752  */
3753  smush_image=CloneImage(image,width,height,MagickTrue,exception);
3754  if (smush_image == (Image *) NULL)
3755  return((Image *) NULL);
3756  if (SetImageStorageClass(smush_image,DirectClass,exception) == MagickFalse)
3757  {
3758  smush_image=DestroyImage(smush_image);
3759  return((Image *) NULL);
3760  }
3761  smush_image->alpha_trait=alpha_trait;
3762  (void) SetImageBackgroundColor(smush_image,exception);
3763  status=MagickTrue;
3764  x_offset=0;
3765  y_offset=0;
3766  for (n=0; n < (MagickOffsetType) number_images; n++)
3767  {
3768  SetGeometry(smush_image,&geometry);
3769  GravityAdjustGeometry(image->columns,image->rows,image->gravity,&geometry);
3770  if (stack != MagickFalse)
3771  {
3772  x_offset-=geometry.x;
3773  y_offset-=SmushYGap(smush_image,image,offset,exception);
3774  }
3775  else
3776  {
3777  x_offset-=SmushXGap(smush_image,image,offset,exception);
3778  y_offset-=geometry.y;
3779  }
3780  status=CompositeImage(smush_image,image,OverCompositeOp,MagickTrue,x_offset,
3781  y_offset,exception);
3782  proceed=SetImageProgress(image,SmushImageTag,n,number_images);
3783  if (proceed == MagickFalse)
3784  break;
3785  if (stack == MagickFalse)
3786  {
3787  x_offset+=(ssize_t) image->columns;
3788  y_offset=0;
3789  }
3790  else
3791  {
3792  x_offset=0;
3793  y_offset+=(ssize_t) image->rows;
3794  }
3795  image=GetNextImageInList(image);
3796  }
3797  if (stack == MagickFalse)
3798  smush_image->columns=(size_t) x_offset;
3799  else
3800  smush_image->rows=(size_t) y_offset;
3801  if (status == MagickFalse)
3802  smush_image=DestroyImage(smush_image);
3803  return(smush_image);
3804 }
3805 
3806 /*
3807 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3808 % %
3809 % %
3810 % %
3811 % S t r i p I m a g e %
3812 % %
3813 % %
3814 % %
3815 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3816 %
3817 % StripImage() strips an image of all profiles and comments.
3818 %
3819 % The format of the StripImage method is:
3820 %
3821 % MagickBooleanType StripImage(Image *image,ExceptionInfo *exception)
3822 %
3823 % A description of each parameter follows:
3824 %
3825 % o image: the image.
3826 %
3827 % o exception: return any errors or warnings in this structure.
3828 %
3829 */
3831 {
3833  status;
3834 
3835  assert(image != (Image *) NULL);
3836  if (image->debug != MagickFalse)
3837  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3838  (void) exception;
3839  DestroyImageProfiles(image);
3840  (void) DeleteImageProperty(image,"comment");
3841  (void) DeleteImageProperty(image,"date:create");
3842  (void) DeleteImageProperty(image,"date:modify");
3843  status=SetImageArtifact(image,"png:exclude-chunk",
3844  "bKGD,caNv,cHRM,eXIf,gAMA,iCCP,iTXt,pHYs,sRGB,tEXt,zCCP,zTXt,date");
3845  return(status);
3846 }
3847 
3848 /*
3849 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3850 % %
3851 % %
3852 % %
3853 + S y n c I m a g e %
3854 % %
3855 % %
3856 % %
3857 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3858 %
3859 % SyncImage() initializes the red, green, and blue intensities of each pixel
3860 % as defined by the colormap index.
3861 %
3862 % The format of the SyncImage method is:
3863 %
3864 % MagickBooleanType SyncImage(Image *image,ExceptionInfo *exception)
3865 %
3866 % A description of each parameter follows:
3867 %
3868 % o image: the image.
3869 %
3870 % o exception: return any errors or warnings in this structure.
3871 %
3872 */
3873 
3874 static inline Quantum PushColormapIndex(Image *image,const Quantum index,
3875  MagickBooleanType *range_exception)
3876 {
3877  if ((size_t) index < image->colors)
3878  return(index);
3879  *range_exception=MagickTrue;
3880  return((Quantum) 0);
3881 }
3882 
3884 {
3885  CacheView
3886  *image_view;
3887 
3889  range_exception,
3890  status,
3891  taint;
3892 
3893  ssize_t
3894  y;
3895 
3896  assert(image != (Image *) NULL);
3897  if (image->debug != MagickFalse)
3898  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3899  assert(image->signature == MagickCoreSignature);
3900  if (image->ping != MagickFalse)
3901  return(MagickTrue);
3902  if (image->storage_class != PseudoClass)
3903  return(MagickFalse);
3904  assert(image->colormap != (PixelInfo *) NULL);
3905  range_exception=MagickFalse;
3906  status=MagickTrue;
3907  taint=image->taint;
3908  image_view=AcquireAuthenticCacheView(image,exception);
3909 #if defined(MAGICKCORE_OPENMP_SUPPORT)
3910  #pragma omp parallel for schedule(static) shared(range_exception,status) \
3911  magick_number_threads(image,image,image->rows,1)
3912 #endif
3913  for (y=0; y < (ssize_t) image->rows; y++)
3914  {
3915  Quantum
3916  index;
3917 
3918  register Quantum
3919  *magick_restrict q;
3920 
3921  register ssize_t
3922  x;
3923 
3924  if (status == MagickFalse)
3925  continue;
3926  q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
3927  if (q == (Quantum *) NULL)
3928  {
3929  status=MagickFalse;
3930  continue;
3931  }
3932  for (x=0; x < (ssize_t) image->columns; x++)
3933  {
3934  index=PushColormapIndex(image,GetPixelIndex(image,q),&range_exception);
3935  SetPixelViaPixelInfo(image,image->colormap+(ssize_t) index,q);
3936  q+=GetPixelChannels(image);
3937  }
3938  if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
3939  status=MagickFalse;
3940  }
3941  image_view=DestroyCacheView(image_view);
3942  image->taint=taint;
3943  if ((image->ping == MagickFalse) && (range_exception != MagickFalse))
3944  (void) ThrowMagickException(exception,GetMagickModule(),
3945  CorruptImageWarning,"InvalidColormapIndex","`%s'",image->filename);
3946  return(status);
3947 }
3948 
3949 /*
3950 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3951 % %
3952 % %
3953 % %
3954 % S y n c I m a g e S e t t i n g s %
3955 % %
3956 % %
3957 % %
3958 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3959 %
3960 % SyncImageSettings() syncs any image_info global options into per-image
3961 % attributes.
3962 %
3963 % Note: in IMv6 free form 'options' were always mapped into 'artifacts', so
3964 % that operations and coders can find such settings. In IMv7 if a desired
3965 % per-image artifact is not set, then it will directly look for a global
3966 % option as a fallback, as such this copy is no longer needed, only the
3967 % link set up.
3968 %
3969 % The format of the SyncImageSettings method is:
3970 %
3971 % MagickBooleanType SyncImageSettings(const ImageInfo *image_info,
3972 % Image *image,ExceptionInfo *exception)
3973 % MagickBooleanType SyncImagesSettings(const ImageInfo *image_info,
3974 % Image *image,ExceptionInfo *exception)
3975 %
3976 % A description of each parameter follows:
3977 %
3978 % o image_info: the image info.
3979 %
3980 % o image: the image.
3981 %
3982 % o exception: return any errors or warnings in this structure.
3983 %
3984 */
3985 
3987  Image *images,ExceptionInfo *exception)
3988 {
3989  Image
3990  *image;
3991 
3992  assert(image_info != (const ImageInfo *) NULL);
3993  assert(image_info->signature == MagickCoreSignature);
3994  assert(images != (Image *) NULL);
3995  assert(images->signature == MagickCoreSignature);
3996  if (images->debug != MagickFalse)
3997  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",images->filename);
3998  image=images;
3999  for ( ; image != (Image *) NULL; image=GetNextImageInList(image))
4000  (void) SyncImageSettings(image_info,image,exception);
4001  (void) DeleteImageOption(image_info,"page");
4002  return(MagickTrue);
4003 }
4004 
4006  Image *image,ExceptionInfo *exception)
4007 {
4008  const char
4009  *option;
4010 
4011  GeometryInfo
4012  geometry_info;
4013 
4015  flags;
4016 
4018  units;
4019 
4020  /*
4021  Sync image options.
4022  */
4023  assert(image_info != (const ImageInfo *) NULL);
4024  assert(image_info->signature == MagickCoreSignature);
4025  assert(image != (Image *) NULL);
4026  assert(image->signature == MagickCoreSignature);
4027  if (image->debug != MagickFalse)
4028  (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
4029  option=GetImageOption(image_info,"background");
4030  if (option != (const char *) NULL)
4031  (void) QueryColorCompliance(option,AllCompliance,&image->background_color,
4032  exception);
4033  option=GetImageOption(image_info,"black-point-compensation");
4034  if (option != (const char *) NULL)
4037  option=GetImageOption(image_info,"blue-primary");
4038  if (option != (const char *) NULL)
4039  {
4040  flags=ParseGeometry(option,&geometry_info);
4041  image->chromaticity.blue_primary.x=geometry_info.rho;
4042  image->chromaticity.blue_primary.y=geometry_info.sigma;
4043  if ((flags & SigmaValue) == 0)
4045  }
4046  option=GetImageOption(image_info,"bordercolor");
4047  if (option != (const char *) NULL)
4048  (void) QueryColorCompliance(option,AllCompliance,&image->border_color,
4049  exception);
4050  /* FUTURE: do not sync compose to per-image compose setting here */
4051  option=GetImageOption(image_info,"compose");
4052  if (option != (const char *) NULL)
4054  MagickFalse,option);
4055  /* -- */
4056  option=GetImageOption(image_info,"compress");
4057  if (option != (const char *) NULL)
4060  option=GetImageOption(image_info,"debug");
4061  if (option != (const char *) NULL)
4063  MagickFalse,option);
4064  option=GetImageOption(image_info,"density");
4065  if (option != (const char *) NULL)
4066  {
4067  flags=ParseGeometry(option,&geometry_info);
4068  image->resolution.x=geometry_info.rho;
4069  image->resolution.y=geometry_info.sigma;
4070  if ((flags & SigmaValue) == 0)
4071  image->resolution.y=image->resolution.x;
4072  }
4073  option=GetImageOption(image_info,"depth");
4074  if (option != (const char *) NULL)
4075  image->depth=StringToUnsignedLong(option);
4076  option=GetImageOption(image_info,"endian");
4077  if (option != (const char *) NULL)
4079  MagickFalse,option);
4080  option=GetImageOption(image_info,"filter");
4081  if (option != (const char *) NULL)
4083  MagickFalse,option);
4084  option=GetImageOption(image_info,"fuzz");
4085  if (option != (const char *) NULL)
4086  image->fuzz=StringToDoubleInterval(option,(double) QuantumRange+1.0);
4087  option=GetImageOption(image_info,"gravity");
4088  if (option != (const char *) NULL)
4090  MagickFalse,option);
4091  option=GetImageOption(image_info,"green-primary");
4092  if (option != (const char *) NULL)
4093  {
4094  flags=ParseGeometry(option,&geometry_info);
4095  image->chromaticity.green_primary.x=geometry_info.rho;
4096  image->chromaticity.green_primary.y=geometry_info.sigma;
4097  if ((flags & SigmaValue) == 0)
4099  }
4100  option=GetImageOption(image_info,"intent");
4101  if (option != (const char *) NULL)
4104  option=GetImageOption(image_info,"intensity");
4105  if (option != (const char *) NULL)
4108  option=GetImageOption(image_info,"interlace");
4109  if (option != (const char *) NULL)
4111  MagickFalse,option);
4112  option=GetImageOption(image_info,"interpolate");
4113  if (option != (const char *) NULL)
4116  option=GetImageOption(image_info,"loop");
4117  if (option != (const char *) NULL)
4118  image->iterations=StringToUnsignedLong(option);
4119  option=GetImageOption(image_info,"mattecolor");
4120  if (option != (const char *) NULL)
4121  (void) QueryColorCompliance(option,AllCompliance,&image->matte_color,
4122  exception);
4123  option=GetImageOption(image_info,"orient");
4124  if (option != (const char *) NULL)
4127  option=GetImageOption(image_info,"page");
4128  if (option != (const char *) NULL)
4129  {
4130  char
4131  *geometry;
4132 
4133  geometry=GetPageGeometry(option);
4134  flags=ParseAbsoluteGeometry(geometry,&image->page);
4135  geometry=DestroyString(geometry);
4136  }
4137  option=GetImageOption(image_info,"quality");
4138  if (option != (const char *) NULL)
4139  image->quality=StringToUnsignedLong(option);
4140  option=GetImageOption(image_info,"red-primary");
4141  if (option != (const char *) NULL)
4142  {
4143  flags=ParseGeometry(option,&geometry_info);
4144  image->chromaticity.red_primary.x=geometry_info.rho;
4145  image->chromaticity.red_primary.y=geometry_info.sigma;
4146  if ((flags & SigmaValue) == 0)
4148  }
4149  if (image_info->quality != UndefinedCompressionQuality)
4150  image->quality=image_info->quality;
4151  option=GetImageOption(image_info,"scene");
4152  if (option != (const char *) NULL)
4153  image->scene=StringToUnsignedLong(option);
4154  option=GetImageOption(image_info,"taint");
4155  if (option != (const char *) NULL)
4157  MagickFalse,option);
4158  option=GetImageOption(image_info,"tile-offset");
4159  if (option != (const char *) NULL)
4160  {
4161  char
4162  *geometry;
4163 
4164  geometry=GetPageGeometry(option);
4165  flags=ParseAbsoluteGeometry(geometry,&image->tile_offset);
4166  geometry=DestroyString(geometry);
4167  }
4168  option=GetImageOption(image_info,"transparent-color");
4169  if (option != (const char *) NULL)
4171  exception);
4172  option=GetImageOption(image_info,"type");
4173  if (option != (const char *) NULL)
4175  option);
4176  option=GetImageOption(image_info,"units");
4177  units=image_info->units;
4178  if (option != (const char *) NULL)
4180  MagickFalse,option);
4181  if (units != UndefinedResolution)
4182  {
4183  if (image->units != units)
4184  switch (image->units)
4185  {
4187  {
4188  if (units == PixelsPerCentimeterResolution)
4189  {
4190  image->resolution.x/=2.54;
4191  image->resolution.y/=2.54;
4192  }
4193  break;
4194  }
4196  {
4197  if (units == PixelsPerInchResolution)
4198  {
4199  image->resolution.x=(double) ((size_t) (100.0*2.54*
4200  image->resolution.x+0.5))/100.0;
4201  image->resolution.y=(double) ((size_t) (100.0*2.54*
4202  image->resolution.y+0.5))/100.0;
4203  }
4204  break;
4205  }
4206  default:
4207  break;
4208  }
4209  image->units=units;
4210  option=GetImageOption(image_info,"density");
4211  if (option != (const char *) NULL)
4212  {
4213  flags=ParseGeometry(option,&geometry_info);
4214  image->resolution.x=geometry_info.rho;
4215  image->resolution.y=geometry_info.sigma;
4216  if ((flags & SigmaValue) == 0)
4217  image->resolution.y=image->resolution.x;
4218  }
4219  }
4220  option=GetImageOption(image_info,"virtual-pixel");
4221  if (option != (const char *) NULL)
4224  exception);
4225  option=GetImageOption(image_info,"white-point");
4226  if (option != (const char *) NULL)
4227  {
4228  flags=ParseGeometry(option,&geometry_info);
4229  image->chromaticity.white_point.x=geometry_info.rho;
4230  image->chromaticity.white_point.y=geometry_info.sigma;
4231  if ((flags & SigmaValue) == 0)
4233  }
4234  /*
4235  Pointer to allow the lookup of pre-image artifact will fallback to a global
4236  option setting/define. This saves a lot of duplication of global options
4237  into per-image artifacts, while ensuring only specifically set per-image
4238  artifacts are preserved when parenthesis ends.
4239  */
4240  if (image->image_info != (ImageInfo *) NULL)
4241  image->image_info=DestroyImageInfo(image->image_info);
4242  image->image_info=CloneImageInfo(image_info);
4243  return(MagickTrue);
4244 }
MagickExport Image * GetImageMask(const Image *image, const PixelMask type, ExceptionInfo *exception)
Definition: image.c:1437
size_t rows
Definition: image.h:172
#define magick_restrict
Definition: MagickCore.h:41
MagickExport FILE * GetImageInfoFile(const ImageInfo *image_info)
Definition: image.c:1407
MagickPrivate Cache DestroyPixelCache(Cache)
MagickExport MagickBooleanType GetMagickUseExtension(const MagickInfo *magick_info)
Definition: magick.c:979
PixelInfo matte_color
Definition: image.h:357
MagickDoubleType MagickRealType
Definition: magick-type.h:120
MagickExport MagickBooleanType NegateImage(Image *image, const MagickBooleanType grayscale, ExceptionInfo *exception)
Definition: enhance.c:3897
PixelIntensityMethod intensity
Definition: image.h:222
MagickExport CacheView * DestroyCacheView(CacheView *cache_view)
Definition: cache-view.c:252
#define TransparentAlpha
Definition: image.h:26
EndianType endian
Definition: image.h:404
double fuzz
Definition: pixel.h:182
size_t signature
Definition: image.h:488
MagickExport const char BackgroundColor[]
Definition: image.c:111
struct _Image * list
Definition: image.h:348
PixelInfo * colormap
Definition: image.h:179
MagickExport ImageInfo * AcquireImageInfo(void)
Definition: image.c:345
InterlaceType interlace
Definition: image.h:225
MagickExport void DestroyImagePixels(Image *image)
Definition: cache.c:900
DisposeType dispose
Definition: image.h:237
Ascii85Info * ascii85
Definition: image.h:309
MagickExport const char PSDensityGeometry[]
Definition: image.c:120
char magick[MagickPathExtent]
Definition: image.h:480
MagickProgressMonitor progress_monitor
Definition: image.h:303
MagickExport PixelChannelMap * AcquirePixelChannelMap(void)
Definition: pixel.c:93
char * scenes
Definition: image.h:390
ImageType type
Definition: image.h:264
size_t iterations
Definition: image.h:248
MagickExport ExceptionType CatchImageException(Image *image)
Definition: image.c:643
MagickExport MagickBooleanType SyncImage(Image *image, ExceptionInfo *exception)
Definition: image.c:3883
ssize_t ticks_per_second
Definition: image.h:245
static Quantum GetPixelAlpha(const Image *magick_restrict image, const Quantum *magick_restrict pixel)
PixelTrait mask_trait
Definition: image.h:363
FilterType
Definition: resample.h:32
MagickExport Image * ReferenceImage(Image *image)
Definition: image.c:2136
FilterType filter
Definition: image.h:219
MagickExport MagickBooleanType DeleteImageOption(ImageInfo *image_info, const char *option)
Definition: option.c:2227
PixelTrait alpha_trait
Definition: pixel.h:179
MagickExport void UnlockSemaphoreInfo(SemaphoreInfo *semaphore_info)
Definition: semaphore.c:450
MagickExport void Ascii85Initialize(Image *image)
Definition: compress.c:264
double pointsize
Definition: image.h:420
ssize_t y
Definition: geometry.h:116
static unsigned long StringToUnsignedLong(const char *magick_restrict value)
const char TransparentColor[]
Definition: image.c:124
MagickExport ssize_t ParseCommandOption(const CommandOption option, const MagickBooleanType list, const char *options)
Definition: option.c:2967
OrientationType
Definition: image.h:76
MagickBooleanType ping
Definition: image.h:273
char * extract
Definition: image.h:390
MagickExport const char DefaultTileFrame[]
Definition: image.c:113
PixelInfo border_color
Definition: image.h:179
PixelInterpolateMethod
Definition: pixel.h:110
PixelInterpolateMethod interpolate
Definition: image.h:255
double x
Definition: image.h:99
size_t signature
Definition: exception.h:123
#define SmushImageTag
MagickExport const char DefaultTileGeometry[]
Definition: image.c:114
MagickExport Image * NewMagickImage(const ImageInfo *image_info, const size_t width, const size_t height, const PixelInfo *background, ExceptionInfo *exception)
Definition: image.c:2049
size_t number_scenes
Definition: image.h:396
char * sampling_factor
Definition: image.h:413
double rho
Definition: geometry.h:106
MagickExport MagickStatusType ParseAbsoluteGeometry(const char *geometry, RectangleInfo *region_info)
Definition: geometry.c:703
MagickExport const char * GetMagicName(const MagicInfo *magic_info)
Definition: magic.c:604
EndianType endian
Definition: image.h:228
MagickBooleanType taint
Definition: image.h:169
MagickExport size_t ConcatenateMagickString(char *destination, const char *source, const size_t length)
Definition: string.c:426
PixelIntensityMethod
Definition: pixel.h:96
MagickBooleanType debug
Definition: image.h:485
MagickExport SemaphoreInfo * AcquireSemaphoreInfo(void)
Definition: semaphore.c:192
MagickExport MagickBooleanType SyncImageSettings(const ImageInfo *image_info, Image *image, ExceptionInfo *exception)
Definition: image.c:4005
static void SetPixelGray(const Image *magick_restrict image, const Quantum gray, Quantum *magick_restrict pixel)
char * font
Definition: image.h:413
MagickExport MagickBooleanType SetImageArtifact(Image *image, const char *artifact, const char *value)
Definition: artifact.c:445
#define OpaqueAlpha
Definition: image.h:25
MagickExport const DelegateInfo * GetDelegateInfo(const char *decode, const char *encode, ExceptionInfo *exception)
Definition: delegate.c:1181
MagickPrivate MagickBooleanType SyncImagePixelCache(Image *, ExceptionInfo *)
Definition: cache.c:5490
InterlaceType
Definition: image.h:64
VirtualPixelMethod
Definition: cache-view.h:27
ColorspaceType colorspace
Definition: image.h:436
MagickExport const char * GetImageArtifact(const Image *image, const char *artifact)
Definition: artifact.c:273
MagickPrivate Cache ReferencePixelCache(Cache)
Definition: cache.c:4736
char * module
Definition: magick.h:64
double z
Definition: image.h:99
MagickBooleanType antialias
Definition: image.h:384
char * name
Definition: magick.h:64
MagickExport MagickBooleanType SetImageAlpha(Image *image, const Quantum alpha, ExceptionInfo *exception)
Definition: image.c:2339
PixelInfo transparent_color
Definition: image.h:424
static PixelTrait GetPixelChannelTraits(const Image *magick_restrict image, const PixelChannel channel)
MagickPrivate MagickBooleanType IsMagickConflict(const char *)
MagickExport ExceptionInfo * AcquireExceptionInfo(void)
Definition: exception.c:115
MagickExport const char LoadImageTag[]
Definition: image.c:117
MagickExport void DestroyImageProfiles(Image *image)
Definition: profile.c:254
MagickExport ssize_t FormatLocaleString(char *magick_restrict string, const size_t length, const char *magick_restrict format,...)
Definition: locale.c:499
static void SetPixelViaPixelInfo(const Image *magick_restrict image, const PixelInfo *magick_restrict pixel_info, Quantum *magick_restrict pixel)
static void * AcquireCriticalMemory(const size_t size)
static Quantum GetPixelReadMask(const Image *magick_restrict image, const Quantum *magick_restrict pixel)
MagickExport void SetImageInfoBlob(ImageInfo *image_info, const void *blob, const size_t length)
Definition: image.c:3073
ResolutionType units
Definition: image.h:198
size_t delay
Definition: image.h:240
MagickExport const char ForegroundColor[]
Definition: image.c:116
char magick[MagickPathExtent]
Definition: image.h:319
size_t magick_rows
Definition: image.h:324
#define MAGICKCORE_QUANTUM_DEPTH
Definition: magick-type.h:28
MagickExport MagickBooleanType ImageToFile(Image *image, char *filename, ExceptionInfo *exception)
Definition: blob.c:2258
MagickExport const Quantum * GetCacheViewVirtualPixels(const CacheView *cache_view, const ssize_t x, const ssize_t y, const size_t columns, const size_t rows, ExceptionInfo *exception)
Definition: cache-view.c:651
MagickBooleanType verbose
Definition: image.h:445
MagickRealType alpha
Definition: pixel.h:191
MagickExport const char * GetImageOption(const ImageInfo *image_info, const char *option)
Definition: option.c:2302
MagickExport char * GetPageGeometry(const char *page_geometry)
Definition: geometry.c:362
MagickPrivate VirtualPixelMethod GetPixelCacheVirtualMethod(const Image *)
Image * image
Definition: image-view.c:67
MagickFormatType format_type
Definition: magick.h:84
char * montage
Definition: image.h:201
CompressionType compression
Definition: image.h:160
double sigma
Definition: geometry.h:106
InterlaceType interlace
Definition: image.h:401
ClassType storage_class
Definition: image.h:154
MagickExport MagickBooleanType CompositeImage(Image *image, const Image *composite, const CompositeOperator compose, const MagickBooleanType clip_to_self, const ssize_t x_offset, const ssize_t y_offset, ExceptionInfo *exception)
Definition: composite.c:528
size_t width
Definition: geometry.h:130
MagickExport BlobInfo * CloneBlobInfo(const BlobInfo *)
RectangleInfo tile_offset
Definition: image.h:261
MagickPrivate Cache ClonePixelCache(const Cache)
MagickExport void * AcquirePixelCachePixels(const Image *image, size_t *length, ExceptionInfo *exception)
Definition: cache.c:314
#define ThrowBinaryException(severity, tag, context)
Definition: log.h:52
ssize_t MagickOffsetType
Definition: magick-type.h:129
MagickExport void GetPixelInfo(const Image *image, PixelInfo *pixel)
Definition: pixel.c:2170
MagickExport void DestroyImageOptions(ImageInfo *image_info)
Definition: option.c:2263
EndianType
Definition: quantum.h:28
char * size
Definition: image.h:390
MagickExport void SetImageInfoFile(ImageInfo *image_info, FILE *file)
Definition: image.c:3145
Definition: image.h:151
void * cache
Definition: image.h:464
MagickExport VirtualPixelMethod GetImageVirtualPixelMethod(const Image *image)
Definition: image.c:1605
ExceptionType
Definition: exception.h:27
ImageType type
Definition: image.h:442
StreamHandler stream
Definition: image.h:468
size_t number_meta_channels
Definition: image.h:283
double x
Definition: geometry.h:123
#define MagickCoreSignature
MagickExport void LockSemaphoreInfo(SemaphoreInfo *semaphore_info)
Definition: semaphore.c:293
MagickExport Quantum * GetCacheViewAuthenticPixels(CacheView *cache_view, const ssize_t x, const ssize_t y, const size_t columns, const size_t rows, ExceptionInfo *exception)
Definition: cache-view.c:299
MagickExport MagickBooleanType CloneImageProperties(Image *image, const Image *clone_image)
Definition: property.c:134
MagickExport MagickBooleanType SetImageMask(Image *image, const PixelMask type, const Image *mask, ExceptionInfo *exception)
Definition: image.c:3185
#define UndefinedTicksPerSecond
Definition: image-private.h:35
MagickExport MagickBooleanType IsGeometry(const char *geometry)
Definition: geometry.c:610
MagickExport Image * BlobToImage(const ImageInfo *image_info, const void *blob, const size_t length, ExceptionInfo *exception)
Definition: blob.c:422
static ssize_t SmushXGap(const Image *smush_image, const Image *images, const ssize_t offset, ExceptionInfo *exception)
Definition: image.c:3537
MagickExport void GetPathComponent(const char *path, PathType type, char *component)
Definition: utility.c:1213
ChannelType channel
Definition: image.h:449
MagickExport MagickBooleanType SetImageAlphaChannel(Image *image, const AlphaChannelOption alpha_type, ExceptionInfo *exception)
Definition: channel.c:974
MagickBooleanType
Definition: magick-type.h:158
PixelInfo matte_color
Definition: image.h:494
MagickExport PixelChannelMap * ClonePixelChannelMap(PixelChannelMap *channel_map)
Definition: pixel.c:133
MagickPrivate void ClonePixelCacheMethods(Cache, const Cache)
MagickExport Image * NewImageList(void)
Definition: list.c:938
PrimaryInfo red_primary
Definition: image.h:125
size_t scene
Definition: image.h:240
unsigned int MagickStatusType
Definition: magick-type.h:121
MagickExport char * AcquireString(const char *source)
Definition: string.c:129
ClassType
Definition: magick-type.h:151
ExceptionInfo * exception
Definition: image-view.c:73
MagickBooleanType black_point_compensation
Definition: image.h:258
MagickExport MagickBooleanType IsImageObject(const Image *image)
Definition: image.c:1905
size_t length
Definition: image.h:477
struct _ImageInfo * image_info
Definition: image.h:342
MagickExport StringInfo * DestroyStringInfo(StringInfo *string_info)
Definition: string.c:850
static Quantum GetPixelWriteMask(const Image *magick_restrict image, const Quantum *magick_restrict pixel)
MagickExport void * AcquireQuantumMemory(const size_t count, const size_t quantum)
Definition: memory.c:543
char filename[MagickPathExtent]
Definition: image.h:480
MagickExport MagickBooleanType CloneImageProfiles(Image *image, const Image *clone_image)
Definition: profile.c:177
MagickExport int LocaleNCompare(const char *p, const char *q, const size_t length)
Definition: locale.c:1570
CustomStreamInfo * custom_stream
Definition: image.h:491
double y
Definition: geometry.h:123
void * blob
Definition: image.h:474
MagickExport time_t GetMagickTime(void)
Definition: timer.c:326
MagickExport ssize_t ReadBlob(Image *, const size_t, void *)
MagickExport MagickBooleanType ClipImagePath(Image *image, const char *pathname, const MagickBooleanType inside, ExceptionInfo *exception)
Definition: image.c:700
double fuzz
Definition: image.h:420
ChannelType channel_mask
Definition: image.h:288
GravityType gravity
Definition: image.h:231
MagickExport MagickBooleanType CloseBlob(Image *)
volatile ssize_t reference_count
Definition: image.h:337
size_t scene
Definition: image.h:396
RectangleInfo page
Definition: image.h:212
MagickPrivate MagickBooleanType IsGlob(const char *) magick_attribute((__pure__))
Definition: token.c:591
MagickExport void DestroyImageProperties(Image *image)
Definition: property.c:314
size_t magick_columns
Definition: image.h:324
#define UndefinedCompressionQuality
Definition: image-private.h:36
MagickExport const char DefaultTileLabel[]
Definition: image.c:115
size_t MagickSizeType
Definition: magick-type.h:130
#define MagickPathExtent
void * cache
Definition: image.h:294
ResolutionType units
Definition: image.h:407
MagickExport PixelChannelMap * DestroyPixelChannelMap(PixelChannelMap *channel_map)
Definition: pixel.c:350
MagickExport MagickBooleanType IsStringTrue(const char *value)
Definition: string.c:1425
static void GetPixelInfoPixel(const Image *magick_restrict image, const Quantum *magick_restrict pixel, PixelInfo *magick_restrict pixel_info)
MagickExport MagickBooleanType IsEventLogging(void)
Definition: log.c:720
CompressionType compression
Definition: image.h:378
PrimaryInfo blue_primary
Definition: image.h:125
#define ThrowFileException(exception, severity, tag, context)
OrientationType orientation
Definition: image.h:381
PixelTrait alpha_trait
Definition: image.h:280
MagickExport void AcquireNextImage(const ImageInfo *image_info, Image *image, ExceptionInfo *exception)
Definition: image.c:386
MagickExport ChannelType SetPixelChannelMask(Image *image, const ChannelType channel_mask)
Definition: pixel.c:6277
static Quantum GetPixelIndex(const Image *magick_restrict image, const Quantum *magick_restrict pixel)
MagickExport void DisassociateBlob(Image *)
MagickExport void SetBlobExempt(Image *image, const MagickBooleanType exempt)
Definition: blob.c:4992
MagickExport ChannelType SetImageChannelMask(Image *image, const ChannelType channel_mask)
Definition: image.c:2501
MagickBooleanType monochrome
Definition: image.h:432
MagickExport Quantum * QueueCacheViewAuthenticPixels(CacheView *cache_view, const ssize_t x, const ssize_t y, const size_t columns, const size_t rows, ExceptionInfo *exception)
Definition: cache-view.c:977
MagickExport MagickBooleanType SetImageInfo(ImageInfo *image_info, const unsigned int frames, ExceptionInfo *exception)
Definition: image.c:2705
MagickExport VirtualPixelMethod SetImageVirtualPixelMethod(Image *image, const VirtualPixelMethod virtual_pixel_method, ExceptionInfo *exception)
Definition: image.c:3492
GravityType
Definition: geometry.h:77
char magick_filename[MagickPathExtent]
Definition: image.h:319
struct _Image * previous
Definition: image.h:348
MagickBooleanType dither
Definition: image.h:267
MagickExport MagickBooleanType ThrowMagickException(ExceptionInfo *exception, const char *module, const char *function, const size_t line, const ExceptionType severity, const char *tag, const char *format,...)
Definition: exception.c:1145
MagickExport MagickBooleanType LogMagickEvent(const LogEventType type, const char *module, const char *function, const size_t line, const char *format,...)
Definition: log.c:1409
MagickExport MagickOffsetType SeekBlob(Image *, const MagickOffsetType, const int)
MagickExport MagickBooleanType SetImageBackgroundColor(Image *image, ExceptionInfo *exception)
Definition: image.c:2417
size_t signature
Definition: image.h:354
size_t columns
Definition: image.h:172
MagickExport const MagickInfo * GetMagickInfo(const char *name, ExceptionInfo *exception)
Definition: magick.c:612
MagickExport Image * SmushImages(const Image *images, const MagickBooleanType stack, const ssize_t offset, ExceptionInfo *exception)
Definition: image.c:3679
MagickExport MagickBooleanType SetImageColor(Image *image, const PixelInfo *color, ExceptionInfo *exception)
Definition: image.c:2534
MagickExport Image * AcquireImage(const ImageInfo *image_info, ExceptionInfo *exception)
Definition: image.c:156
MagickExport MagickBooleanType OpenBlob(const ImageInfo *, Image *, const BlobMode, ExceptionInfo *)
MagickExport MagickBooleanType GetMagickAdjoin(const MagickInfo *magick_info)
Definition: magick.c:352
ssize_t x
Definition: geometry.h:134
static Quantum PushColormapIndex(Image *image, const Quantum index, MagickBooleanType *range_exception)
Definition: image.c:3874
MagickExport char * GetEnvironmentValue(const char *name)
Definition: string.c:1182
SemaphoreInfo * semaphore
Definition: image.h:340
MagickExport const char BorderColor[]
Definition: image.c:112
struct _Image * next
Definition: image.h:348
size_t height
Definition: geometry.h:130
MagickExport MagickBooleanType QueryColorCompliance(const char *name, const ComplianceType compliance, PixelInfo *color, ExceptionInfo *exception)
Definition: color.c:2216
ChannelType
Definition: pixel.h:33
MagickExport MagickBooleanType SetImageStorageClass(Image *image, const ClassType storage_class, ExceptionInfo *exception)
Definition: image.c:2617
MagickExport void CatchException(ExceptionInfo *exception)
Definition: exception.c:203
static void SetPixelWriteMask(const Image *magick_restrict image, const Quantum mask, Quantum *magick_restrict pixel)
MagickExport size_t CopyMagickString(char *destination, const char *source, const size_t length)
Definition: string.c:755
ssize_t offset
Definition: image.h:206
RectangleInfo extract_info
Definition: image.h:212
MagickExport MagickBooleanType ResetImagePage(Image *image, const char *page)
Definition: image.c:2172
MagickExport MagickBooleanType GetMagickEndianSupport(const MagickInfo *magick_info)
Definition: magick.c:577
MagickExport size_t InterpretImageFilename(const ImageInfo *image_info, Image *image, const char *format, int value, char *filename, ExceptionInfo *exception)
Definition: image.c:1649
PixelChannel
Definition: pixel.h:67
MagickExport MagickBooleanType IsBlobSeekable(const Image *image)
Definition: blob.c:2849
MagickExport MagickBooleanType CopyImagePixels(Image *image, const Image *source_image, const RectangleInfo *geometry, const OffsetInfo *offset, ExceptionInfo *exception)
Definition: image.c:1049
char * texture
Definition: image.h:413
MagickExport MagickBooleanType SetImageExtent(Image *image, const size_t columns, const size_t rows, ExceptionInfo *exception)
Definition: image.c:2659
RenderingIntent
Definition: profile.h:30
double y
Definition: image.h:99
size_t quality
Definition: image.h:163
size_t colors
Definition: image.h:172
size_t depth
Definition: pixel.h:185
TimerInfo timer
Definition: image.h:300
MagickExport MagickBooleanType SyncImagesSettings(ImageInfo *image_info, Image *images, ExceptionInfo *exception)
Definition: image.c:3986
MagickExport const char SaveImageTag[]
Definition: image.c:122
static size_t GetPixelChannels(const Image *magick_restrict image)
MagickExport int LocaleCompare(const char *p, const char *q)
Definition: locale.c:1435
static void SetPixelCompositeMask(const Image *magick_restrict image, const Quantum mask, Quantum *magick_restrict pixel)
PixelInfo border_color
Definition: image.h:424
DisposeType
Definition: layer.h:27
char filename[MagickPathExtent]
Definition: image.h:319
#define GetMagickModule()
Definition: log.h:28
PrimaryInfo green_primary
Definition: image.h:125
MagickFormatType
Definition: magick.h:28
MagickExport void GetTimerInfo(TimerInfo *time_info)
Definition: timer.c:365
size_t quality
Definition: image.h:410
MagickBooleanType affirm
Definition: image.h:384
MagickExport void ConformPixelInfo(Image *image, const PixelInfo *source, PixelInfo *destination, ExceptionInfo *exception)
Definition: pixel.c:212
#define ThrowImageException(severity, tag)
static Quantum ClampToQuantum(const MagickRealType value)
Definition: quantum.h:84
static PixelChannel GetPixelChannelChannel(const Image *magick_restrict image, const ssize_t offset)
MagickExport CacheView * AcquireVirtualCacheView(const Image *image, ExceptionInfo *exception)
Definition: cache-view.c:149
PrimaryInfo white_point
Definition: image.h:125
void * client_data
Definition: image.h:464
char * density
Definition: image.h:413
MagickExport MagickBooleanType ResetImagePixels(Image *image, ExceptionInfo *exception)
Definition: image.c:2243
char unique[MagickPathExtent]
Definition: image.h:480
static double StringToDoubleInterval(const char *string, const double interval)
MagickExport ImageInfo * DestroyImageInfo(ImageInfo *image_info)
Definition: image.c:1252
CompressionType
Definition: compress.h:25
RenderingIntent rendering_intent
Definition: image.h:192
MagickExport Image * AppendImages(const Image *images, const MagickBooleanType stack, ExceptionInfo *exception)
Definition: image.c:443
MagickExport MagickBooleanType IsTaintImage(const Image *image)
Definition: image.c:1942
MagickExport MagickBooleanType CloneImageOptions(ImageInfo *image_info, const ImageInfo *clone_info)
Definition: option.c:2130
const char MatteColor[]
Definition: image.c:119
MagickBooleanType synchronize
Definition: image.h:458
unsigned short Quantum
Definition: magick-type.h:82
MagickExport MagickBooleanType SetImageColorspace(Image *image, const ColorspaceType colorspace, ExceptionInfo *exception)
Definition: colorspace.c:1135
char * server_name
Definition: image.h:413
MagickExport void DestroyImageArtifacts(Image *image)
Definition: artifact.c:233
ChannelType channels
Definition: image.h:366
MagickExport Image * GetNextImageInList(const Image *images)
Definition: list.c:771
MagickExport const char LoadImagesTag[]
Definition: image.c:118
MagickExport char * DestroyString(char *string)
Definition: string.c:823
MagickExport void * AcquireMagickMemory(const size_t size)
Definition: memory.c:472
char * geometry
Definition: image.h:201
MagickExport MagickBooleanType DeleteImageProperty(Image *image, const char *property)
Definition: property.c:279
MagickExport const char * GetImageProperty(const Image *image, const char *property, ExceptionInfo *exception)
Definition: property.c:2233
MagickExport MagickBooleanType ModifyImage(Image **image, ExceptionInfo *exception)
Definition: image.c:1995
MagickPrivate VirtualPixelMethod SetPixelCacheVirtualMethod(Image *, const VirtualPixelMethod, ExceptionInfo *)
Definition: cache.c:5190
MagickExport MagickBooleanType IsBlobExempt(const Image *image)
Definition: blob.c:2818
MagickExport MagickBooleanType StripImage(Image *image, ExceptionInfo *exception)
Definition: image.c:3830
MagickExport ImageInfo * CloneImageInfo(const ImageInfo *image_info)
Definition: image.c:940
size_t number_channels
Definition: image.h:283
#define CopyImageTag
time_t timestamp
Definition: image.h:331
MagickExport MagickStatusType ParseGeometry(const char *geometry, GeometryInfo *geometry_info)
Definition: geometry.c:853
static void SetPixelChannel(const Image *magick_restrict image, const PixelChannel channel, const Quantum quantum, Quantum *magick_restrict pixel)
MagickBooleanType dither
Definition: image.h:432
char * directory
Definition: image.h:201
ChromaticityInfo chromaticity
Definition: image.h:189
BlobInfo * blob
Definition: image.h:328
FILE * file
Definition: image.h:471
static Quantum GetPixelCompositeMask(const Image *magick_restrict image, const Quantum *magick_restrict pixel)
static void SetPixelAlpha(const Image *magick_restrict image, const Quantum alpha, Quantum *magick_restrict pixel)
size_t metacontent_extent
Definition: image.h:283
MagickExport void SetGeometry(const Image *image, RectangleInfo *geometry)
Definition: geometry.c:1686
ssize_t x
Definition: geometry.h:116
MagickExport const MagicInfo * GetMagicInfo(const unsigned char *magic, const size_t length, ExceptionInfo *exception)
Definition: magic.c:280
MagickExport void GetImageInfo(ImageInfo *image_info)
Definition: image.c:1345
MagickExport MagickBooleanType IsHighDynamicRangeImage(const Image *image, ExceptionInfo *exception)
Definition: image.c:1806
MagickExport void * RelinquishMagickMemory(void *memory)
Definition: memory.c:1069
PointInfo resolution
Definition: image.h:209
MagickExport size_t GetMagicPatternExtent(ExceptionInfo *exception)
Definition: magic.c:363
MagickBooleanType(* MagickProgressMonitor)(const char *, const MagickOffsetType, const MagickSizeType, void *)
Definition: monitor.h:26
MagickExport MagickBooleanType ClipImage(Image *image, ExceptionInfo *exception)
Definition: image.c:695
ImageType
Definition: image.h:48
MagickExport void GravityAdjustGeometry(const size_t width, const size_t height, const GravityType gravity, RectangleInfo *region)
Definition: geometry.c:531
MagickExport char * CloneString(char **destination, const char *source)
Definition: string.c:286
#define Swap(x, y)
Definition: studio.h:345
MagickExport void SetImageInfoCustomStream(ImageInfo *image_info, CustomStreamInfo *custom_stream)
Definition: image.c:3110
MagickExport BlobInfo * ReferenceBlob(BlobInfo *)
Definition: blob.c:4826
MagickExport MagickBooleanType CloneImageArtifacts(Image *image, const Image *clone_image)
Definition: artifact.c:102
CompositeOperator compose
Definition: image.h:234
CompositeOperator
Definition: composite.h:25
ResolutionType
Definition: image.h:89
#define MagickExport
MagickSizeType extent
Definition: image.h:270
MagickExport MagickBooleanType SyncCacheViewAuthenticPixels(CacheView *magick_restrict cache_view, ExceptionInfo *exception)
Definition: cache-view.c:1100
OrientationType orientation
Definition: image.h:166
MagickProgressMonitor progress_monitor
Definition: image.h:461
double fuzz
Definition: image.h:216
ssize_t y
Definition: geometry.h:134
MagickExport CacheView * AcquireAuthenticCacheView(const Image *image, ExceptionInfo *exception)
Definition: cache-view.c:112
MagickExport void DestroyBlob(Image *image)
Definition: blob.c:893
MagickExport const double DefaultResolution
Definition: image.c:127
ColorspaceType colorspace
Definition: pixel.h:176
static ssize_t SmushYGap(const Image *smush_image, const Image *images, const ssize_t offset, ExceptionInfo *exception)
Definition: image.c:3608
MagickBooleanType adjoin
Definition: image.h:384
PixelMask
Definition: pixel.h:127
char * page
Definition: image.h:390
MagickBooleanType ping
Definition: image.h:445
PixelTrait
Definition: pixel.h:135
MagickExport MagickBooleanType IsSceneGeometry(const char *geometry, const MagickBooleanType pedantic)
Definition: geometry.c:651
PixelInfo transparent_color
Definition: image.h:179
#define AppendImageTag
MagickExport MagickRealType GetPixelIntensity(const Image *magick_restrict image, const Quantum *magick_restrict pixel)
Definition: pixel.c:2358
PixelInfo background_color
Definition: image.h:179
MagickExport MagickBooleanType SetImageRegionMask(Image *image, const PixelMask type, const RectangleInfo *region, ExceptionInfo *exception)
Definition: image.c:3342
MagickExport void RelinquishSemaphoreInfo(SemaphoreInfo **semaphore_info)
Definition: semaphore.c:351
MagickSizeType QuantumAny
Definition: magick-type.h:144
void * client_data
Definition: image.h:306
MagickExport void LocaleUpper(char *string)
Definition: locale.c:1630
MagickExport Image * DestroyImage(Image *image)
Definition: image.c:1181
static void SetPixelReadMask(const Image *magick_restrict image, const Quantum mask, Quantum *magick_restrict pixel)
MagickExport Image * CloneImage(const Image *image, const size_t columns, const size_t rows, const MagickBooleanType detach, ExceptionInfo *exception)
Definition: image.c:796
MagickExport ssize_t GetImageReferenceCount(Image *image)
Definition: image.c:1566
double gamma
Definition: image.h:186
PixelInfo background_color
Definition: image.h:424
MagickExport const char PSPageGeometry[]
Definition: image.c:121
ColorspaceType colorspace
Definition: image.h:157
MagickExport StringInfo * CloneStringInfo(const StringInfo *string_info)
Definition: string.c:338
MagickExport void DisassociateImageStream(Image *image)
Definition: image.c:1314
#define QuantumRange
Definition: magick-type.h:83
MagickExport MagickBooleanType SetImageProgress(const Image *image, const char *tag, const MagickOffsetType offset, const MagickSizeType extent)
Definition: monitor.c:136
MagickBooleanType temporary
Definition: image.h:384
PixelChannelMap * channel_map
Definition: image.h:291
MagickBooleanType debug
Definition: image.h:334
size_t depth
Definition: image.h:396
void * profile
Definition: image.h:455
MagickPrivate Cache AcquirePixelCache(const size_t)
MagickExport ExceptionInfo * DestroyExceptionInfo(ExceptionInfo *exception)
Definition: exception.c:418
size_t depth
Definition: image.h:172
ExceptionType severity
Definition: exception.h:104
MagickExport const char SaveImagesTag[]
Definition: image.c:123