2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6 % IIIII M M AAA GGGG EEEEE %
8 % I M M M AAAAA G GG EEE %
10 % IIIII M M A A GGGG EEEEE %
13 % MagickCore Image Methods %
20 % Copyright 1999-2010 ImageMagick Studio LLC, a non-profit organization %
21 % dedicated to making software imaging solutions freely available. %
23 % You may not use this file except in compliance with the License. You may %
24 % obtain a copy of the License at %
26 % http://www.imagemagick.org/script/license.php %
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. %
34 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
43 #include "magick/studio.h"
44 #include "magick/animate.h"
45 #include "magick/artifact.h"
46 #include "magick/blob.h"
47 #include "magick/blob-private.h"
48 #include "magick/cache.h"
49 #include "magick/cache-private.h"
50 #include "magick/cache-view.h"
51 #include "magick/client.h"
52 #include "magick/color.h"
53 #include "magick/color-private.h"
54 #include "magick/colormap.h"
55 #include "magick/colorspace.h"
56 #include "magick/colorspace-private.h"
57 #include "magick/composite.h"
58 #include "magick/composite-private.h"
59 #include "magick/compress.h"
60 #include "magick/constitute.h"
61 #include "magick/deprecate.h"
62 #include "magick/display.h"
63 #include "magick/draw.h"
64 #include "magick/enhance.h"
65 #include "magick/exception.h"
66 #include "magick/exception-private.h"
67 #include "magick/gem.h"
68 #include "magick/geometry.h"
69 #include "magick/histogram.h"
70 #include "magick/image-private.h"
71 #include "magick/list.h"
72 #include "magick/magic.h"
73 #include "magick/magick.h"
74 #include "magick/memory_.h"
75 #include "magick/module.h"
76 #include "magick/monitor.h"
77 #include "magick/monitor-private.h"
78 #include "magick/option.h"
79 #include "magick/paint.h"
80 #include "magick/pixel-private.h"
81 #include "magick/profile.h"
82 #include "magick/property.h"
83 #include "magick/quantize.h"
84 #include "magick/random_.h"
85 #include "magick/segment.h"
86 #include "magick/semaphore.h"
87 #include "magick/signature-private.h"
88 #include "magick/statistic.h"
89 #include "magick/string_.h"
90 #include "magick/string-private.h"
91 #include "magick/thread-private.h"
92 #include "magick/threshold.h"
93 #include "magick/timer.h"
94 #include "magick/utility.h"
95 #include "magick/version.h"
96 #include "magick/xwindow-private.h"
102 BackgroundColor[] = "#ffffff", /* white */
103 BorderColor[] = "#dfdfdf", /* gray */
104 DefaultTileFrame[] = "15x15+3+3",
105 DefaultTileGeometry[] = "120x120+4+3>",
106 DefaultTileLabel[] = "%f\n%G\n%b",
107 ForegroundColor[] = "#000", /* black */
108 LoadImageTag[] = "Load/Image",
109 LoadImagesTag[] = "Load/Images",
110 MatteColor[] = "#bdbdbd", /* gray */
111 PSDensityGeometry[] = "72.0x72.0",
112 PSPageGeometry[] = "612x792",
113 SaveImageTag[] = "Save/Image",
114 SaveImagesTag[] = "Save/Images",
115 TransparentColor[] = "#00000000"; /* transparent black */
118 DefaultResolution = 72.0;
121 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
125 % A c q u i r e I m a g e %
129 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
131 % AcquireImage() returns a pointer to an image structure initialized to
134 % The format of the AcquireImage method is:
136 % Image *AcquireImage(const ImageInfo *image_info)
138 % A description of each parameter follows:
140 % o image_info: Many of the image default values are set from this
141 % structure. For example, filename, compression, depth, background color,
145 MagickExport Image *AcquireImage(const ImageInfo *image_info)
154 Allocate image structure.
156 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
157 image=(Image *) AcquireAlignedMemory(1,sizeof(*image));
158 if (image == (Image *) NULL)
159 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
160 (void) ResetMagickMemory(image,0,sizeof(*image));
162 Initialize Image structure.
164 (void) CopyMagickString(image->magick,"MIFF",MaxTextExtent);
165 image->storage_class=DirectClass;
166 image->depth=MAGICKCORE_QUANTUM_DEPTH;
167 image->colorspace=RGBColorspace;
168 image->interlace=NoInterlace;
169 image->ticks_per_second=UndefinedTicksPerSecond;
170 image->compose=OverCompositeOp;
172 GetExceptionInfo(&image->exception);
173 (void) QueryColorDatabase(BackgroundColor,&image->background_color,
175 (void) QueryColorDatabase(BorderColor,&image->border_color,&image->exception);
176 (void) QueryColorDatabase(MatteColor,&image->matte_color,&image->exception);
177 (void) QueryColorDatabase(TransparentColor,&image->transparent_color,
179 image->x_resolution=DefaultResolution;
180 image->y_resolution=DefaultResolution;
181 image->units=PixelsPerInchResolution;
182 GetTimerInfo(&image->timer);
183 image->cache=AcquirePixelCache(0);
184 image->blob=CloneBlobInfo((BlobInfo *) NULL);
185 image->debug=IsEventLogging();
186 image->reference_count=1;
187 image->semaphore=AllocateSemaphoreInfo();
188 image->signature=MagickSignature;
189 if (image_info == (ImageInfo *) NULL)
194 SetBlobExempt(image,image_info->file != (FILE *) NULL ? MagickTrue :
196 (void) CopyMagickString(image->filename,image_info->filename,MaxTextExtent);
197 (void) CopyMagickString(image->magick_filename,image_info->filename,
199 (void) CopyMagickString(image->magick,image_info->magick,MaxTextExtent);
200 if (image_info->size != (char *) NULL)
202 (void) ParseAbsoluteGeometry(image_info->size,&image->extract_info);
203 image->columns=image->extract_info.width;
204 image->rows=image->extract_info.height;
205 image->offset=image->extract_info.x;
206 image->extract_info.x=0;
207 image->extract_info.y=0;
209 if (image_info->extract != (char *) NULL)
214 flags=ParseAbsoluteGeometry(image_info->extract,&geometry);
215 if (((flags & XValue) != 0) || ((flags & YValue) != 0))
217 image->extract_info=geometry;
218 Swap(image->columns,image->extract_info.width);
219 Swap(image->rows,image->extract_info.height);
222 image->compression=image_info->compression;
223 image->quality=image_info->quality;
224 image->endian=image_info->endian;
225 image->interlace=image_info->interlace;
226 image->units=image_info->units;
227 if (image_info->density != (char *) NULL)
232 flags=ParseGeometry(image_info->density,&geometry_info);
233 image->x_resolution=geometry_info.rho;
234 image->y_resolution=geometry_info.sigma;
235 if ((flags & SigmaValue) == 0)
236 image->y_resolution=image->x_resolution;
238 if (image_info->page != (char *) NULL)
243 image->page=image->extract_info;
244 geometry=GetPageGeometry(image_info->page);
245 (void) ParseAbsoluteGeometry(geometry,&image->page);
246 geometry=DestroyString(geometry);
248 if (image_info->depth != 0)
249 image->depth=image_info->depth;
250 image->dither=image_info->dither;
251 image->background_color=image_info->background_color;
252 image->border_color=image_info->border_color;
253 image->matte_color=image_info->matte_color;
254 image->transparent_color=image_info->transparent_color;
255 image->progress_monitor=image_info->progress_monitor;
256 image->client_data=image_info->client_data;
257 if (image_info->cache != (void *) NULL)
258 ClonePixelCacheMethods(image->cache,image_info->cache);
259 (void) SetImageVirtualPixelMethod(image,image_info->virtual_pixel_method);
260 (void) SyncImageSettings(image_info,image);
265 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
269 % A c q u i r e I m a g e C o l o r m a p %
273 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
275 % AcquireImageColormap() allocates an image colormap and initializes
276 % it to a linear gray colorspace. If the image already has a colormap,
277 % it is replaced. AcquireImageColormap() returns MagickTrue if successful,
278 % otherwise MagickFalse if there is not enough memory.
280 % The format of the AcquireImageColormap method is:
282 % MagickBooleanType AcquireImageColormap(Image *image,
283 % const unsigned long colors)
285 % A description of each parameter follows:
287 % o image: the image.
289 % o colors: the number of colors in the image colormap.
293 static inline unsigned long MagickMax(const unsigned long x,
294 const unsigned long y)
301 static inline unsigned long MagickMin(const unsigned long x,
302 const unsigned long y)
309 MagickExport MagickBooleanType AcquireImageColormap(Image *image,
310 const unsigned long colors)
319 Allocate image colormap.
321 assert(image != (Image *) NULL);
322 assert(image->signature == MagickSignature);
323 if (image->debug != MagickFalse)
324 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
325 image->colors=colors;
326 length=(size_t) colors;
327 if (image->colormap == (PixelPacket *) NULL)
328 image->colormap=(PixelPacket *) AcquireQuantumMemory(length,
329 sizeof(*image->colormap));
331 image->colormap=(PixelPacket *) ResizeQuantumMemory(image->colormap,length,
332 sizeof(*image->colormap));
333 if (image->colormap == (PixelPacket *) NULL)
334 ThrowBinaryException(ResourceLimitError,"MemoryAllocationFailed",
336 for (i=0; i < (long) image->colors; i++)
341 pixel=(unsigned long) (i*(QuantumRange/MagickMax(colors-1,1)));
342 image->colormap[i].red=(Quantum) pixel;
343 image->colormap[i].green=(Quantum) pixel;
344 image->colormap[i].blue=(Quantum) pixel;
345 image->colormap[i].opacity=OpaqueOpacity;
347 return(SetImageStorageClass(image,PseudoClass));
351 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
355 % A c q u i r e I m a g e I n f o %
359 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
361 % AcquireImageInfo() allocates the ImageInfo structure.
363 % The format of the AcquireImageInfo method is:
365 % ImageInfo *AcquireImageInfo(void)
368 MagickExport ImageInfo *AcquireImageInfo(void)
373 image_info=(ImageInfo *) AcquireAlignedMemory(1,sizeof(*image_info));
374 if (image_info == (ImageInfo *) NULL)
375 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
376 GetImageInfo(image_info);
381 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
385 % A c q u i r e N e x t I m a g e %
389 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
391 % AcquireNextImage() initializes the next image in a sequence to
392 % default values. The next member of image points to the newly allocated
393 % image. If there is a memory shortage, next is assigned NULL.
395 % The format of the AcquireNextImage method is:
397 % void AcquireNextImage(const ImageInfo *image_info,Image *image)
399 % A description of each parameter follows:
401 % o image_info: Many of the image default values are set from this
402 % structure. For example, filename, compression, depth, background color,
405 % o image: the image.
408 MagickExport void AcquireNextImage(const ImageInfo *image_info,Image *image)
411 Allocate image structure.
413 assert(image != (Image *) NULL);
414 assert(image->signature == MagickSignature);
415 if (image->debug != MagickFalse)
416 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
417 image->next=AcquireImage(image_info);
418 if (GetNextImageInList(image) == (Image *) NULL)
420 (void) CopyMagickString(GetNextImageInList(image)->filename,image->filename,
422 if (image_info != (ImageInfo *) NULL)
423 (void) CopyMagickString(GetNextImageInList(image)->filename,
424 image_info->filename,MaxTextExtent);
425 DestroyBlob(GetNextImageInList(image));
426 image->next->blob=ReferenceBlob(image->blob);
427 image->next->endian=image->endian;
428 image->next->scene=image->scene+1;
429 image->next->previous=image;
433 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
437 % A p p e n d I m a g e s %
441 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
443 % AppendImages() takes all images from the current image pointer to the end
444 % of the image list and appends them to each other top-to-bottom if the
445 % stack parameter is true, otherwise left-to-right.
447 % The current gravity setting now effects how the image is justified in the
450 % The format of the AppendImages method is:
452 % Image *AppendImages(const Image *image,const MagickBooleanType stack,
453 % ExceptionInfo *exception)
455 % A description of each parameter follows:
457 % o image: the image sequence.
459 % o stack: A value other than 0 stacks the images top-to-bottom.
461 % o exception: return any errors or warnings in this structure.
464 MagickExport Image *AppendImages(const Image *image,
465 const MagickBooleanType stack,ExceptionInfo *exception)
467 #define AppendImageTag "Append/Image"
499 Ensure the image have the same column width.
501 assert(image != (Image *) NULL);
502 assert(image->signature == MagickSignature);
503 if (image->debug != MagickFalse)
504 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
505 assert(exception != (ExceptionInfo *) NULL);
506 assert(exception->signature == MagickSignature);
509 width=image->columns;
511 next=GetNextImageInList(image);
512 for ( ; next != (Image *) NULL; next=GetNextImageInList(next))
514 if (next->matte != MagickFalse)
517 if (stack != MagickFalse)
519 if (next->columns > width)
524 width+=next->columns;
525 if (next->rows > height)
529 Initialize append next attributes.
531 append_image=CloneImage(image,width,height,MagickTrue,exception);
532 if (append_image == (Image *) NULL)
533 return((Image *) NULL);
534 if (SetImageStorageClass(append_image,DirectClass) == MagickFalse)
536 InheritException(exception,&append_image->exception);
537 append_image=DestroyImage(append_image);
538 return((Image *) NULL);
540 append_image->matte=matte;
541 (void) SetImageBackgroundColor(append_image);
545 append_view=AcquireCacheView(append_image);
546 for (n=0; n < (long) number_images; n++)
548 SetGeometry(append_image,&geometry);
549 GravityAdjustGeometry(image->columns,image->rows,image->gravity,&geometry);
550 if (stack != MagickFalse)
551 x_offset-=geometry.x;
553 y_offset-=geometry.y;
554 image_view=AcquireCacheView(image);
555 #if defined(MAGICKCORE_OPENMP_SUPPORT)
556 #pragma omp parallel for schedule(dynamic,4) shared(status)
558 for (y=0; y < (long) image->rows; y++)
563 register const IndexPacket
566 register const PixelPacket
570 *restrict append_indexes;
578 if (status == MagickFalse)
580 p=GetCacheViewVirtualPixels(image_view,0,y,image->columns,1,exception);
581 q=QueueCacheViewAuthenticPixels(append_view,x_offset,y+y_offset,
582 image->columns,1,exception);
583 if ((p == (const PixelPacket *) NULL) || (q == (PixelPacket *) NULL))
588 indexes=GetCacheViewVirtualIndexQueue(image_view);
589 append_indexes=GetCacheViewAuthenticIndexQueue(append_view);
590 for (x=0; x < (long) image->columns; x++)
592 SetRedPixelComponent(q,GetRedPixelComponent(p));
593 SetGreenPixelComponent(q,GetGreenPixelComponent(p));
594 SetBluePixelComponent(q,GetBluePixelComponent(p));
595 SetOpacityPixelComponent(q,OpaqueOpacity);
596 if (image->matte != MagickFalse)
597 SetOpacityPixelComponent(q,GetOpacityPixelComponent(p));
598 if (image->colorspace == CMYKColorspace)
599 append_indexes[x]=indexes[x];
603 sync=SyncCacheViewAuthenticPixels(append_view,exception);
604 if (sync == MagickFalse)
607 image_view=DestroyCacheView(image_view);
608 proceed=SetImageProgress(image,AppendImageTag,n,number_images);
609 if (proceed == MagickFalse)
611 if (stack == MagickFalse)
613 x_offset+=image->columns;
619 y_offset+=image->rows;
621 image=GetNextImageInList(image);
623 append_view=DestroyCacheView(append_view);
624 if (status == MagickFalse)
625 append_image=DestroyImage(append_image);
626 return(append_image);
630 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
634 % C a t c h I m a g e E x c e p t i o n %
638 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
640 % CatchImageException() returns if no exceptions are found in the image
641 % sequence, otherwise it determines the most severe exception and reports
642 % it as a warning or error depending on the severity.
644 % The format of the CatchImageException method is:
646 % ExceptionType CatchImageException(Image *image)
648 % A description of each parameter follows:
650 % o image: An image sequence.
653 MagickExport ExceptionType CatchImageException(Image *image)
661 assert(image != (const Image *) NULL);
662 assert(image->signature == MagickSignature);
663 if (image->debug != MagickFalse)
664 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
665 exception=AcquireExceptionInfo();
666 GetImageException(image,exception);
667 CatchException(exception);
668 severity=exception->severity;
669 exception=DestroyExceptionInfo(exception);
674 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
678 % C l i p I m a g e P a t h %
682 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
684 % ClipImagePath() sets the image clip mask based any clipping path information
687 % The format of the ClipImagePath method is:
689 % MagickBooleanType ClipImagePath(Image *image,const char *pathname,
690 % const MagickBooleanType inside)
692 % A description of each parameter follows:
694 % o image: the image.
696 % o pathname: name of clipping path resource. If name is preceded by #, use
697 % clipping path numbered by name.
699 % o inside: if non-zero, later operations take effect inside clipping path.
700 % Otherwise later operations take effect outside clipping path.
704 MagickExport MagickBooleanType ClipImage(Image *image)
706 return(ClipImagePath(image,"#1",MagickTrue));
709 MagickExport MagickBooleanType ClipImagePath(Image *image,const char *pathname,
710 const MagickBooleanType inside)
712 #define ClipImagePathTag "ClipPath/Image"
726 assert(image != (const Image *) NULL);
727 assert(image->signature == MagickSignature);
728 if (image->debug != MagickFalse)
729 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
730 assert(pathname != NULL);
731 property=AcquireString(pathname);
732 (void) FormatMagickString(property,MaxTextExtent,"8BIM:1999,2998:%s",
734 value=GetImageProperty(image,property);
735 property=DestroyString(property);
736 if (value == (const char *) NULL)
738 ThrowFileException(&image->exception,OptionError,"NoClipPathDefined",
742 image_info=AcquireImageInfo();
743 (void) CopyMagickString(image_info->filename,image->filename,MaxTextExtent);
744 (void) ConcatenateMagickString(image_info->filename,pathname,MaxTextExtent);
745 clip_mask=BlobToImage(image_info,value,strlen(value),&image->exception);
746 image_info=DestroyImageInfo(image_info);
747 if (clip_mask == (Image *) NULL)
749 if (clip_mask->storage_class == PseudoClass)
751 (void) SyncImage(clip_mask);
752 if (SetImageStorageClass(clip_mask,DirectClass) == MagickFalse)
755 if (inside == MagickFalse)
756 (void) NegateImage(clip_mask,MagickFalse);
757 (void) FormatMagickString(clip_mask->magick_filename,MaxTextExtent,
758 "8BIM:1999,2998:%s\nPS",pathname);
759 (void) SetImageClipMask(image,clip_mask);
760 clip_mask=DestroyImage(clip_mask);
765 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
769 % C l o n e I m a g e %
773 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
775 % CloneImage() copies an image and returns the copy as a new image object.
776 % If the specified columns and rows is 0, an exact copy of the image is
777 % returned, otherwise the pixel data is undefined and must be initialized
778 % with the QueueAuthenticPixels() and SyncAuthenticPixels() methods. On
779 % failure, a NULL image is returned and exception describes the reason for the
782 % The format of the CloneImage method is:
784 % Image *CloneImage(const Image *image,const unsigned long columns,
785 % const unsigned long rows,const MagickBooleanType orphan,
786 % ExceptionInfo *exception)
788 % A description of each parameter follows:
790 % o image: the image.
792 % o columns: the number of columns in the cloned image.
794 % o rows: the number of rows in the cloned image.
796 % o detach: With a value other than 0, the cloned image is detached from
797 % its parent I/O stream.
799 % o exception: return any errors or warnings in this structure.
802 MagickExport Image *CloneImage(const Image *image,const unsigned long columns,
803 const unsigned long rows,const MagickBooleanType detach,
804 ExceptionInfo *exception)
818 assert(image != (const Image *) NULL);
819 assert(image->signature == MagickSignature);
820 if (image->debug != MagickFalse)
821 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
822 assert(exception != (ExceptionInfo *) NULL);
823 assert(exception->signature == MagickSignature);
824 clone_image=(Image *) AcquireAlignedMemory(1,sizeof(*clone_image));
825 if (clone_image == (Image *) NULL)
826 ThrowImageException(ResourceLimitError,"MemoryAllocationFailed");
827 (void) ResetMagickMemory(clone_image,0,sizeof(*clone_image));
828 clone_image->signature=MagickSignature;
829 clone_image->storage_class=image->storage_class;
830 clone_image->colorspace=image->colorspace;
831 clone_image->matte=image->matte;
832 clone_image->columns=image->columns;
833 clone_image->rows=image->rows;
834 clone_image->dither=image->dither;
835 if (image->colormap != (PixelPacket *) NULL)
838 Allocate and copy the image colormap.
840 clone_image->colors=image->colors;
841 length=(size_t) image->colors;
842 clone_image->colormap=(PixelPacket *) AcquireQuantumMemory(length,
843 sizeof(*clone_image->colormap));
844 if (clone_image->colormap == (PixelPacket *) NULL)
845 ThrowImageException(ResourceLimitError,"MemoryAllocationFailed");
846 (void) CopyMagickMemory(clone_image->colormap,image->colormap,length*
847 sizeof(*clone_image->colormap));
849 (void) CloneImageProfiles(clone_image,image);
850 (void) CloneImageProperties(clone_image,image);
851 (void) CloneImageArtifacts(clone_image,image);
852 GetTimerInfo(&clone_image->timer);
853 GetExceptionInfo(&clone_image->exception);
854 InheritException(&clone_image->exception,&image->exception);
855 if (image->ascii85 != (void *) NULL)
856 Ascii85Initialize(clone_image);
857 clone_image->magick_columns=image->magick_columns;
858 clone_image->magick_rows=image->magick_rows;
859 clone_image->type=image->type;
860 (void) CopyMagickString(clone_image->magick_filename,image->magick_filename,
862 (void) CopyMagickString(clone_image->magick,image->magick,MaxTextExtent);
863 (void) CopyMagickString(clone_image->filename,image->filename,MaxTextExtent);
864 clone_image->progress_monitor=image->progress_monitor;
865 clone_image->client_data=image->client_data;
866 clone_image->reference_count=1;
867 clone_image->next=NewImageList();
868 clone_image->previous=NewImageList();
869 clone_image->list=NewImageList();
870 clone_image->clip_mask=NewImageList();
871 clone_image->mask=NewImageList();
872 if (detach == MagickFalse)
873 clone_image->blob=ReferenceBlob(image->blob);
875 clone_image->blob=CloneBlobInfo((BlobInfo *) NULL);
876 clone_image->debug=IsEventLogging();
877 clone_image->semaphore=AllocateSemaphoreInfo();
878 if ((columns == 0) && (rows == 0))
880 if (image->montage != (char *) NULL)
881 (void) CloneString(&clone_image->montage,image->montage);
882 if (image->directory != (char *) NULL)
883 (void) CloneString(&clone_image->directory,image->directory);
884 if (image->clip_mask != (Image *) NULL)
885 clone_image->clip_mask=CloneImage(image->clip_mask,0,0,MagickTrue,
887 if (image->mask != (Image *) NULL)
888 clone_image->mask=CloneImage(image->mask,0,0,MagickTrue,exception);
889 clone_image->cache=ReferencePixelCache(image->cache);
892 scale=(MagickRealType) columns/(MagickRealType) image->columns;
893 clone_image->page.width=(unsigned long) floor(scale*image->page.width+0.5);
894 clone_image->page.x=(long) ceil(scale*image->page.x-0.5);
895 clone_image->tile_offset.x=(long) ceil(scale*image->tile_offset.x-0.5);
896 scale=(MagickRealType) rows/(MagickRealType) image->rows;
897 clone_image->page.height=(unsigned long) floor(scale*image->page.height+0.5);
898 clone_image->page.y=(long) ceil(scale*image->page.y-0.5);
899 clone_image->tile_offset.y=(long) ceil(scale*image->tile_offset.y-0.5);
900 clone_image->columns=columns;
901 clone_image->rows=rows;
902 clone_image->cache=ClonePixelCache(image->cache);
907 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
911 % C l o n e I m a g e I n f o %
915 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
917 % CloneImageInfo() makes a copy of the given image info structure. If
918 % NULL is specified, a new image info structure is created initialized to
921 % The format of the CloneImageInfo method is:
923 % ImageInfo *CloneImageInfo(const ImageInfo *image_info)
925 % A description of each parameter follows:
927 % o image_info: the image info.
930 MagickExport ImageInfo *CloneImageInfo(const ImageInfo *image_info)
935 clone_info=AcquireImageInfo();
936 if (image_info == (ImageInfo *) NULL)
938 clone_info->compression=image_info->compression;
939 clone_info->temporary=image_info->temporary;
940 clone_info->adjoin=image_info->adjoin;
941 clone_info->antialias=image_info->antialias;
942 clone_info->scene=image_info->scene;
943 clone_info->number_scenes=image_info->number_scenes;
944 clone_info->depth=image_info->depth;
945 if (image_info->size != (char *) NULL)
946 (void) CloneString(&clone_info->size,image_info->size);
947 if (image_info->extract != (char *) NULL)
948 (void) CloneString(&clone_info->extract,image_info->extract);
949 if (image_info->scenes != (char *) NULL)
950 (void) CloneString(&clone_info->scenes,image_info->scenes);
951 if (image_info->page != (char *) NULL)
952 (void) CloneString(&clone_info->page,image_info->page);
953 clone_info->interlace=image_info->interlace;
954 clone_info->endian=image_info->endian;
955 clone_info->units=image_info->units;
956 clone_info->quality=image_info->quality;
957 if (image_info->sampling_factor != (char *) NULL)
958 (void) CloneString(&clone_info->sampling_factor,
959 image_info->sampling_factor);
960 if (image_info->server_name != (char *) NULL)
961 (void) CloneString(&clone_info->server_name,image_info->server_name);
962 if (image_info->font != (char *) NULL)
963 (void) CloneString(&clone_info->font,image_info->font);
964 if (image_info->texture != (char *) NULL)
965 (void) CloneString(&clone_info->texture,image_info->texture);
966 if (image_info->density != (char *) NULL)
967 (void) CloneString(&clone_info->density,image_info->density);
968 clone_info->pointsize=image_info->pointsize;
969 clone_info->fuzz=image_info->fuzz;
970 clone_info->pen=image_info->pen;
971 clone_info->background_color=image_info->background_color;
972 clone_info->border_color=image_info->border_color;
973 clone_info->matte_color=image_info->matte_color;
974 clone_info->transparent_color=image_info->transparent_color;
975 clone_info->dither=image_info->dither;
976 clone_info->monochrome=image_info->monochrome;
977 clone_info->colors=image_info->colors;
978 clone_info->colorspace=image_info->colorspace;
979 clone_info->type=image_info->type;
980 clone_info->orientation=image_info->orientation;
981 clone_info->preview_type=image_info->preview_type;
982 clone_info->group=image_info->group;
983 clone_info->ping=image_info->ping;
984 clone_info->verbose=image_info->verbose;
985 if (image_info->view != (char *) NULL)
986 (void) CloneString(&clone_info->view,image_info->view);
987 if (image_info->authenticate != (char *) NULL)
988 (void) CloneString(&clone_info->authenticate,image_info->authenticate);
989 (void) CloneImageOptions(clone_info,image_info);
990 clone_info->progress_monitor=image_info->progress_monitor;
991 clone_info->client_data=image_info->client_data;
992 clone_info->cache=image_info->cache;
993 if (image_info->cache != (void *) NULL)
994 clone_info->cache=ReferencePixelCache(image_info->cache);
995 if (image_info->profile != (void *) NULL)
996 clone_info->profile=(void *) CloneStringInfo((StringInfo *)
997 image_info->profile);
998 SetImageInfoFile(clone_info,image_info->file);
999 SetImageInfoBlob(clone_info,image_info->blob,image_info->length);
1000 clone_info->stream=image_info->stream;
1001 clone_info->virtual_pixel_method=image_info->virtual_pixel_method;
1002 (void) CopyMagickString(clone_info->magick,image_info->magick,MaxTextExtent);
1003 (void) CopyMagickString(clone_info->unique,image_info->unique,MaxTextExtent);
1004 (void) CopyMagickString(clone_info->zero,image_info->zero,MaxTextExtent);
1005 (void) CopyMagickString(clone_info->filename,image_info->filename,
1007 clone_info->subimage=image_info->scene; /* deprecated */
1008 clone_info->subrange=image_info->number_scenes; /* deprecated */
1009 clone_info->channel=image_info->channel;
1010 clone_info->debug=IsEventLogging();
1011 clone_info->signature=image_info->signature;
1016 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1020 % C o m b i n e I m a g e s %
1024 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1026 % CombineImages() combines one or more images into a single image. The
1027 % grayscale value of the pixels of each image in the sequence is assigned in
1028 % order to the specified channels of the combined image. The typical
1029 % ordering would be image 1 => Red, 2 => Green, 3 => Blue, etc.
1031 % The format of the CombineImages method is:
1033 % Image *CombineImages(const Image *image,const ChannelType channel,
1034 % ExceptionInfo *exception)
1036 % A description of each parameter follows:
1038 % o image: the image.
1040 % o exception: return any errors or warnings in this structure.
1043 MagickExport Image *CombineImages(const Image *image,const ChannelType channel,
1044 ExceptionInfo *exception)
1046 #define CombineImageTag "Combine/Image"
1065 Ensure the image are the same size.
1067 assert(image != (const Image *) NULL);
1068 assert(image->signature == MagickSignature);
1069 if (image->debug != MagickFalse)
1070 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1071 assert(exception != (ExceptionInfo *) NULL);
1072 assert(exception->signature == MagickSignature);
1073 for (next=image; next != (Image *) NULL; next=GetNextImageInList(next))
1075 if ((next->columns != image->columns) || (next->rows != image->rows))
1076 ThrowImageException(OptionError,"ImagesAreNotTheSameSize");
1078 combine_image=CloneImage(image,0,0,MagickTrue,exception);
1079 if (combine_image == (Image *) NULL)
1080 return((Image *) NULL);
1081 if (SetImageStorageClass(combine_image,DirectClass) == MagickFalse)
1083 InheritException(exception,&combine_image->exception);
1084 combine_image=DestroyImage(combine_image);
1085 return((Image *) NULL);
1087 if ((channel & OpacityChannel) != 0)
1088 combine_image->matte=MagickTrue;
1089 (void) SetImageBackgroundColor(combine_image);
1095 combine_view=AcquireCacheView(combine_image);
1096 #if defined(MAGICKCORE_OPENMP_SUPPORT)
1097 #pragma omp parallel for schedule(dynamic,4) shared(progress,status)
1099 for (y=0; y < (long) combine_image->rows; y++)
1110 register const PixelPacket
1116 register PixelPacket
1119 if (status == MagickFalse)
1121 pixels=GetCacheViewAuthenticPixels(combine_view,0,y,combine_image->columns,
1123 if (pixels == (PixelPacket *) NULL)
1129 if (((channel & RedChannel) != 0) && (next != (Image *) NULL))
1131 image_view=AcquireCacheView(next);
1132 p=GetCacheViewVirtualPixels(image_view,0,y,next->columns,1,exception);
1133 if (p == (const PixelPacket *) NULL)
1136 for (x=0; x < (long) combine_image->columns; x++)
1138 SetRedPixelComponent(q,PixelIntensityToQuantum(p));
1142 image_view=DestroyCacheView(image_view);
1143 next=GetNextImageInList(next);
1145 if (((channel & GreenChannel) != 0) && (next != (Image *) NULL))
1147 image_view=AcquireCacheView(next);
1148 p=GetCacheViewVirtualPixels(image_view,0,y,next->columns,1,exception);
1149 if (p == (const PixelPacket *) NULL)
1152 for (x=0; x < (long) combine_image->columns; x++)
1154 SetGreenPixelComponent(q,PixelIntensityToQuantum(p));
1158 image_view=DestroyCacheView(image_view);
1159 next=GetNextImageInList(next);
1161 if (((channel & BlueChannel) != 0) && (next != (Image *) NULL))
1163 image_view=AcquireCacheView(next);
1164 p=GetCacheViewVirtualPixels(image_view,0,y,next->columns,1,exception);
1165 if (p == (const PixelPacket *) NULL)
1168 for (x=0; x < (long) combine_image->columns; x++)
1170 SetBluePixelComponent(q,PixelIntensityToQuantum(p));
1174 image_view=DestroyCacheView(image_view);
1175 next=GetNextImageInList(next);
1177 if (((channel & OpacityChannel) != 0) && (next != (Image *) NULL))
1179 image_view=AcquireCacheView(next);
1180 p=GetCacheViewVirtualPixels(image_view,0,y,next->columns,1,exception);
1181 if (p == (const PixelPacket *) NULL)
1184 for (x=0; x < (long) combine_image->columns; x++)
1186 SetOpacityPixelComponent(q,PixelIntensityToQuantum(p));
1190 image_view=DestroyCacheView(image_view);
1191 next=GetNextImageInList(next);
1193 if (((channel & IndexChannel) != 0) &&
1194 (image->colorspace == CMYKColorspace) && (next != (Image *) NULL))
1199 image_view=AcquireCacheView(next);
1200 p=GetCacheViewVirtualPixels(image_view,0,y,next->columns,1,exception);
1201 if (p == (const PixelPacket *) NULL)
1203 indexes=GetCacheViewAuthenticIndexQueue(combine_view);
1204 for (x=0; x < (long) combine_image->columns; x++)
1206 indexes[x]=PixelIntensityToQuantum(p);
1209 image_view=DestroyCacheView(image_view);
1210 next=GetNextImageInList(next);
1212 if (SyncCacheViewAuthenticPixels(combine_view,exception) == MagickFalse)
1214 if (image->progress_monitor != (MagickProgressMonitor) NULL)
1219 #if defined(MAGICKCORE_OPENMP_SUPPORT)
1220 #pragma omp critical (MagickCore_CombineImages)
1222 proceed=SetImageProgress(image,CombineImageTag,progress++,
1223 combine_image->rows);
1224 if (proceed == MagickFalse)
1228 combine_view=DestroyCacheView(combine_view);
1229 if (status == MagickFalse)
1230 combine_image=DestroyImage(combine_image);
1231 return(combine_image);
1235 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1239 % D e s t r o y I m a g e %
1243 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1245 % DestroyImage() dereferences an image, deallocating memory associated with
1246 % the image if the reference count becomes zero.
1248 % The format of the DestroyImage method is:
1250 % Image *DestroyImage(Image *image)
1252 % A description of each parameter follows:
1254 % o image: the image.
1257 MagickExport Image *DestroyImage(Image *image)
1265 assert(image != (Image *) NULL);
1266 assert(image->signature == MagickSignature);
1267 if (image->debug != MagickFalse)
1268 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1269 destroy=MagickFalse;
1270 LockSemaphoreInfo(image->semaphore);
1271 image->reference_count--;
1272 if (image->reference_count == 0)
1274 UnlockSemaphoreInfo(image->semaphore);
1275 if (destroy == MagickFalse)
1276 return((Image *) NULL);
1280 DestroyImagePixels(image);
1281 if (image->clip_mask != (Image *) NULL)
1282 image->clip_mask=DestroyImage(image->clip_mask);
1283 if (image->mask != (Image *) NULL)
1284 image->mask=DestroyImage(image->mask);
1285 if (image->montage != (char *) NULL)
1286 image->montage=DestroyString(image->montage);
1287 if (image->directory != (char *) NULL)
1288 image->directory=DestroyString(image->directory);
1289 if (image->colormap != (PixelPacket *) NULL)
1290 image->colormap=(PixelPacket *) RelinquishMagickMemory(image->colormap);
1291 if (image->geometry != (char *) NULL)
1292 image->geometry=DestroyString(image->geometry);
1293 DestroyImageProfiles(image);
1294 DestroyImageProperties(image);
1295 DestroyImageArtifacts(image);
1296 if (image->ascii85 != (Ascii85Info*) NULL)
1297 image->ascii85=(Ascii85Info *) RelinquishMagickMemory(image->ascii85);
1299 (void) DestroyExceptionInfo(&image->exception);
1300 if (image->semaphore != (SemaphoreInfo *) NULL)
1301 DestroySemaphoreInfo(&image->semaphore);
1302 image->signature=(~MagickSignature);
1303 image=(Image *) RelinquishMagickMemory(image);
1308 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1312 % D e s t r o y I m a g e I n f o %
1316 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1318 % DestroyImageInfo() deallocates memory associated with an ImageInfo
1321 % The format of the DestroyImageInfo method is:
1323 % ImageInfo *DestroyImageInfo(ImageInfo *image_info)
1325 % A description of each parameter follows:
1327 % o image_info: the image info.
1330 MagickExport ImageInfo *DestroyImageInfo(ImageInfo *image_info)
1332 assert(image_info != (ImageInfo *) NULL);
1333 assert(image_info->signature == MagickSignature);
1334 if (image_info->debug != MagickFalse)
1335 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
1336 image_info->filename);
1337 if (image_info->size != (char *) NULL)
1338 image_info->size=DestroyString(image_info->size);
1339 if (image_info->extract != (char *) NULL)
1340 image_info->extract=DestroyString(image_info->extract);
1341 if (image_info->scenes != (char *) NULL)
1342 image_info->scenes=DestroyString(image_info->scenes);
1343 if (image_info->page != (char *) NULL)
1344 image_info->page=DestroyString(image_info->page);
1345 if (image_info->sampling_factor != (char *) NULL)
1346 image_info->sampling_factor=DestroyString(
1347 image_info->sampling_factor);
1348 if (image_info->server_name != (char *) NULL)
1349 image_info->server_name=DestroyString(
1350 image_info->server_name);
1351 if (image_info->font != (char *) NULL)
1352 image_info->font=DestroyString(image_info->font);
1353 if (image_info->texture != (char *) NULL)
1354 image_info->texture=DestroyString(image_info->texture);
1355 if (image_info->density != (char *) NULL)
1356 image_info->density=DestroyString(image_info->density);
1357 if (image_info->view != (char *) NULL)
1358 image_info->view=DestroyString(image_info->view);
1359 if (image_info->authenticate != (char *) NULL)
1360 image_info->authenticate=DestroyString(
1361 image_info->authenticate);
1362 DestroyImageOptions(image_info);
1363 if (image_info->cache != (void *) NULL)
1364 image_info->cache=DestroyPixelCache(image_info->cache);
1365 if (image_info->profile != (StringInfo *) NULL)
1366 image_info->profile=(void *) DestroyStringInfo((StringInfo *)
1367 image_info->profile);
1368 image_info->signature=(~MagickSignature);
1369 image_info=(ImageInfo *) RelinquishMagickMemory(image_info);
1374 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1378 + D i s a s s o c i a t e I m a g e S t r e a m %
1382 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1384 % DisassociateImageStream() disassociates the image stream.
1386 % The format of the DisassociateImageStream method is:
1388 % MagickBooleanType DisassociateImageStream(const Image *image)
1390 % A description of each parameter follows:
1392 % o image: the image.
1395 MagickExport void DisassociateImageStream(Image *image)
1397 assert(image != (const Image *) NULL);
1398 assert(image->signature == MagickSignature);
1399 if (image->debug != MagickFalse)
1400 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1401 (void) DetachBlob(image->blob);
1405 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1409 % G e t I m a g e A l p h a C h a n n e l %
1413 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1415 % GetImageAlphaChannel() returns MagickFalse if the image alpha channel is
1416 % not activated. That is, the image is RGB rather than RGBA or CMYK rather
1419 % The format of the GetImageAlphaChannel method is:
1421 % MagickBooleanType GetImageAlphaChannel(const Image *image)
1423 % A description of each parameter follows:
1425 % o image: the image.
1428 MagickExport MagickBooleanType GetImageAlphaChannel(const Image *image)
1430 assert(image != (const Image *) NULL);
1431 if (image->debug != MagickFalse)
1432 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1433 assert(image->signature == MagickSignature);
1434 return(image->matte);
1438 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1442 % G e t I m a g e C l i p M a s k %
1446 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1448 % GetImageClipMask() returns the clip path associated with the image.
1450 % The format of the GetImageClipMask method is:
1452 % Image *GetImageClipMask(const Image *image,ExceptionInfo *exception)
1454 % A description of each parameter follows:
1456 % o image: the image.
1459 MagickExport Image *GetImageClipMask(const Image *image,
1460 ExceptionInfo *exception)
1462 assert(image != (const Image *) NULL);
1463 if (image->debug != MagickFalse)
1464 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1465 assert(image->signature == MagickSignature);
1466 if (image->clip_mask == (Image *) NULL)
1467 return((Image *) NULL);
1468 return(CloneImage(image->clip_mask,0,0,MagickTrue,exception));
1472 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1476 % G e t I m a g e E x c e p t i o n %
1480 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1482 % GetImageException() traverses an image sequence and returns any
1483 % error more severe than noted by the exception parameter.
1485 % The format of the GetImageException method is:
1487 % void GetImageException(Image *image,ExceptionInfo *exception)
1489 % A description of each parameter follows:
1491 % o image: Specifies a pointer to a list of one or more images.
1493 % o exception: return the highest severity exception.
1496 MagickExport void GetImageException(Image *image,ExceptionInfo *exception)
1501 assert(image != (Image *) NULL);
1502 assert(image->signature == MagickSignature);
1503 if (image->debug != MagickFalse)
1504 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1505 assert(exception != (ExceptionInfo *) NULL);
1506 assert(exception->signature == MagickSignature);
1507 for (next=image; next != (Image *) NULL; next=GetNextImageInList(next))
1509 if (next->exception.severity == UndefinedException)
1511 if (next->exception.severity > exception->severity)
1512 InheritException(exception,&next->exception);
1513 next->exception.severity=UndefinedException;
1518 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1522 % G e t I m a g e I n f o %
1526 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1528 % GetImageInfo() initializes image_info to default values.
1530 % The format of the GetImageInfo method is:
1532 % void GetImageInfo(ImageInfo *image_info)
1534 % A description of each parameter follows:
1536 % o image_info: the image info.
1539 MagickExport void GetImageInfo(ImageInfo *image_info)
1545 File and image dimension members.
1547 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1548 assert(image_info != (ImageInfo *) NULL);
1549 (void) ResetMagickMemory(image_info,0,sizeof(*image_info));
1550 image_info->adjoin=MagickTrue;
1551 image_info->interlace=NoInterlace;
1552 image_info->channel=DefaultChannels;
1553 image_info->quality=UndefinedCompressionQuality;
1554 image_info->antialias=MagickTrue;
1555 image_info->dither=MagickTrue;
1556 exception=AcquireExceptionInfo();
1557 (void) QueryColorDatabase(BackgroundColor,&image_info->background_color,
1559 (void) QueryColorDatabase(BorderColor,&image_info->border_color,exception);
1560 (void) QueryColorDatabase(MatteColor,&image_info->matte_color,exception);
1561 (void) QueryColorDatabase(TransparentColor,&image_info->transparent_color,
1563 exception=DestroyExceptionInfo(exception);
1564 image_info->debug=IsEventLogging();
1565 image_info->signature=MagickSignature;
1569 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1573 % G e t I m a g e I n f o F i l e %
1577 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1579 % GetImageInfoFile() returns the image info file member.
1581 % The format of the GetImageInfoFile method is:
1583 % FILE *GetImageInfoFile(const ImageInfo *image_info)
1585 % A description of each parameter follows:
1587 % o image_info: the image info.
1590 MagickExport FILE *GetImageInfoFile(const ImageInfo *image_info)
1592 return(image_info->file);
1596 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1600 % G e t I m a g e M a s k %
1604 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1606 % GetImageMask() returns the mask associated with the image.
1608 % The format of the GetImageMask method is:
1610 % Image *GetImageMask(const Image *image,ExceptionInfo *exception)
1612 % A description of each parameter follows:
1614 % o image: the image.
1617 MagickExport Image *GetImageMask(const Image *image,ExceptionInfo *exception)
1619 assert(image != (const Image *) NULL);
1620 if (image->debug != MagickFalse)
1621 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1622 assert(image->signature == MagickSignature);
1623 if (image->mask == (Image *) NULL)
1624 return((Image *) NULL);
1625 return(CloneImage(image->mask,0,0,MagickTrue,exception));
1629 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1633 + G e t I m a g e R e f e r e n c e C o u n t %
1637 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1639 % GetImageReferenceCount() returns the image reference count.
1641 % The format of the GetReferenceCount method is:
1643 % long GetImageReferenceCount(Image *image)
1645 % A description of each parameter follows:
1647 % o image: the image.
1650 MagickExport long GetImageReferenceCount(Image *image)
1655 assert(image != (Image *) NULL);
1656 assert(image->signature == MagickSignature);
1657 if (image->debug != MagickFalse)
1658 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1659 LockSemaphoreInfo(image->semaphore);
1660 reference_count=image->reference_count;
1661 UnlockSemaphoreInfo(image->semaphore);
1662 return(reference_count);
1666 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1670 % 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 %
1674 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1676 % GetImageVirtualPixelMethod() gets the "virtual pixels" method for the
1677 % image. A virtual pixel is any pixel access that is outside the boundaries
1678 % of the image cache.
1680 % The format of the GetImageVirtualPixelMethod() method is:
1682 % VirtualPixelMethod GetImageVirtualPixelMethod(const Image *image)
1684 % A description of each parameter follows:
1686 % o image: the image.
1689 MagickExport VirtualPixelMethod GetImageVirtualPixelMethod(const Image *image)
1691 assert(image != (Image *) NULL);
1692 assert(image->signature == MagickSignature);
1693 if (image->debug != MagickFalse)
1694 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1695 return(GetPixelCacheVirtualMethod(image));
1699 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1703 % I n t e r p r e t I m a g e F i l e n a m e %
1707 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1709 % InterpretImageFilename() interprets embedded characters in an image filename.
1710 % The filename length is returned.
1712 % The format of the InterpretImageFilename method is:
1714 % size_t InterpretImageFilename(const ImageInfo *image_info,
1715 % Image *image,const char *format,int value,char *filename)
1717 % A description of each parameter follows.
1719 % o image_info: the image info..
1721 % o image: the image.
1723 % o format: A filename describing the format to use to write the numeric
1724 % argument. Only the first numeric format identifier is replaced.
1726 % o value: Numeric value to substitute into format filename.
1728 % o filename: return the formatted filename in this character buffer.
1731 MagickExport size_t InterpretImageFilename(const ImageInfo *image_info,
1732 Image *image,const char *format,int value,char *filename)
1746 canonical=MagickFalse;
1747 (void) CopyMagickString(filename,format,MaxTextExtent);
1748 for (p=strchr(format,'%'); p != (char *) NULL; p=strchr(p+1,'%'))
1761 value=strtol(q,&q,10);
1772 (void) FormatMagickString(filename+(p-format),(size_t) (MaxTextExtent-
1773 (p-format)),p,value);
1775 (void) ConcatenateMagickString(filename,q,MaxTextExtent);
1776 canonical=MagickTrue;
1785 pattern[MaxTextExtent];
1802 if (strchr(p,']') == (char *) NULL)
1806 for (i=0; (i < (MaxTextExtent-1L)) && (*r != '\0'); i++)
1817 if (LocaleNCompare(pattern,"filename:",9) != 0)
1819 value=(const char *) NULL;
1820 if ((image_info != (const ImageInfo *) NULL) &&
1821 (image != (const Image *) NULL))
1822 value=GetMagickProperty(image_info,image,pattern);
1824 if (image != (Image *) NULL)
1825 value=GetImageProperty(image,pattern);
1827 if (image_info != (ImageInfo *) NULL)
1828 value=GetImageOption(image_info,pattern);
1829 if (value == (const char *) NULL)
1834 (void) CopyMagickString(filename+(p-format),value,(size_t)
1835 (MaxTextExtent-(p-format)));
1837 (void) ConcatenateMagickString(filename,r+1,MaxTextExtent);
1838 canonical=MagickTrue;
1848 for (q=filename; *q != '\0'; q++)
1849 if ((*q == '%') && (*(q+1) == '%'))
1850 (void) CopyMagickString(q,q+1,(size_t) (MaxTextExtent-(q-filename)));
1851 if (canonical == MagickFalse)
1852 (void) CopyMagickString(filename,format,MaxTextExtent);
1853 return(strlen(filename));
1857 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1861 % I s H i g h D y n a m i c R a n g e I m a g e %
1865 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1867 % IsHighDynamicRangeImage() returns MagickTrue if any pixel component is
1868 % non-integer or exceeds the bounds of the quantum depth (e.g. for Q16
1871 % The format of the IsHighDynamicRangeImage method is:
1873 % MagickBooleanType IsHighDynamicRangeImage(const Image *image,
1874 % ExceptionInfo *exception)
1876 % A description of each parameter follows:
1878 % o image: the image.
1880 % o exception: return any errors or warnings in this structure.
1883 MagickExport MagickBooleanType IsHighDynamicRangeImage(const Image *image,
1884 ExceptionInfo *exception)
1886 #if !defined(MAGICKCORE_HDRI_SUPPORT)
1889 return(MagickFalse);
1903 assert(image != (Image *) NULL);
1904 assert(image->signature == MagickSignature);
1905 if (image->debug != MagickFalse)
1906 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
1908 GetMagickPixelPacket(image,&zero);
1909 image_view=AcquireCacheView(image);
1910 #if defined(MAGICKCORE_OPENMP_SUPPORT)
1911 #pragma omp parallel for schedule(dynamic,4) shared(status)
1913 for (y=0; y < (long) image->rows; y++)
1918 register const IndexPacket
1921 register const PixelPacket
1927 if (status == MagickFalse)
1929 p=GetCacheViewVirtualPixels(image_view,0,y,image->columns,1,exception);
1930 if (p == (const PixelPacket *) NULL)
1935 indexes=GetCacheViewVirtualIndexQueue(image_view);
1937 for (x=0; x < (long) image->columns; x++)
1939 SetMagickPixelPacket(image,p,indexes+x,&pixel);
1940 if ((pixel.red < 0.0) || (pixel.red > QuantumRange) ||
1941 (pixel.red != (QuantumAny) pixel.red))
1943 if ((pixel.green < 0.0) || (pixel.green > QuantumRange) ||
1944 (pixel.green != (QuantumAny) pixel.green))
1946 if ((pixel.blue < 0.0) || (pixel.blue > QuantumRange) ||
1947 (pixel.blue != (QuantumAny) pixel.blue))
1949 if (pixel.matte != MagickFalse)
1951 if ((pixel.opacity < 0.0) || (pixel.opacity > QuantumRange) ||
1952 (pixel.opacity != (QuantumAny) pixel.opacity))
1955 if (pixel.colorspace == CMYKColorspace)
1957 if ((pixel.index < 0.0) || (pixel.index > QuantumRange) ||
1958 (pixel.index != (QuantumAny) pixel.index))
1963 if (x < (long) image->columns)
1966 image_view=DestroyCacheView(image_view);
1967 return(status != MagickFalse ? MagickFalse : MagickTrue);
1972 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1976 % I s I m a g e O b j e c t %
1980 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1982 % IsImageObject() returns MagickTrue if the image sequence contains a valid
1983 % set of image objects.
1985 % The format of the IsImageObject method is:
1987 % MagickBooleanType IsImageObject(const Image *image)
1989 % A description of each parameter follows:
1991 % o image: the image.
1994 MagickExport MagickBooleanType IsImageObject(const Image *image)
1996 register const Image
1999 assert(image != (Image *) NULL);
2000 if (image->debug != MagickFalse)
2001 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2002 for (p=image; p != (Image *) NULL; p=GetNextImageInList(p))
2003 if (p->signature != MagickSignature)
2004 return(MagickFalse);
2009 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2013 % I s T a i n t I m a g e %
2017 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2019 % IsTaintImage() returns MagickTrue any pixel in the image has been altered
2020 % since it was first constituted.
2022 % The format of the IsTaintImage method is:
2024 % MagickBooleanType IsTaintImage(const Image *image)
2026 % A description of each parameter follows:
2028 % o image: the image.
2031 MagickExport MagickBooleanType IsTaintImage(const Image *image)
2034 magick[MaxTextExtent],
2035 filename[MaxTextExtent];
2037 register const Image
2040 assert(image != (Image *) NULL);
2041 if (image->debug != MagickFalse)
2042 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2043 assert(image->signature == MagickSignature);
2044 (void) CopyMagickString(magick,image->magick,MaxTextExtent);
2045 (void) CopyMagickString(filename,image->filename,MaxTextExtent);
2046 for (p=image; p != (Image *) NULL; p=GetNextImageInList(p))
2048 if (p->taint != MagickFalse)
2050 if (LocaleCompare(p->magick,magick) != 0)
2052 if (LocaleCompare(p->filename,filename) != 0)
2055 return(MagickFalse);
2059 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2063 % M o d i f y I m a g e %
2067 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2069 % ModifyImage() ensures that there is only a single reference to the image
2070 % to be modified, updating the provided image pointer to point to a clone of
2071 % the original image if necessary.
2073 % The format of the ModifyImage method is:
2075 % MagickBooleanType ModifyImage(Image *image,ExceptionInfo *exception)
2077 % A description of each parameter follows:
2079 % o image: the image.
2081 % o exception: return any errors or warnings in this structure.
2084 MagickExport MagickBooleanType ModifyImage(Image **image,
2085 ExceptionInfo *exception)
2090 assert(image != (Image **) NULL);
2091 assert(*image != (Image *) NULL);
2092 assert((*image)->signature == MagickSignature);
2093 if ((*image)->debug != MagickFalse)
2094 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",(*image)->filename);
2095 if (GetImageReferenceCount(*image) <= 1)
2097 clone_image=CloneImage(*image,0,0,MagickTrue,exception);
2098 LockSemaphoreInfo((*image)->semaphore);
2099 (*image)->reference_count--;
2100 UnlockSemaphoreInfo((*image)->semaphore);
2106 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2110 % N e w M a g i c k I m a g e %
2114 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2116 % NewMagickImage() creates a blank image canvas of the specified size and
2119 % The format of the NewMagickImage method is:
2121 % Image *NewMagickImage(const ImageInfo *image_info,
2122 % const unsigned long width,const unsigned long height,
2123 % const MagickPixelPacket *background)
2125 % A description of each parameter follows:
2127 % o image: the image.
2129 % o width: the image width.
2131 % o height: the image height.
2133 % o background: the image color.
2136 MagickExport Image *NewMagickImage(const ImageInfo *image_info,
2137 const unsigned long width,const unsigned long height,
2138 const MagickPixelPacket *background)
2155 assert(image_info != (const ImageInfo *) NULL);
2156 if (image_info->debug != MagickFalse)
2157 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2158 assert(image_info->signature == MagickSignature);
2159 assert(background != (const MagickPixelPacket *) NULL);
2160 image=AcquireImage(image_info);
2161 image->columns=width;
2163 image->colorspace=background->colorspace;
2164 image->matte=background->matte;
2165 image->fuzz=background->fuzz;
2166 image->depth=background->depth;
2168 exception=(&image->exception);
2169 image_view=AcquireCacheView(image);
2170 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2171 #pragma omp parallel for schedule(dynamic,4) shared(status)
2173 for (y=0; y < (long) image->rows; y++)
2175 register IndexPacket
2181 register PixelPacket
2184 if (status == MagickFalse)
2186 q=QueueCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2187 if (q == (PixelPacket *) NULL)
2192 indexes=GetCacheViewAuthenticIndexQueue(image_view);
2193 for (x=0; x < (long) image->columns; x++)
2195 SetPixelPacket(image,background,q,indexes+x);
2198 if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2201 image_view=DestroyCacheView(image_view);
2202 if (status == MagickFalse)
2203 image=DestroyImage(image);
2208 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2212 % R e f e r e n c e I m a g e %
2216 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2218 % ReferenceImage() increments the reference count associated with an image
2219 % returning a pointer to the image.
2221 % The format of the ReferenceImage method is:
2223 % Image *ReferenceImage(Image *image)
2225 % A description of each parameter follows:
2227 % o image: the image.
2230 MagickExport Image *ReferenceImage(Image *image)
2232 assert(image != (Image *) NULL);
2233 if (image->debug != MagickFalse)
2234 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2235 assert(image->signature == MagickSignature);
2236 LockSemaphoreInfo(image->semaphore);
2237 image->reference_count++;
2238 UnlockSemaphoreInfo(image->semaphore);
2243 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2247 % R e s e t I m a g e P a g e %
2251 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2253 % ResetImagePage() resets the image page canvas and position.
2255 % The format of the ResetImagePage method is:
2257 % MagickBooleanType ResetImagePage(Image *image,const char *page)
2259 % A description of each parameter follows:
2261 % o image: the image.
2263 % o page: the relative page specification.
2266 MagickExport MagickBooleanType ResetImagePage(Image *image,const char *page)
2274 assert(image != (Image *) NULL);
2275 assert(image->signature == MagickSignature);
2276 if (image->debug != MagickFalse)
2277 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
2278 flags=ParseAbsoluteGeometry(page,&geometry);
2279 if ((flags & WidthValue) != 0)
2281 if ((flags & HeightValue) == 0)
2282 geometry.height=geometry.width;
2283 image->page.width=geometry.width;
2284 image->page.height=geometry.height;
2286 if ((flags & AspectValue) != 0)
2288 if ((flags & XValue) != 0)
2289 image->page.x+=geometry.x;
2290 if ((flags & YValue) != 0)
2291 image->page.y+=geometry.y;
2295 if ((flags & XValue) != 0)
2297 image->page.x=geometry.x;
2298 if ((image->page.width == 0) && (geometry.x > 0))
2299 image->page.width=image->columns+geometry.x;
2301 if ((flags & YValue) != 0)
2303 image->page.y=geometry.y;
2304 if ((image->page.height == 0) && (geometry.y > 0))
2305 image->page.height=image->rows+geometry.y;
2312 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2316 % S e p a r a t e I m a g e C h a n n e l %
2320 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2322 % SeparateImageChannel() separates a channel from the image and returns it as
2323 % a grayscale image. A channel is a particular color component of each pixel
2326 % The format of the SeparateImageChannel method is:
2328 % MagickBooleanType SeparateImageChannel(Image *image,
2329 % const ChannelType channel)
2331 % A description of each parameter follows:
2333 % o image: the image.
2335 % o channel: Identify which channel to extract: RedChannel, GreenChannel,
2336 % BlueChannel, OpacityChannel, CyanChannel, MagentaChannel,
2337 % YellowChannel, or BlackChannel.
2340 MagickExport MagickBooleanType SeparateImageChannel(Image *image,
2341 const ChannelType channel)
2343 #define SeparateImageTag "Separate/Image"
2358 assert(image != (Image *) NULL);
2359 assert(image->signature == MagickSignature);
2360 if (image->debug != MagickFalse)
2361 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
2362 if (SetImageStorageClass(image,DirectClass) == MagickFalse)
2363 return(MagickFalse);
2365 Separate image channels.
2368 if (channel == GrayChannels)
2369 image->matte=MagickTrue;
2371 exception=(&image->exception);
2372 image_view=AcquireCacheView(image);
2373 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2374 #pragma omp parallel for schedule(dynamic,4) shared(progress,status)
2376 for (y=0; y < (long) image->rows; y++)
2378 register IndexPacket
2384 register PixelPacket
2387 if (status == MagickFalse)
2389 q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2390 if (q == (PixelPacket *) NULL)
2395 indexes=GetCacheViewAuthenticIndexQueue(image_view);
2400 for (x=0; x < (long) image->columns; x++)
2410 for (x=0; x < (long) image->columns; x++)
2420 for (x=0; x < (long) image->columns; x++)
2428 case OpacityChannel:
2430 for (x=0; x < (long) image->columns; x++)
2433 q->green=q->opacity;
2441 if ((image->storage_class != PseudoClass) &&
2442 (image->colorspace != CMYKColorspace))
2444 for (x=0; x < (long) image->columns; x++)
2447 q->green=indexes[x];
2453 case TrueAlphaChannel:
2455 for (x=0; x < (long) image->columns; x++)
2457 q->red=(Quantum) GetAlphaPixelComponent(q);
2458 q->green=(Quantum) GetAlphaPixelComponent(q);
2459 q->blue=(Quantum) GetAlphaPixelComponent(q);
2466 for (x=0; x < (long) image->columns; x++)
2468 q->opacity=(Quantum) (QuantumRange-PixelIntensityToQuantum(q));
2476 if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2478 if (image->progress_monitor != (MagickProgressMonitor) NULL)
2483 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2484 #pragma omp critical (MagickCore_SeparateImageChannel)
2486 proceed=SetImageProgress(image,SeparateImageTag,progress++,image->rows);
2487 if (proceed == MagickFalse)
2491 image_view=DestroyCacheView(image_view);
2492 if (channel != GrayChannels)
2493 image->matte=MagickFalse;
2494 (void) SetImageColorspace(image,RGBColorspace);
2499 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2503 % S e p a r a t e I m a g e s %
2507 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2509 % SeparateImages() returns a separate grayscale image for each channel
2512 % The format of the SeparateImages method is:
2514 % MagickBooleanType SeparateImages(const Image *image,
2515 % const ChannelType channel,ExceptionInfo *exception)
2517 % A description of each parameter follows:
2519 % o image: the image.
2521 % o channel: Identify which channels to extract: RedChannel, GreenChannel,
2522 % BlueChannel, OpacityChannel, CyanChannel, MagentaChannel,
2523 % YellowChannel, or BlackChannel.
2525 % o exception: return any errors or warnings in this structure.
2528 MagickExport Image *SeparateImages(const Image *image,const ChannelType channel,
2529 ExceptionInfo *exception)
2535 assert(image != (Image *) NULL);
2536 assert(image->signature == MagickSignature);
2537 if (image->debug != MagickFalse)
2538 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
2539 images=NewImageList();
2540 if ((channel & RedChannel) != 0)
2542 separate_image=CloneImage(image,0,0,MagickTrue,exception);
2543 (void) SeparateImageChannel(separate_image,RedChannel);
2544 AppendImageToList(&images,separate_image);
2546 if ((channel & GreenChannel) != 0)
2548 separate_image=CloneImage(image,0,0,MagickTrue,exception);
2549 (void) SeparateImageChannel(separate_image,GreenChannel);
2550 AppendImageToList(&images,separate_image);
2552 if ((channel & BlueChannel) != 0)
2554 separate_image=CloneImage(image,0,0,MagickTrue,exception);
2555 (void) SeparateImageChannel(separate_image,BlueChannel);
2556 AppendImageToList(&images,separate_image);
2558 if (((channel & BlackChannel) != 0) && (image->colorspace == CMYKColorspace))
2560 separate_image=CloneImage(image,0,0,MagickTrue,exception);
2561 (void) SeparateImageChannel(separate_image,BlackChannel);
2562 AppendImageToList(&images,separate_image);
2564 if ((channel & OpacityChannel) != 0)
2566 separate_image=CloneImage(image,0,0,MagickTrue,exception);
2567 (void) SeparateImageChannel(separate_image,OpacityChannel);
2568 AppendImageToList(&images,separate_image);
2574 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2578 % S e t I m a g e A l p h a C h a n n e l %
2582 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2584 % SetImageAlphaChannel() activates, deactivates, resets, or sets the alpha
2587 % The format of the SetImageAlphaChannel method is:
2589 % MagickBooleanType SetImageAlphaChannel(Image *image,
2590 % const AlphaChannelType alpha_type)
2592 % A description of each parameter follows:
2594 % o image: the image.
2596 % o alpha_type: The alpha channel type: ActivateAlphaChannel,
2597 % CopyAlphaChannel, DeactivateAlphaChannel, ExtractAlphaChannel,
2598 % OpaqueAlphaChannel, ResetAlphaChannel, SetAlphaChannel,
2599 % ShapeAlphaChannel, and TransparentAlphaChannel.
2602 MagickExport MagickBooleanType SetImageAlphaChannel(Image *image,
2603 const AlphaChannelType alpha_type)
2608 assert(image != (Image *) NULL);
2609 if (image->debug != MagickFalse)
2610 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2611 assert(image->signature == MagickSignature);
2615 case ActivateAlphaChannel:
2617 image->matte=MagickTrue;
2620 case BackgroundAlphaChannel:
2644 Set transparent pixels to background color.
2646 if (image->matte == MagickFalse)
2648 if (SetImageStorageClass(image,DirectClass) == MagickFalse)
2650 GetMagickPixelPacket(image,&background);
2651 SetMagickPixelPacket(image,&image->background_color,(const IndexPacket *)
2653 if (image->colorspace == CMYKColorspace)
2654 ConvertRGBToCMYK(&background);
2656 SetPixelPacket(image,&background,&pixel,&index);
2658 exception=(&image->exception);
2659 image_view=AcquireCacheView(image);
2660 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2661 #pragma omp parallel for schedule(dynamic,4) shared(status)
2663 for (y=0; y < (long) image->rows; y++)
2665 register IndexPacket
2671 register PixelPacket
2674 if (status == MagickFalse)
2676 q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,
2678 if (q == (PixelPacket *) NULL)
2683 for (x=0; x < (long) image->columns; x++)
2685 if (q->opacity == TransparentOpacity)
2688 q->green=pixel.green;
2693 if (image->colorspace == CMYKColorspace)
2695 indexes=GetCacheViewAuthenticIndexQueue(image_view);
2696 for (x=0; x < (long) image->columns; x++)
2699 if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2702 image_view=DestroyCacheView(image_view);
2705 case DeactivateAlphaChannel:
2707 image->matte=MagickFalse;
2710 case ShapeAlphaChannel:
2711 case CopyAlphaChannel:
2714 Special usage case for SeparateImageChannel(): copy grayscale color to
2717 status=SeparateImageChannel(image,GrayChannels);
2718 image->matte=MagickTrue; /* make sure transparency is now on! */
2719 if (alpha_type == ShapeAlphaChannel)
2725 Reset all color channels to background color.
2727 GetMagickPixelPacket(image,&background);
2728 SetMagickPixelPacket(image,&(image->background_color),(IndexPacket *)
2730 (void) LevelColorsImage(image,&background,&background,MagickTrue);
2734 case ExtractAlphaChannel:
2736 status=SeparateImageChannel(image,TrueAlphaChannel);
2737 image->matte=MagickFalse;
2740 case ResetAlphaChannel:
2741 case OpaqueAlphaChannel:
2743 status=SetImageOpacity(image,OpaqueOpacity);
2744 image->matte=MagickTrue;
2747 case TransparentAlphaChannel:
2749 status=SetImageOpacity(image,TransparentOpacity);
2750 image->matte=MagickTrue;
2753 case SetAlphaChannel:
2755 if (image->matte == MagickFalse)
2757 status=SetImageOpacity(image,OpaqueOpacity);
2758 image->matte=MagickTrue;
2762 case UndefinedAlphaChannel:
2769 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2773 % S e t I m a g e B a c k g r o u n d C o l o r %
2777 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2779 % SetImageBackgroundColor() initializes the image pixels to the image
2780 % background color. The background color is defined by the background_color
2781 % member of the image structure.
2783 % The format of the SetImage method is:
2785 % MagickBooleanType SetImageBackgroundColor(Image *image)
2787 % A description of each parameter follows:
2789 % o image: the image.
2792 MagickExport MagickBooleanType SetImageBackgroundColor(Image *image)
2815 assert(image != (Image *) NULL);
2816 if (image->debug != MagickFalse)
2817 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2818 assert(image->signature == MagickSignature);
2819 if (SetImageStorageClass(image,DirectClass) == MagickFalse)
2820 return(MagickFalse);
2821 if (image->background_color.opacity != OpaqueOpacity)
2822 image->matte=MagickTrue;
2823 GetMagickPixelPacket(image,&background);
2824 SetMagickPixelPacket(image,&image->background_color,(const IndexPacket *)
2826 if (image->colorspace == CMYKColorspace)
2827 ConvertRGBToCMYK(&background);
2829 SetPixelPacket(image,&background,&pixel,&index);
2831 Set image background color.
2834 exception=(&image->exception);
2835 image_view=AcquireCacheView(image);
2836 #if defined(MAGICKCORE_OPENMP_SUPPORT)
2837 #pragma omp parallel for schedule(dynamic,4) shared(status)
2839 for (y=0; y < (long) image->rows; y++)
2841 register IndexPacket
2847 register PixelPacket
2850 if (status == MagickFalse)
2852 q=QueueCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
2853 if (q == (PixelPacket *) NULL)
2858 for (x=0; x < (long) image->columns; x++)
2860 if (image->colorspace == CMYKColorspace)
2862 indexes=GetCacheViewAuthenticIndexQueue(image_view);
2863 for (x=0; x < (long) image->columns; x++)
2866 if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
2869 image_view=DestroyCacheView(image_view);
2874 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2878 % S e t I m a g e S t o r a g e C l a s s %
2882 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2884 % SetImageStorageClass() sets the image class: DirectClass for true color
2885 % images or PseudoClass for colormapped images.
2887 % The format of the SetImageStorageClass method is:
2889 % MagickBooleanType SetImageStorageClass(Image *image,
2890 % const ClassType storage_class)
2892 % A description of each parameter follows:
2894 % o image: the image.
2896 % o storage_class: The image class.
2899 MagickExport MagickBooleanType SetImageStorageClass(Image *image,
2900 const ClassType storage_class)
2905 if (image->storage_class == storage_class)
2907 image->storage_class=storage_class;
2908 cache=GetImagePixelCache(image,MagickTrue,&image->exception);
2909 return(cache == (Cache) NULL ? MagickFalse : MagickTrue);
2913 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2917 % S e t I m a g e C l i p M a s k %
2921 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2923 % SetImageClipMask() associates a clip path with the image. The clip path
2924 % must be the same dimensions as the image. Set any pixel component of
2925 % the clip path to TransparentOpacity to prevent that corresponding image
2926 % pixel component from being updated when SyncAuthenticPixels() is applied.
2928 % The format of the SetImageClipMask method is:
2930 % MagickBooleanType SetImageClipMask(Image *image,const Image *clip_mask)
2932 % A description of each parameter follows:
2934 % o image: the image.
2936 % o clip_mask: the image clip path.
2939 MagickExport MagickBooleanType SetImageClipMask(Image *image,
2940 const Image *clip_mask)
2942 assert(image != (Image *) NULL);
2943 if (image->debug != MagickFalse)
2944 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
2945 assert(image->signature == MagickSignature);
2946 if (clip_mask != (const Image *) NULL)
2947 if ((clip_mask->columns != image->columns) ||
2948 (clip_mask->rows != image->rows))
2949 ThrowBinaryException(ImageError,"ImageSizeDiffers",image->filename);
2950 if (image->clip_mask != (Image *) NULL)
2951 image->clip_mask=DestroyImage(image->clip_mask);
2952 image->clip_mask=NewImageList();
2953 if (clip_mask == (Image *) NULL)
2955 if (SetImageStorageClass(image,DirectClass) == MagickFalse)
2956 return(MagickFalse);
2957 image->clip_mask=CloneImage(clip_mask,0,0,MagickTrue,&image->exception);
2958 if (image->clip_mask == (Image *) NULL)
2959 return(MagickFalse);
2964 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2968 % S e t I m a g e E x t e n t %
2972 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
2974 % SetImageExtent() sets the image size (i.e. columns & rows).
2976 % The format of the SetImageExtent method is:
2978 % MagickBooleanType SetImageExtent(Image *image,
2979 % const unsigned long columns,const unsigned long rows)
2981 % A description of each parameter follows:
2983 % o image: the image.
2985 % o columns: The image width in pixels.
2987 % o rows: The image height in pixels.
2990 MagickExport MagickBooleanType SetImageExtent(Image *image,
2991 const unsigned long columns,const unsigned long rows)
2996 if ((columns != 0) && (rows != 0))
2998 image->columns=columns;
3001 cache=GetImagePixelCache(image,MagickTrue,&image->exception);
3002 return(cache == (Cache) NULL ? MagickFalse : MagickTrue);
3006 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3010 + S e t I m a g e I n f o %
3014 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3016 % SetImageInfo() initializes the `magick' field of the ImageInfo structure.
3017 % It is set to a type of image format based on the prefix or suffix of the
3018 % filename. For example, `ps:image' returns PS indicating a Postscript image.
3019 % JPEG is returned for this filename: `image.jpg'. The filename prefix has
3020 % precendence over the suffix. Use an optional index enclosed in brackets
3021 % after a file name to specify a desired scene of a multi-resolution image
3022 % format like Photo CD (e.g. img0001.pcd[4]). A True (non-zero) return value
3023 % indicates success.
3025 % The format of the SetImageInfo method is:
3027 % MagickBooleanType SetImageInfo(ImageInfo *image_info,
3028 % const unsigned int frames,ExceptionInfo *exception)
3030 % A description of each parameter follows:
3032 % o image_info: the image info.
3034 % o frames: the number of images you intend to write.
3036 % o exception: return any errors or warnings in this structure.
3039 MagickExport MagickBooleanType SetImageInfo(ImageInfo *image_info,
3040 const unsigned int frames,ExceptionInfo *exception)
3043 extension[MaxTextExtent],
3044 filename[MaxTextExtent],
3045 magic[MaxTextExtent],
3047 subimage[MaxTextExtent];
3071 magick[2*MaxTextExtent];
3074 Look for 'image.format' in filename.
3076 assert(image_info != (ImageInfo *) NULL);
3077 assert(image_info->signature == MagickSignature);
3078 if (image_info->debug != MagickFalse)
3079 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
3080 image_info->filename);
3084 GetPathComponent(image_info->filename,SubimagePath,subimage);
3085 if (*subimage != '\0')
3088 Look for scene specification (e.g. img0001.pcd[4]).
3090 if (IsSceneGeometry(subimage,MagickFalse) == MagickFalse)
3092 if (IsGeometry(subimage) != MagickFalse)
3093 (void) CloneString(&image_info->extract,subimage);
3101 (void) CloneString(&image_info->scenes,subimage);
3102 image_info->scene=StringToUnsignedLong(image_info->scenes);
3103 image_info->number_scenes=image_info->scene;
3104 p=image_info->scenes;
3105 for (q=(char *) image_info->scenes; *q != '\0'; p++)
3107 while ((isspace((int) ((unsigned char) *p)) != 0) ||
3110 first=(unsigned long) strtol(p,&q,10);
3112 while (isspace((int) ((unsigned char) *q)) != 0)
3115 last=(unsigned long) strtol(q+1,&q,10);
3118 if (first < image_info->scene)
3119 image_info->scene=first;
3120 if (last > image_info->number_scenes)
3121 image_info->number_scenes=last;
3124 image_info->number_scenes-=image_info->scene-1;
3125 image_info->subimage=image_info->scene;
3126 image_info->subrange=image_info->number_scenes;
3131 GetPathComponent(image_info->filename,ExtensionPath,extension);
3132 #if defined(MAGICKCORE_ZLIB_DELEGATE)
3133 if (*extension != '\0')
3134 if ((LocaleCompare(extension,"gz") == 0) ||
3135 (LocaleCompare(extension,"Z") == 0) ||
3136 (LocaleCompare(extension,"wmz") == 0))
3139 path[MaxTextExtent];
3141 (void) CopyMagickString(path,image_info->filename,MaxTextExtent);
3142 path[strlen(path)-strlen(extension)-1]='\0';
3143 GetPathComponent(path,ExtensionPath,extension);
3146 #if defined(MAGICKCORE_BZLIB_DELEGATE)
3147 if (*extension != '\0')
3148 if (LocaleCompare(extension,"bz2") == 0)
3151 path[MaxTextExtent];
3153 (void) CopyMagickString(path,image_info->filename,MaxTextExtent);
3154 path[strlen(path)-strlen(extension)-1]='\0';
3155 GetPathComponent(path,ExtensionPath,extension);
3158 image_info->affirm=MagickFalse;
3159 sans_exception=AcquireExceptionInfo();
3160 if (*extension != '\0')
3169 *format_type_formats[] =
3192 User specified image format.
3194 (void) CopyMagickString(magic,extension,MaxTextExtent);
3197 Look for explicit image formats.
3199 format_type=UndefinedFormatType;
3201 while ((format_type == UndefinedFormatType) &&
3202 (format_type_formats[i] != (char *) NULL))
3204 if ((*magic == *format_type_formats[i]) &&
3205 (LocaleCompare(magic,format_type_formats[i]) == 0))
3206 format_type=ExplicitFormatType;
3209 magick_info=GetMagickInfo(magic,sans_exception);
3210 if ((magick_info != (const MagickInfo *) NULL) &&
3211 (magick_info->format_type != UndefinedFormatType))
3212 format_type=magick_info->format_type;
3213 if (format_type == UndefinedFormatType)
3214 (void) CopyMagickString(image_info->magick,magic,MaxTextExtent);
3216 if (format_type == ExplicitFormatType)
3218 image_info->affirm=MagickTrue;
3219 (void) CopyMagickString(image_info->magick,magic,MaxTextExtent);
3221 if (LocaleCompare(magic,"RGB") == 0)
3222 image_info->affirm=MagickFalse; /* maybe SGI disguised as RGB */
3225 Look for explicit 'format:image' in filename.
3228 GetPathComponent(image_info->filename,MagickPath,magic);
3230 (void) CopyMagickString(magic,image_info->magick,MaxTextExtent);
3234 User specified image format.
3237 if (IsMagickConflict(magic) == MagickFalse)
3239 (void) CopyMagickString(image_info->magick,magic,MaxTextExtent);
3240 if (LocaleCompare(magic,"EPHEMERAL") != 0)
3241 image_info->affirm=MagickTrue;
3243 image_info->temporary=MagickTrue;
3246 magick_info=GetMagickInfo(magic,sans_exception);
3247 sans_exception=DestroyExceptionInfo(sans_exception);
3248 if ((magick_info == (const MagickInfo *) NULL) ||
3249 (GetMagickEndianSupport(magick_info) == MagickFalse))
3250 image_info->endian=UndefinedEndian;
3251 GetPathComponent(image_info->filename,CanonicalPath,filename);
3252 (void) CopyMagickString(image_info->filename,filename,MaxTextExtent);
3253 if ((image_info->adjoin != MagickFalse) && (frames > 1))
3256 Test for multiple image support (e.g. image%02d.png).
3258 (void) InterpretImageFilename(image_info,(Image *) NULL,
3259 image_info->filename,(int) image_info->scene,filename);
3260 if ((LocaleCompare(filename,image_info->filename) != 0) &&
3261 (strchr(filename,'%') == (char *) NULL))
3262 image_info->adjoin=MagickFalse;
3264 if ((image_info->adjoin != MagickFalse) && (frames > 0))
3267 Some image formats do not support multiple frames per file.
3269 magick_info=GetMagickInfo(magic,exception);
3270 if (magick_info != (const MagickInfo *) NULL)
3271 if (GetMagickAdjoin(magick_info) == MagickFalse)
3272 image_info->adjoin=MagickFalse;
3274 if (image_info->affirm != MagickFalse)
3279 Determine the image format from the first few bytes of the file.
3281 image=AcquireImage(image_info);
3282 (void) CopyMagickString(image->filename,image_info->filename,
3284 status=OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
3285 if (status == MagickFalse)
3287 image=DestroyImage(image);
3288 return(MagickFalse);
3290 if ((IsBlobSeekable(image) == MagickFalse) ||
3291 (IsBlobExempt(image) != MagickFalse))
3294 Copy standard input or pipe to temporary file.
3297 status=ImageToFile(image,filename,exception);
3298 (void) CloseBlob(image);
3299 if (status == MagickFalse)
3301 image=DestroyImage(image);
3302 return(MagickFalse);
3304 SetImageInfoFile(image_info,(FILE *) NULL);
3305 (void) CopyMagickString(image->filename,filename,MaxTextExtent);
3306 status=OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
3307 if (status == MagickFalse)
3309 image=DestroyImage(image);
3310 return(MagickFalse);
3312 (void) CopyMagickString(image_info->filename,filename,MaxTextExtent);
3313 image_info->temporary=MagickTrue;
3315 (void) ResetMagickMemory(magick,0,sizeof(magick));
3316 count=ReadBlob(image,2*MaxTextExtent,magick);
3317 (void) CloseBlob(image);
3318 image=DestroyImage(image);
3320 Check magic.xml configuration file.
3322 sans_exception=AcquireExceptionInfo();
3323 magic_info=GetMagicInfo(magick,(size_t) count,sans_exception);
3324 if ((magic_info != (const MagicInfo *) NULL) &&
3325 (GetMagicName(magic_info) != (char *) NULL))
3327 (void) CopyMagickString(image_info->magick,GetMagicName(magic_info),
3329 magick_info=GetMagickInfo(image_info->magick,sans_exception);
3330 if ((magick_info == (const MagickInfo *) NULL) ||
3331 (GetMagickEndianSupport(magick_info) == MagickFalse))
3332 image_info->endian=UndefinedEndian;
3333 sans_exception=DestroyExceptionInfo(sans_exception);
3336 magick_info=GetMagickInfo(image_info->magick,sans_exception);
3337 if ((magick_info == (const MagickInfo *) NULL) ||
3338 (GetMagickEndianSupport(magick_info) == MagickFalse))
3339 image_info->endian=UndefinedEndian;
3340 sans_exception=DestroyExceptionInfo(sans_exception);
3346 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3350 % S e t I m a g e I n f o B l o b %
3354 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3356 % SetImageInfoBlob() sets the image info blob member.
3358 % The format of the SetImageInfoBlob method is:
3360 % void SetImageInfoBlob(ImageInfo *image_info,const void *blob,
3361 % const size_t length)
3363 % A description of each parameter follows:
3365 % o image_info: the image info.
3369 % o length: the blob length.
3372 MagickExport void SetImageInfoBlob(ImageInfo *image_info,const void *blob,
3373 const size_t length)
3375 assert(image_info != (ImageInfo *) NULL);
3376 assert(image_info->signature == MagickSignature);
3377 if (image_info->debug != MagickFalse)
3378 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
3379 image_info->filename);
3380 image_info->blob=(void *) blob;
3381 image_info->length=length;
3385 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3389 % S e t I m a g e I n f o F i l e %
3393 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3395 % SetImageInfoFile() sets the image info file member.
3397 % The format of the SetImageInfoFile method is:
3399 % void SetImageInfoFile(ImageInfo *image_info,FILE *file)
3401 % A description of each parameter follows:
3403 % o image_info: the image info.
3408 MagickExport void SetImageInfoFile(ImageInfo *image_info,FILE *file)
3410 assert(image_info != (ImageInfo *) NULL);
3411 assert(image_info->signature == MagickSignature);
3412 if (image_info->debug != MagickFalse)
3413 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
3414 image_info->filename);
3415 image_info->file=file;
3419 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3423 % S e t I m a g e M a s k %
3427 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3429 % SetImageMask() associates a mask with the image. The mask must be the same
3430 % dimensions as the image.
3432 % The format of the SetImageMask method is:
3434 % MagickBooleanType SetImageMask(Image *image,const Image *mask)
3436 % A description of each parameter follows:
3438 % o image: the image.
3440 % o mask: the image mask.
3443 MagickExport MagickBooleanType SetImageMask(Image *image,
3446 assert(image != (Image *) NULL);
3447 if (image->debug != MagickFalse)
3448 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3449 assert(image->signature == MagickSignature);
3450 if (mask != (const Image *) NULL)
3451 if ((mask->columns != image->columns) || (mask->rows != image->rows))
3452 ThrowBinaryException(ImageError,"ImageSizeDiffers",image->filename);
3453 if (image->mask != (Image *) NULL)
3454 image->mask=DestroyImage(image->mask);
3455 image->mask=NewImageList();
3456 if (mask == (Image *) NULL)
3458 if (SetImageStorageClass(image,DirectClass) == MagickFalse)
3459 return(MagickFalse);
3460 image->mask=CloneImage(mask,0,0,MagickTrue,&image->exception);
3461 if (image->mask == (Image *) NULL)
3462 return(MagickFalse);
3467 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3471 % S e t I m a g e O p a c i t y %
3475 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3477 % SetImageOpacity() sets the opacity levels of the image.
3479 % The format of the SetImageOpacity method is:
3481 % MagickBooleanType SetImageOpacity(Image *image,const Quantum opacity)
3483 % A description of each parameter follows:
3485 % o image: the image.
3487 % o opacity: the level of transparency: 0 is fully opaque and QuantumRange is
3488 % fully transparent.
3491 MagickExport MagickBooleanType SetImageOpacity(Image *image,
3492 const Quantum opacity)
3506 assert(image != (Image *) NULL);
3507 if (image->debug != MagickFalse)
3508 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3509 assert(image->signature == MagickSignature);
3510 image->matte=opacity != OpaqueOpacity ? MagickTrue : MagickFalse;
3512 exception=(&image->exception);
3513 image_view=AcquireCacheView(image);
3514 #if defined(MAGICKCORE_OPENMP_SUPPORT)
3515 #pragma omp parallel for schedule(dynamic,4) shared(status)
3517 for (y=0; y < (long) image->rows; y++)
3522 register PixelPacket
3525 if (status == MagickFalse)
3527 q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
3528 if (q == (PixelPacket *) NULL)
3533 for (x=0; x < (long) image->columns; x++)
3535 SetOpacityPixelComponent(q,opacity);
3538 if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
3541 image_view=DestroyCacheView(image_view);
3546 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3550 % S e t I m a g e T y p e %
3554 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3556 % SetImageType() sets the type of image. Choose from these types:
3558 % Bilevel Grayscale GrayscaleMatte
3559 % Palette PaletteMatte TrueColor
3560 % TrueColorMatte ColorSeparation ColorSeparationMatte
3563 % The format of the SetImageType method is:
3565 % MagickBooleanType SetImageType(Image *image,const ImageType type)
3567 % A description of each parameter follows:
3569 % o image: the image.
3571 % o type: Image type.
3574 MagickExport MagickBooleanType SetImageType(Image *image,const ImageType type)
3588 assert(image != (Image *) NULL);
3589 if (image->debug != MagickFalse)
3590 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3591 assert(image->signature == MagickSignature);
3593 image_info=AcquireImageInfo();
3594 image_info->dither=image->dither;
3595 artifact=GetImageArtifact(image,"dither");
3596 if (artifact != (const char *) NULL)
3597 (void) SetImageOption(image_info,"dither",artifact);
3602 if (IsGrayImage(image,&image->exception) == MagickFalse)
3603 status=TransformImageColorspace(image,GRAYColorspace);
3604 if (IsMonochromeImage(image,&image->exception) == MagickFalse)
3606 quantize_info=AcquireQuantizeInfo(image_info);
3607 quantize_info->number_colors=2;
3608 quantize_info->colorspace=GRAYColorspace;
3609 status=QuantizeImage(quantize_info,image);
3610 quantize_info=DestroyQuantizeInfo(quantize_info);
3612 image->matte=MagickFalse;
3617 if (IsGrayImage(image,&image->exception) == MagickFalse)
3618 status=TransformImageColorspace(image,GRAYColorspace);
3619 image->matte=MagickFalse;
3622 case GrayscaleMatteType:
3624 if (IsGrayImage(image,&image->exception) == MagickFalse)
3625 status=TransformImageColorspace(image,GRAYColorspace);
3626 if (image->matte == MagickFalse)
3627 (void) SetImageAlphaChannel(image,OpaqueAlphaChannel);
3632 if (image->colorspace != RGBColorspace)
3633 status=TransformImageColorspace(image,RGBColorspace);
3634 if ((image->storage_class == DirectClass) || (image->colors > 256))
3636 quantize_info=AcquireQuantizeInfo(image_info);
3637 quantize_info->number_colors=256;
3638 status=QuantizeImage(quantize_info,image);
3639 quantize_info=DestroyQuantizeInfo(quantize_info);
3641 image->matte=MagickFalse;
3644 case PaletteBilevelMatteType:
3646 if (image->colorspace != RGBColorspace)
3647 status=TransformImageColorspace(image,RGBColorspace);
3648 if (image->matte == MagickFalse)
3649 (void) SetImageAlphaChannel(image,OpaqueAlphaChannel);
3650 (void) BilevelImageChannel(image,AlphaChannel,(double) QuantumRange/2.0);
3651 quantize_info=AcquireQuantizeInfo(image_info);
3652 status=QuantizeImage(quantize_info,image);
3653 quantize_info=DestroyQuantizeInfo(quantize_info);
3656 case PaletteMatteType:
3658 if (image->colorspace != RGBColorspace)
3659 status=TransformImageColorspace(image,RGBColorspace);
3660 if (image->matte == MagickFalse)
3661 (void) SetImageAlphaChannel(image,OpaqueAlphaChannel);
3662 quantize_info=AcquireQuantizeInfo(image_info);
3663 quantize_info->colorspace=TransparentColorspace;
3664 status=QuantizeImage(quantize_info,image);
3665 quantize_info=DestroyQuantizeInfo(quantize_info);
3670 if (image->colorspace != RGBColorspace)
3671 status=TransformImageColorspace(image,RGBColorspace);
3672 if (image->storage_class != DirectClass)
3673 status=SetImageStorageClass(image,DirectClass);
3674 image->matte=MagickFalse;
3677 case TrueColorMatteType:
3679 if (image->colorspace != RGBColorspace)
3680 status=TransformImageColorspace(image,RGBColorspace);
3681 if (image->storage_class != DirectClass)
3682 status=SetImageStorageClass(image,DirectClass);
3683 if (image->matte == MagickFalse)
3684 (void) SetImageAlphaChannel(image,OpaqueAlphaChannel);
3687 case ColorSeparationType:
3689 if (image->colorspace != CMYKColorspace)
3691 if (image->colorspace != RGBColorspace)
3692 status=TransformImageColorspace(image,RGBColorspace);
3693 status=TransformImageColorspace(image,CMYKColorspace);
3695 if (image->storage_class != DirectClass)
3696 status=SetImageStorageClass(image,DirectClass);
3697 image->matte=MagickFalse;
3700 case ColorSeparationMatteType:
3702 if (image->colorspace != CMYKColorspace)
3704 if (image->colorspace != RGBColorspace)
3705 status=TransformImageColorspace(image,RGBColorspace);
3706 status=TransformImageColorspace(image,CMYKColorspace);
3708 if (image->storage_class != DirectClass)
3709 status=SetImageStorageClass(image,DirectClass);
3710 if (image->matte == MagickFalse)
3711 (void) SetImageAlphaChannel(image,OpaqueAlphaChannel);
3719 image_info=DestroyImageInfo(image_info);
3724 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3728 % 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 %
3732 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3734 % SetImageVirtualPixelMethod() sets the "virtual pixels" method for the
3735 % image and returns the previous setting. A virtual pixel is any pixel access
3736 % that is outside the boundaries of the image cache.
3738 % The format of the SetImageVirtualPixelMethod() method is:
3740 % VirtualPixelMethod SetImageVirtualPixelMethod(const Image *image,
3741 % const VirtualPixelMethod virtual_pixel_method)
3743 % A description of each parameter follows:
3745 % o image: the image.
3747 % o virtual_pixel_method: choose the type of virtual pixel.
3750 MagickExport VirtualPixelMethod SetImageVirtualPixelMethod(const Image *image,
3751 const VirtualPixelMethod virtual_pixel_method)
3753 assert(image != (const Image *) NULL);
3754 assert(image->signature == MagickSignature);
3755 if (image->debug != MagickFalse)
3756 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
3757 return(SetPixelCacheVirtualMethod(image,virtual_pixel_method));
3761 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3765 % S t r i p I m a g e %
3769 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3771 % StripImage() strips an image of all profiles and comments.
3773 % The format of the StripImage method is:
3775 % MagickBooleanType StripImage(Image *image)
3777 % A description of each parameter follows:
3779 % o image: the image.
3782 MagickExport MagickBooleanType StripImage(Image *image)
3784 assert(image != (Image *) NULL);
3785 if (image->debug != MagickFalse)
3786 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3787 DestroyImageProfiles(image);
3788 (void) DeleteImageProperty(image,"comment");
3793 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3797 + S y n c I m a g e %
3801 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3803 % SyncImage() initializes the red, green, and blue intensities of each pixel
3804 % as defined by the colormap index.
3806 % The format of the SyncImage method is:
3808 % MagickBooleanType SyncImage(Image *image)
3810 % A description of each parameter follows:
3812 % o image: the image.
3816 static inline IndexPacket PushColormapIndex(Image *image,
3817 const unsigned long index,MagickBooleanType *range_exception)
3819 if (index < image->colors)
3820 return((IndexPacket) index);
3821 *range_exception=MagickTrue;
3822 return((IndexPacket) 0);
3825 MagickExport MagickBooleanType SyncImage(Image *image)
3840 assert(image != (Image *) NULL);
3841 if (image->debug != MagickFalse)
3842 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3843 assert(image->signature == MagickSignature);
3844 if (image->storage_class == DirectClass)
3845 return(MagickFalse);
3846 range_exception=MagickFalse;
3848 exception=(&image->exception);
3849 image_view=AcquireCacheView(image);
3850 #if defined(MAGICKCORE_OPENMP_SUPPORT)
3851 #pragma omp parallel for schedule(dynamic,4) shared(status)
3853 for (y=0; y < (long) image->rows; y++)
3861 register IndexPacket
3867 register PixelPacket
3870 if (status == MagickFalse)
3872 q=GetCacheViewAuthenticPixels(image_view,0,y,image->columns,1,exception);
3873 if (q == (PixelPacket *) NULL)
3878 indexes=GetCacheViewAuthenticIndexQueue(image_view);
3879 for (x=0; x < (long) image->columns; x++)
3881 index=PushColormapIndex(image,(unsigned long) indexes[x],
3883 pixel=image->colormap[(long) index];
3885 q->green=pixel.green;
3889 if (SyncCacheViewAuthenticPixels(image_view,exception) == MagickFalse)
3892 image_view=DestroyCacheView(image_view);
3893 if (range_exception != MagickFalse)
3894 (void) ThrowMagickException(&image->exception,GetMagickModule(),
3895 CorruptImageError,"InvalidColormapIndex","`%s'",image->filename);
3900 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3904 % S y n c I m a g e S e t t i n g s %
3908 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3910 % SyncImageSettings() sync the image info options to the image.
3912 % The format of the SyncImageSettings method is:
3914 % MagickBooleanType SyncImageSettings(const ImageInfo *image_info,
3916 % MagickBooleanType SyncImagesSettings(const ImageInfo *image_info,
3919 % A description of each parameter follows:
3921 % o image_info: the image info.
3923 % o image: the image.
3927 MagickExport MagickBooleanType SyncImagesSettings(ImageInfo *image_info,
3933 assert(image_info != (const ImageInfo *) NULL);
3934 assert(image_info->signature == MagickSignature);
3935 assert(images != (Image *) NULL);
3936 assert(images->signature == MagickSignature);
3937 if (images->debug != MagickFalse)
3938 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",images->filename);
3940 for ( ; image != (Image *) NULL; image=GetNextImageInList(image))
3941 (void) SyncImageSettings(image_info,image);
3942 (void) DeleteImageOption(image_info,"page");
3946 MagickExport MagickBooleanType SyncImageSettings(const ImageInfo *image_info,
3950 property[MaxTextExtent];
3965 assert(image_info != (const ImageInfo *) NULL);
3966 assert(image_info->signature == MagickSignature);
3967 assert(image != (Image *) NULL);
3968 assert(image->signature == MagickSignature);
3969 if (image->debug != MagickFalse)
3970 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
3971 option=GetImageOption(image_info,"background");
3972 if (option != (const char *) NULL)
3973 (void) QueryColorDatabase(option,&image->background_color,
3975 option=GetImageOption(image_info,"bias");
3976 if (option != (const char *) NULL)
3977 image->bias=SiPrefixToDouble(option,QuantumRange);
3978 option=GetImageOption(image_info,"black-point-compensation");
3979 if (option != (const char *) NULL)
3980 image->black_point_compensation=(MagickBooleanType) ParseMagickOption(
3981 MagickBooleanOptions,MagickFalse,option);
3982 option=GetImageOption(image_info,"blue-primary");
3983 if (option != (const char *) NULL)
3985 flags=ParseGeometry(option,&geometry_info);
3986 image->chromaticity.blue_primary.x=geometry_info.rho;
3987 image->chromaticity.blue_primary.y=geometry_info.sigma;
3988 if ((flags & SigmaValue) == 0)
3989 image->chromaticity.blue_primary.y=image->chromaticity.blue_primary.x;
3991 option=GetImageOption(image_info,"bordercolor");
3992 if (option != (const char *) NULL)
3993 (void) QueryColorDatabase(option,&image->border_color,&image->exception);
3994 option=GetImageOption(image_info,"colors");
3995 if (option != (const char *) NULL)
3996 image->colors=StringToUnsignedLong(option);
3997 option=GetImageOption(image_info,"compose");
3998 if (option != (const char *) NULL)
3999 image->compose=(CompositeOperator) ParseMagickOption(MagickComposeOptions,
4000 MagickFalse,option);
4001 option=GetImageOption(image_info,"compress");
4002 if (option != (const char *) NULL)
4003 image->compression=(CompressionType) ParseMagickOption(
4004 MagickCompressOptions,MagickFalse,option);
4005 option=GetImageOption(image_info,"debug");
4006 if (option != (const char *) NULL)
4007 image->debug=(MagickBooleanType) ParseMagickOption(MagickBooleanOptions,
4008 MagickFalse,option);
4009 option=GetImageOption(image_info,"delay");
4010 if (option != (const char *) NULL)
4015 flags=ParseGeometry(option,&geometry_info);
4016 if ((flags & GreaterValue) != 0)
4018 if (image->delay > (unsigned long) floor(geometry_info.rho+0.5))
4019 image->delay=(unsigned long) floor(geometry_info.rho+0.5);
4022 if ((flags & LessValue) != 0)
4024 if (image->delay < (unsigned long) floor(geometry_info.rho+0.5))
4025 image->ticks_per_second=(long) floor(geometry_info.sigma+0.5);
4028 image->delay=(unsigned long) floor(geometry_info.rho+0.5);
4029 if ((flags & SigmaValue) != 0)
4030 image->ticks_per_second=(long) floor(geometry_info.sigma+0.5);
4032 option=GetImageOption(image_info,"density");
4033 if (option != (const char *) NULL)
4041 flags=ParseGeometry(option,&geometry_info);
4042 image->x_resolution=geometry_info.rho;
4043 image->y_resolution=geometry_info.sigma;
4044 if ((flags & SigmaValue) == 0)
4045 image->y_resolution=image->x_resolution;
4047 option=GetImageOption(image_info,"depth");
4048 if (option != (const char *) NULL)
4049 image->depth=StringToUnsignedLong(option);
4050 option=GetImageOption(image_info,"dispose");
4051 if (option != (const char *) NULL)
4052 image->dispose=(DisposeType) ParseMagickOption(MagickDisposeOptions,
4053 MagickFalse,option);
4054 option=GetImageOption(image_info,"endian");
4055 if (option != (const char *) NULL)
4056 image->endian=(EndianType) ParseMagickOption(MagickEndianOptions,
4057 MagickFalse,option);
4058 if (image_info->extract != (char *) NULL)
4059 (void) ParseAbsoluteGeometry(image_info->extract,&image->extract_info);
4060 option=GetImageOption(image_info,"filter");
4061 if (option != (const char *) NULL)
4062 image->filter=(FilterTypes) ParseMagickOption(MagickFilterOptions,
4063 MagickFalse,option);
4064 option=GetImageOption(image_info,"fuzz");
4065 if (option != (const char *) NULL)
4066 image->fuzz=SiPrefixToDouble(option,QuantumRange);
4067 option=GetImageOption(image_info,"gravity");
4068 if (option != (const char *) NULL)
4069 image->gravity=(GravityType) ParseMagickOption(MagickGravityOptions,
4070 MagickFalse,option);
4071 option=GetImageOption(image_info,"green-primary");
4072 if (option != (const char *) NULL)
4074 flags=ParseGeometry(option,&geometry_info);
4075 image->chromaticity.green_primary.x=geometry_info.rho;
4076 image->chromaticity.green_primary.y=geometry_info.sigma;
4077 if ((flags & SigmaValue) == 0)
4078 image->chromaticity.green_primary.y=image->chromaticity.green_primary.x;
4080 option=GetImageOption(image_info,"intent");
4081 if (option != (const char *) NULL)
4082 image->rendering_intent=(RenderingIntent) ParseMagickOption(
4083 MagickIntentOptions,MagickFalse,option);
4084 option=GetImageOption(image_info,"interlace");
4085 if (option != (const char *) NULL)
4086 image->interlace=(InterlaceType) ParseMagickOption(MagickInterlaceOptions,
4087 MagickFalse,option);
4088 option=GetImageOption(image_info,"interpolate");
4089 if (option != (const char *) NULL)
4090 image->interpolate=(InterpolatePixelMethod) ParseMagickOption(
4091 MagickInterpolateOptions,MagickFalse,option);
4092 option=GetImageOption(image_info,"loop");
4093 if (option != (const char *) NULL)
4094 image->iterations=StringToUnsignedLong(option);
4095 option=GetImageOption(image_info,"mattecolor");
4096 if (option != (const char *) NULL)
4097 (void) QueryColorDatabase(option,&image->matte_color,&image->exception);
4098 option=GetImageOption(image_info,"orient");
4099 if (option != (const char *) NULL)
4100 image->orientation=(OrientationType) ParseMagickOption(
4101 MagickOrientationOptions,MagickFalse,option);
4102 option=GetImageOption(image_info,"quality");
4103 if (option != (const char *) NULL)
4104 image->quality=StringToUnsignedLong(option);
4105 option=GetImageOption(image_info,"page");
4106 if (option != (const char *) NULL)
4111 geometry=GetPageGeometry(option);
4112 flags=ParseAbsoluteGeometry(geometry,&image->page);
4113 geometry=DestroyString(geometry);
4115 option=GetImageOption(image_info,"red-primary");
4116 if (option != (const char *) NULL)
4118 flags=ParseGeometry(option,&geometry_info);
4119 image->chromaticity.red_primary.x=geometry_info.rho;
4120 image->chromaticity.red_primary.y=geometry_info.sigma;
4121 if ((flags & SigmaValue) == 0)
4122 image->chromaticity.red_primary.y=image->chromaticity.red_primary.x;
4124 if (image_info->quality != UndefinedCompressionQuality)
4125 image->quality=image_info->quality;
4126 option=GetImageOption(image_info,"scene");
4127 if (option != (const char *) NULL)
4128 image->scene=StringToUnsignedLong(option);
4129 option=GetImageOption(image_info,"taint");
4130 if (option != (const char *) NULL)
4131 image->taint=(MagickBooleanType) ParseMagickOption(MagickBooleanOptions,
4132 MagickFalse,option);
4133 option=GetImageOption(image_info,"tile-offset");
4134 if (option != (const char *) NULL)
4139 geometry=GetPageGeometry(option);
4140 flags=ParseAbsoluteGeometry(geometry,&image->tile_offset);
4141 geometry=DestroyString(geometry);
4143 option=GetImageOption(image_info,"transparent-color");
4144 if (option != (const char *) NULL)
4145 (void) QueryColorDatabase(option,&image->transparent_color,
4147 option=GetImageOption(image_info,"type");
4148 if (option != (const char *) NULL)
4149 image->type=(ImageType) ParseMagickOption(MagickTypeOptions,MagickFalse,
4151 option=GetImageOption(image_info,"units");
4152 if (option != (const char *) NULL)
4153 image->units=(ResolutionType) ParseMagickOption(MagickResolutionOptions,
4154 MagickFalse,option);
4155 if (image_info->units != UndefinedResolution)
4157 if (image->units != image_info->units)
4158 switch (image->units)
4160 case PixelsPerInchResolution:
4162 if (image_info->units == PixelsPerCentimeterResolution)
4164 image->x_resolution/=2.54;
4165 image->y_resolution/=2.54;
4169 case PixelsPerCentimeterResolution:
4171 if (image_info->units == PixelsPerInchResolution)
4173 image->x_resolution*=2.54;
4174 image->y_resolution*=2.54;
4181 image->units=image_info->units;
4183 option=GetImageOption(image_info,"white-point");
4184 if (option != (const char *) NULL)
4186 flags=ParseGeometry(option,&geometry_info);
4187 image->chromaticity.white_point.x=geometry_info.rho;
4188 image->chromaticity.white_point.y=geometry_info.sigma;
4189 if ((flags & SigmaValue) == 0)
4190 image->chromaticity.white_point.y=image->chromaticity.white_point.x;
4192 ResetImageOptionIterator(image_info);
4193 for (option=GetNextImageOption(image_info); option != (const char *) NULL; )
4195 value=GetImageOption(image_info,option);
4196 if (value != (const char *) NULL)
4198 (void) FormatMagickString(property,MaxTextExtent,"%s",option);
4199 (void) SetImageArtifact(image,property,value);
4201 option=GetNextImageOption(image_info);