1/*
2%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3%                                                                             %
4%                                                                             %
5%                                                                             %
6%              M   M   OOO   GGGGG  RRRR   IIIII  FFFFF  Y   Y                %
7%              MM MM  O   O  G      R   R    I    F       Y Y                 %
8%              M M M  O   O  G GGG  RRRR     I    FFF      Y                  %
9%              M   M  O   O  G   G  R R      I    F        Y                  %
10%              M   M   OOO   GGGG   R  R   IIIII  F        Y                  %
11%                                                                             %
12%                                                                             %
13%                         MagickWand Module Methods                           %
14%                                                                             %
15%                              Software Design                                %
16%                                   Cristy                                    %
17%                                March 2000                                   %
18%                                                                             %
19%                                                                             %
20%  Copyright 1999-2016 ImageMagick Studio LLC, a non-profit organization      %
21%  dedicated to making software imaging solutions freely available.           %
22%                                                                             %
23%  You may not use this file except in compliance with the License.  You may  %
24%  obtain a copy of the License at                                            %
25%                                                                             %
26%    http://www.imagemagick.org/script/license.php                            %
27%                                                                             %
28%  Unless required by applicable law or agreed to in writing, software        %
29%  distributed under the License is distributed on an "AS IS" BASIS,          %
30%  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.   %
31%  See the License for the specific language governing permissions and        %
32%  limitations under the License.                                             %
33%                                                                             %
34%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
35%
36%  Use the mogrify program to resize an image, blur, crop, despeckle, dither,
37%  draw on, flip, join, re-sample, and much more. This tool is similiar to
38%  convert except that the original image file is overwritten (unless you
39%  change the file suffix with the -format option) with any changes you
40%  request.
41%
42*/
43
44/*
45  Include declarations.
46*/
47#include "MagickWand/studio.h"
48#include "MagickWand/MagickWand.h"
49#include "MagickWand/magick-wand-private.h"
50#include "MagickWand/mogrify-private.h"
51#include "MagickCore/image-private.h"
52#include "MagickCore/monitor-private.h"
53#include "MagickCore/string-private.h"
54#include "MagickCore/thread-private.h"
55#include "MagickCore/utility-private.h"
56#include "MagickCore/blob-private.h"
57#if defined(MAGICKCORE_HAVE_UTIME_H)
58#include <utime.h>
59#endif
60
61/*
62  Constant declaration.
63*/
64static const char
65  MogrifyAlphaColor[] = "#bdbdbd",  /* gray */
66  MogrifyBackgroundColor[] = "#ffffff",  /* white */
67  MogrifyBorderColor[] = "#dfdfdf";  /* gray */
68
69/*
70  Define declarations.
71*/
72#define UndefinedCompressionQuality  0UL
73
74/*
75%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
76%                                                                             %
77%                                                                             %
78%                                                                             %
79%     M a g i c k C o m m a n d G e n e s i s                                 %
80%                                                                             %
81%                                                                             %
82%                                                                             %
83%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
84%
85%  MagickCommandGenesis() applies image processing options to an image as
86%  prescribed by command line options.
87%
88%  It wiil look for special options like "-debug", "-bench", and
89%  "-distribute-cache" that needs to be applied even before the main
90%  processing begins, and may completely overrule normal command processing.
91%  Such 'Genesis' Options can only be given on the CLI, (not in a script)
92%  and are typically ignored (as they have been handled) if seen later.
93%
94%  The format of the MagickCommandGenesis method is:
95%
96%      MagickBooleanType MagickCommandGenesis(ImageInfo *image_info,
97%        MagickCommand command,int argc,char **argv,char **metadata,
98%        ExceptionInfo *exception)
99%
100%  A description of each parameter follows:
101%
102%    o image_info: the image info.
103%
104%    o command: Choose from ConvertImageCommand, IdentifyImageCommand,
105%      MogrifyImageCommand, CompositeImageCommand, CompareImagesCommand,
106%      ConjureImageCommand, StreamImageCommand, ImportImageCommand,
107%      DisplayImageCommand, or AnimateImageCommand.
108%
109%    o argc: Specifies a pointer to an integer describing the number of
110%      elements in the argument vector.
111%
112%    o argv: Specifies a pointer to a text array containing the command line
113%      arguments.
114%
115%    o metadata: any metadata is returned here.
116%
117%    o exception: return any errors or warnings in this structure.
118%
119*/
120WandExport MagickBooleanType MagickCommandGenesis(ImageInfo *image_info,
121  MagickCommand command,int argc,char **argv,char **metadata,
122  ExceptionInfo *exception)
123{
124  char
125    client_name[MaxTextExtent],
126    *option;
127
128  double
129    duration,
130    serial;
131
132  MagickBooleanType
133    concurrent,
134    regard_warnings,
135    status;
136
137  register ssize_t
138    i;
139
140  size_t
141    iterations,
142    number_threads;
143
144  ssize_t
145    n;
146
147  (void) setlocale(LC_ALL,"");
148  (void) setlocale(LC_NUMERIC,"C");
149  GetPathComponent(argv[0],TailPath,client_name);
150  SetClientName(client_name);
151  concurrent=MagickFalse;
152  duration=(-1.0);
153  iterations=1;
154  status=MagickTrue;
155  regard_warnings=MagickFalse;
156  for (i=1; i < (ssize_t) (argc-1); i++)
157  {
158    option=argv[i];
159    if ((strlen(option) == 1) || ((*option != '-') && (*option != '+')))
160      continue;
161    if (LocaleCompare("-bench",option) == 0)
162      iterations=StringToUnsignedLong(argv[++i]);
163    if (LocaleCompare("-concurrent",option) == 0)
164      concurrent=MagickTrue;
165    if (LocaleCompare("-debug",option) == 0)
166      (void) SetLogEventMask(argv[++i]);
167    if (LocaleCompare("-distribute-cache",option) == 0)
168      {
169        DistributePixelCacheServer(StringToInteger(argv[++i]),exception);
170        exit(0);
171      }
172    if (LocaleCompare("-duration",option) == 0)
173      duration=StringToDouble(argv[++i],(char **) NULL);
174    if (LocaleCompare("-regard-warnings",option) == 0)
175      regard_warnings=MagickTrue;
176  }
177  if (iterations == 1)
178    {
179      char
180        *text;
181
182      text=(char *) NULL;
183      status=command(image_info,argc,argv,&text,exception);
184      if (exception->severity != UndefinedException)
185        {
186          if ((exception->severity > ErrorException) ||
187              (regard_warnings != MagickFalse))
188            status=MagickFalse;
189          CatchException(exception);
190        }
191      if (text != (char *) NULL)
192        {
193          if (metadata != (char **) NULL)
194            (void) ConcatenateString(&(*metadata),text);
195          text=DestroyString(text);
196        }
197      return(status);
198    }
199  number_threads=GetOpenMPMaximumThreads();
200  serial=0.0;
201  for (n=1; n <= (ssize_t) number_threads; n++)
202  {
203    double
204      e,
205      parallel,
206      user_time;
207
208    TimerInfo
209      *timer;
210
211    (void) SetMagickResourceLimit(ThreadResource,(MagickSizeType) n);
212    timer=AcquireTimerInfo();
213    if (concurrent == MagickFalse)
214      {
215        for (i=0; i < (ssize_t) iterations; i++)
216        {
217          char
218            *text;
219
220          text=(char *) NULL;
221          if (status == MagickFalse)
222            continue;
223          if (duration > 0)
224            {
225              if (GetElapsedTime(timer) > duration)
226                continue;
227              (void) ContinueTimer(timer);
228            }
229          status=command(image_info,argc,argv,&text,exception);
230          if (exception->severity != UndefinedException)
231            {
232              if ((exception->severity > ErrorException) ||
233                  (regard_warnings != MagickFalse))
234                status=MagickFalse;
235              CatchException(exception);
236            }
237          if (text != (char *) NULL)
238            {
239              if (metadata != (char **) NULL)
240                (void) ConcatenateString(&(*metadata),text);
241              text=DestroyString(text);
242            }
243          }
244      }
245    else
246      {
247        SetOpenMPNested(1);
248#if defined(MAGICKCORE_OPENMP_SUPPORT)
249        # pragma omp parallel for shared(status)
250#endif
251        for (i=0; i < (ssize_t) iterations; i++)
252        {
253          char
254            *text;
255
256          text=(char *) NULL;
257          if (status == MagickFalse)
258            continue;
259          if (duration > 0)
260            {
261              if (GetElapsedTime(timer) > duration)
262                continue;
263              (void) ContinueTimer(timer);
264            }
265          status=command(image_info,argc,argv,&text,exception);
266#if defined(MAGICKCORE_OPENMP_SUPPORT)
267          # pragma omp critical (MagickCore_MagickCommandGenesis)
268#endif
269          {
270            if (exception->severity != UndefinedException)
271              {
272                if ((exception->severity > ErrorException) ||
273                    (regard_warnings != MagickFalse))
274                  status=MagickFalse;
275                CatchException(exception);
276              }
277            if (text != (char *) NULL)
278              {
279                if (metadata != (char **) NULL)
280                  (void) ConcatenateString(&(*metadata),text);
281                text=DestroyString(text);
282              }
283          }
284        }
285      }
286    user_time=GetUserTime(timer);
287    parallel=GetElapsedTime(timer);
288    e=1.0;
289    if (n == 1)
290      serial=parallel;
291    else
292      e=((1.0/(1.0/((serial/(serial+parallel))+(1.0-(serial/(serial+parallel)))/
293        (double) n)))-(1.0/(double) n))/(1.0-1.0/(double) n);
294    (void) FormatLocaleFile(stderr,
295      "Performance[%.20g]: %.20gi %0.3fips %0.3fe %0.3fu %lu:%02lu.%03lu\n",
296      (double) n,(double) iterations,(double) iterations/parallel,e,user_time,
297      (unsigned long) (parallel/60.0),(unsigned long) floor(fmod(parallel,
298      60.0)),(unsigned long) (1000.0*(parallel-floor(parallel))+0.5));
299    timer=DestroyTimerInfo(timer);
300  }
301  return(status);
302}
303
304/*
305%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
306%                                                                             %
307%                                                                             %
308%                                                                             %
309+     M o g r i f y I m a g e                                                 %
310%                                                                             %
311%                                                                             %
312%                                                                             %
313%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
314%
315%  MogrifyImage() applies simple single image processing options to a single
316%  image that may be part of a large list, but also handles any 'region'
317%  image handling.
318%
319%  The image in the list may be modified in three different ways...
320%
321%    * directly modified (EG: -negate, -gamma, -level, -annotate, -draw),
322%    * replaced by a new image (EG: -spread, -resize, -rotate, -morphology)
323%    * replace by a list of images (only the -separate option!)
324%
325%  In each case the result is returned into the list, and a pointer to the
326%  modified image (last image added if replaced by a list of images) is
327%  returned.
328%
329%  ASIDE: The -crop is present but restricted to non-tile single image crops
330%
331%  This means if all the images are being processed (such as by
332%  MogrifyImages(), next image to be processed will be as per the pointer
333%  (*image)->next.  Also the image list may grow as a result of some specific
334%  operations but as images are never merged or deleted, it will never shrink
335%  in length.  Typically the list will remain the same length.
336%
337%  WARNING: As the image pointed to may be replaced, the first image in the
338%  list may also change.  GetFirstImageInList() should be used by caller if
339%  they wish return the Image pointer to the first image in list.
340%
341%
342%  The format of the MogrifyImage method is:
343%
344%      MagickBooleanType MogrifyImage(ImageInfo *image_info,const int argc,
345%        const char **argv,Image **image)
346%
347%  A description of each parameter follows:
348%
349%    o image_info: the image info..
350%
351%    o argc: Specifies a pointer to an integer describing the number of
352%      elements in the argument vector.
353%
354%    o argv: Specifies a pointer to a text array containing the command line
355%      arguments.
356%
357%    o image: the image.
358%
359%    o exception: return any errors or warnings in this structure.
360%
361*/
362
363static inline Image *GetImageCache(const ImageInfo *image_info,const char *path,
364  ExceptionInfo *exception)
365{
366  char
367    key[MagickPathExtent];
368
369  ExceptionInfo
370    *sans_exception;
371
372  Image
373    *image;
374
375  ImageInfo
376    *read_info;
377
378  /*
379    Read an image into a image cache (for repeated usage) if not already in
380    cache.  Then return the image that is in the cache.
381  */
382  (void) FormatLocaleString(key,MagickPathExtent,"cache:%s",path);
383  sans_exception=AcquireExceptionInfo();
384  image=(Image *) GetImageRegistry(ImageRegistryType,key,sans_exception);
385  sans_exception=DestroyExceptionInfo(sans_exception);
386  if (image != (Image *) NULL)
387    return(image);
388  read_info=CloneImageInfo(image_info);
389  (void) CopyMagickString(read_info->filename,path,MagickPathExtent);
390  image=ReadImage(read_info,exception);
391  read_info=DestroyImageInfo(read_info);
392  if (image != (Image *) NULL)
393    (void) SetImageRegistry(ImageRegistryType,key,image,exception);
394  return(image);
395}
396
397static inline MagickBooleanType IsPathWritable(const char *path)
398{
399  if (IsPathAccessible(path) == MagickFalse)
400    return(MagickFalse);
401  if (access_utf8(path,W_OK) != 0)
402    return(MagickFalse);
403  return(MagickTrue);
404}
405
406static MagickBooleanType MonitorProgress(const char *text,
407  const MagickOffsetType offset,const MagickSizeType extent,
408  void *wand_unused(client_data))
409{
410  char
411    message[MagickPathExtent],
412    tag[MagickPathExtent];
413
414  const char
415    *locale_message;
416
417  register char
418    *p;
419
420  magick_unreferenced(client_data);
421
422  if ((extent <= 1) || (offset < 0) || (offset >= (MagickOffsetType) extent))
423    return(MagickTrue);
424  if ((offset != (MagickOffsetType) (extent-1)) && ((offset % 50) != 0))
425    return(MagickTrue);
426  (void) CopyMagickString(tag,text,MagickPathExtent);
427  p=strrchr(tag,'/');
428  if (p != (char *) NULL)
429    *p='\0';
430  (void) FormatLocaleString(message,MagickPathExtent,"Monitor/%s",tag);
431  locale_message=GetLocaleMessage(message);
432  if (locale_message == message)
433    locale_message=tag;
434  if (p == (char *) NULL)
435    (void) FormatLocaleFile(stderr,"%s: %ld of %lu, %02ld%% complete\r",
436      locale_message,(long) offset,(unsigned long) extent,(long)
437      (100L*offset/(extent-1)));
438  else
439    (void) FormatLocaleFile(stderr,"%s[%s]: %ld of %lu, %02ld%% complete\r",
440      locale_message,p+1,(long) offset,(unsigned long) extent,(long)
441      (100L*offset/(extent-1)));
442  if (offset == (MagickOffsetType) (extent-1))
443    (void) FormatLocaleFile(stderr,"\n");
444  (void) fflush(stderr);
445  return(MagickTrue);
446}
447
448static Image *SparseColorOption(const Image *image,
449  const SparseColorMethod method,const char *arguments,
450  const MagickBooleanType color_from_image,ExceptionInfo *exception)
451{
452  char
453    token[MagickPathExtent];
454
455  const char
456    *p;
457
458  double
459    *sparse_arguments;
460
461  Image
462    *sparse_image;
463
464  PixelInfo
465    color;
466
467  MagickBooleanType
468    error;
469
470  register size_t
471    x;
472
473  size_t
474    number_arguments,
475    number_colors;
476
477  /*
478    SparseColorOption() parses the complex -sparse-color argument into an an
479    array of floating point values then calls SparseColorImage().  Argument is
480    a complex mix of floating-point pixel coodinates, and color specifications
481    (or direct floating point numbers).  The number of floats needed to
482    represent a color varies depending on the current channel setting.
483  */
484  assert(image != (Image *) NULL);
485  assert(image->signature == MagickCoreSignature);
486  if (image->debug != MagickFalse)
487    (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",image->filename);
488  assert(exception != (ExceptionInfo *) NULL);
489  assert(exception->signature == MagickCoreSignature);
490  /*
491    Limit channels according to image - and add up number of color channel.
492  */
493  number_colors=0;
494  if ((GetPixelRedTraits(image) & UpdatePixelTrait) != 0)
495    number_colors++;
496  if ((GetPixelGreenTraits(image) & UpdatePixelTrait) != 0)
497    number_colors++;
498  if ((GetPixelBlueTraits(image) & UpdatePixelTrait) != 0)
499    number_colors++;
500  if (((GetPixelBlackTraits(image) & UpdatePixelTrait) != 0) &&
501      (image->colorspace == CMYKColorspace))
502    number_colors++;
503  if (((GetPixelAlphaTraits(image) & UpdatePixelTrait) != 0) &&
504      (image->alpha_trait != UndefinedPixelTrait))
505    number_colors++;
506
507  /*
508    Read string, to determine number of arguments needed,
509  */
510  p=arguments;
511  x=0;
512  while( *p != '\0' )
513  {
514    GetNextToken(p,&p,MagickPathExtent,token);
515    if ( token[0] == ',' ) continue;
516    if ( isalpha((int) token[0]) || token[0] == '#' ) {
517      if ( color_from_image ) {
518        (void) ThrowMagickException(exception,GetMagickModule(),
519            OptionError, "InvalidArgument", "'%s': %s", "sparse-color",
520            "Color arg given, when colors are coming from image");
521        return( (Image *) NULL);
522      }
523      x += number_colors;  /* color argument */
524    }
525    else {
526      x++;   /* floating point argument */
527    }
528  }
529  error=MagickTrue;
530  if ( color_from_image ) {
531    /* just the control points are being given */
532    error = ( x % 2 != 0 ) ? MagickTrue : MagickFalse;
533    number_arguments=(x/2)*(2+number_colors);
534  }
535  else {
536    /* control points and color values */
537    error = ( x % (2+number_colors) != 0 ) ? MagickTrue : MagickFalse;
538    number_arguments=x;
539  }
540  if ( error ) {
541    (void) ThrowMagickException(exception,GetMagickModule(),
542               OptionError, "InvalidArgument", "'%s': %s", "sparse-color",
543               "Invalid number of Arguments");
544    return( (Image *) NULL);
545  }
546
547  /* Allocate and fill in the floating point arguments */
548  sparse_arguments=(double *) AcquireQuantumMemory(number_arguments,
549    sizeof(*sparse_arguments));
550  if (sparse_arguments == (double *) NULL) {
551    (void) ThrowMagickException(exception,GetMagickModule(),ResourceLimitError,
552      "MemoryAllocationFailed","%s","SparseColorOption");
553    return( (Image *) NULL);
554  }
555  (void) ResetMagickMemory(sparse_arguments,0,number_arguments*
556    sizeof(*sparse_arguments));
557  p=arguments;
558  x=0;
559  while( *p != '\0' && x < number_arguments ) {
560    /* X coordinate */
561    token[0]=','; while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
562    if ( token[0] == '\0' ) break;
563    if ( isalpha((int) token[0]) || token[0] == '#' ) {
564      (void) ThrowMagickException(exception,GetMagickModule(),
565            OptionError, "InvalidArgument", "'%s': %s", "sparse-color",
566            "Color found, instead of X-coord");
567      error = MagickTrue;
568      break;
569    }
570    sparse_arguments[x++]=StringToDouble(token,(char **) NULL);
571    /* Y coordinate */
572    token[0]=','; while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
573    if ( token[0] == '\0' ) break;
574    if ( isalpha((int) token[0]) || token[0] == '#' ) {
575      (void) ThrowMagickException(exception,GetMagickModule(),
576            OptionError, "InvalidArgument", "'%s': %s", "sparse-color",
577            "Color found, instead of Y-coord");
578      error = MagickTrue;
579      break;
580    }
581    sparse_arguments[x++]=StringToDouble(token,(char **) NULL);
582    /* color values for this control point */
583#if 0
584    if ( (color_from_image ) {
585      /* get color from image */
586      /* HOW??? */
587    }
588    else
589#endif
590    {
591      /* color name or function given in string argument */
592      token[0]=','; while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
593      if ( token[0] == '\0' ) break;
594      if ( isalpha((int) token[0]) || token[0] == '#' ) {
595        /* Color string given */
596        (void) QueryColorCompliance(token,AllCompliance,&color,exception);
597        if ((GetPixelRedTraits(image) & UpdatePixelTrait) != 0)
598          sparse_arguments[x++] = QuantumScale*color.red;
599        if ((GetPixelGreenTraits(image) & UpdatePixelTrait) != 0)
600          sparse_arguments[x++] = QuantumScale*color.green;
601        if ((GetPixelBlueTraits(image) & UpdatePixelTrait) != 0)
602          sparse_arguments[x++] = QuantumScale*color.blue;
603        if (((GetPixelBlackTraits(image) & UpdatePixelTrait) != 0) &&
604            (image->colorspace == CMYKColorspace))
605          sparse_arguments[x++] = QuantumScale*color.black;
606        if (((GetPixelAlphaTraits(image) & UpdatePixelTrait) != 0) &&
607            (image->alpha_trait != UndefinedPixelTrait))
608          sparse_arguments[x++] = QuantumScale*color.alpha;
609      }
610      else {
611        /* Colors given as a set of floating point values - experimental */
612        /* NB: token contains the first floating point value to use! */
613        if ((GetPixelRedTraits(image) & UpdatePixelTrait) != 0)
614          {
615          while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
616          if ( token[0] == '\0' || isalpha((int)token[0]) || token[0] == '#' )
617            break;
618          sparse_arguments[x++]=StringToDouble(token,(char **) NULL);
619          token[0] = ','; /* used this token - get another */
620        }
621        if ((GetPixelGreenTraits(image) & UpdatePixelTrait) != 0)
622          {
623          while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
624          if ( token[0] == '\0' || isalpha((int)token[0]) || token[0] == '#' )
625            break;
626          sparse_arguments[x++]=StringToDouble(token,(char **) NULL);
627          token[0] = ','; /* used this token - get another */
628        }
629        if ((GetPixelBlueTraits(image) & UpdatePixelTrait) != 0)
630          {
631          while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
632          if ( token[0] == '\0' || isalpha((int)token[0]) || token[0] == '#' )
633            break;
634          sparse_arguments[x++]=StringToDouble(token,(char **) NULL);
635          token[0] = ','; /* used this token - get another */
636        }
637        if (((GetPixelBlackTraits(image) & UpdatePixelTrait) != 0) &&
638            (image->colorspace == CMYKColorspace))
639          {
640          while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
641          if ( token[0] == '\0' || isalpha((int)token[0]) || token[0] == '#' )
642            break;
643          sparse_arguments[x++]=StringToDouble(token,(char **) NULL);
644          token[0] = ','; /* used this token - get another */
645        }
646        if (((GetPixelAlphaTraits(image) & UpdatePixelTrait) != 0) &&
647            (image->alpha_trait != UndefinedPixelTrait))
648          {
649          while ( token[0] == ',' ) GetNextToken(p,&p,MagickPathExtent,token);
650          if ( token[0] == '\0' || isalpha((int)token[0]) || token[0] == '#' )
651            break;
652          sparse_arguments[x++]=StringToDouble(token,(char **) NULL);
653          token[0] = ','; /* used this token - get another */
654        }
655      }
656    }
657  }
658  if ( number_arguments != x && !error ) {
659    (void) ThrowMagickException(exception,GetMagickModule(),OptionError,
660      "InvalidArgument","'%s': %s","sparse-color","Argument Parsing Error");
661    sparse_arguments=(double *) RelinquishMagickMemory(sparse_arguments);
662    return( (Image *) NULL);
663  }
664  if ( error )
665    return( (Image *) NULL);
666
667  /* Call the Interpolation function with the parsed arguments */
668  sparse_image=SparseColorImage(image,method,number_arguments,sparse_arguments,
669    exception);
670  sparse_arguments=(double *) RelinquishMagickMemory(sparse_arguments);
671  return( sparse_image );
672}
673
674WandExport MagickBooleanType MogrifyImage(ImageInfo *image_info,const int argc,
675  const char **argv,Image **image,ExceptionInfo *exception)
676{
677  CompositeOperator
678    compose;
679
680  const char
681    *format,
682    *option;
683
684  double
685    attenuate;
686
687  DrawInfo
688    *draw_info;
689
690  GeometryInfo
691    geometry_info;
692
693  Image
694    *region_image;
695
696  ImageInfo
697    *mogrify_info;
698
699  MagickStatusType
700    status;
701
702  PixelInfo
703    fill;
704
705  MagickStatusType
706    flags;
707
708  PixelInterpolateMethod
709    interpolate_method;
710
711  QuantizeInfo
712    *quantize_info;
713
714  RectangleInfo
715    geometry,
716    region_geometry;
717
718  register ssize_t
719    i;
720
721  /*
722    Initialize method variables.
723  */
724  assert(image_info != (const ImageInfo *) NULL);
725  assert(image_info->signature == MagickCoreSignature);
726  assert(image != (Image **) NULL);
727  assert((*image)->signature == MagickCoreSignature);
728  if ((*image)->debug != MagickFalse)
729    (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",(*image)->filename);
730  if (argc < 0)
731    return(MagickTrue);
732  mogrify_info=CloneImageInfo(image_info);
733  draw_info=CloneDrawInfo(mogrify_info,(DrawInfo *) NULL);
734  quantize_info=AcquireQuantizeInfo(mogrify_info);
735  SetGeometryInfo(&geometry_info);
736  GetPixelInfo(*image,&fill);
737  fill=(*image)->background_color;
738  attenuate=1.0;
739  compose=(*image)->compose;
740  interpolate_method=UndefinedInterpolatePixel;
741  format=GetImageOption(mogrify_info,"format");
742  SetGeometry(*image,&region_geometry);
743  region_image=NewImageList();
744  /*
745    Transmogrify the image.
746  */
747  for (i=0; i < (ssize_t) argc; i++)
748  {
749    Image
750      *mogrify_image;
751
752    ssize_t
753      count;
754
755    option=argv[i];
756    if (IsCommandOption(option) == MagickFalse)
757      continue;
758    count=MagickMax(ParseCommandOption(MagickCommandOptions,MagickFalse,option),
759      0L);
760    if ((i+count) >= (ssize_t) argc)
761      break;
762    status=MogrifyImageInfo(mogrify_info,(int) count+1,argv+i,exception);
763    mogrify_image=(Image *) NULL;
764    switch (*(option+1))
765    {
766      case 'a':
767      {
768        if (LocaleCompare("adaptive-blur",option+1) == 0)
769          {
770            /*
771              Adaptive blur image.
772            */
773            (void) SyncImageSettings(mogrify_info,*image,exception);
774            flags=ParseGeometry(argv[i+1],&geometry_info);
775            if ((flags & SigmaValue) == 0)
776              geometry_info.sigma=1.0;
777            mogrify_image=AdaptiveBlurImage(*image,geometry_info.rho,
778              geometry_info.sigma,exception);
779            break;
780          }
781        if (LocaleCompare("adaptive-resize",option+1) == 0)
782          {
783            /*
784              Adaptive resize image.
785            */
786            (void) SyncImageSettings(mogrify_info,*image,exception);
787            (void) ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
788            mogrify_image=AdaptiveResizeImage(*image,geometry.width,
789              geometry.height,exception);
790            break;
791          }
792        if (LocaleCompare("adaptive-sharpen",option+1) == 0)
793          {
794            /*
795              Adaptive sharpen image.
796            */
797            (void) SyncImageSettings(mogrify_info,*image,exception);
798            flags=ParseGeometry(argv[i+1],&geometry_info);
799            if ((flags & SigmaValue) == 0)
800              geometry_info.sigma=1.0;
801            mogrify_image=AdaptiveSharpenImage(*image,geometry_info.rho,
802              geometry_info.sigma,exception);
803            break;
804          }
805        if (LocaleCompare("affine",option+1) == 0)
806          {
807            /*
808              Affine matrix.
809            */
810            if (*option == '+')
811              {
812                GetAffineMatrix(&draw_info->affine);
813                break;
814              }
815            (void) ParseAffineGeometry(argv[i+1],&draw_info->affine,exception);
816            break;
817          }
818        if (LocaleCompare("alpha",option+1) == 0)
819          {
820            AlphaChannelOption
821              alpha_type;
822
823            (void) SyncImageSettings(mogrify_info,*image,exception);
824            alpha_type=(AlphaChannelOption) ParseCommandOption(
825              MagickAlphaChannelOptions,MagickFalse,argv[i+1]);
826            (void) SetImageAlphaChannel(*image,alpha_type,exception);
827            break;
828          }
829        if (LocaleCompare("annotate",option+1) == 0)
830          {
831            char
832              *text,
833              geometry_str[MagickPathExtent];
834
835            /*
836              Annotate image.
837            */
838            (void) SyncImageSettings(mogrify_info,*image,exception);
839            SetGeometryInfo(&geometry_info);
840            flags=ParseGeometry(argv[i+1],&geometry_info);
841            if ((flags & SigmaValue) == 0)
842              geometry_info.sigma=geometry_info.rho;
843            text=InterpretImageProperties(mogrify_info,*image,argv[i+2],
844              exception);
845            if (text == (char *) NULL)
846              break;
847            (void) CloneString(&draw_info->text,text);
848            text=DestroyString(text);
849            (void) FormatLocaleString(geometry_str,MagickPathExtent,"%+f%+f",
850              geometry_info.xi,geometry_info.psi);
851            (void) CloneString(&draw_info->geometry,geometry_str);
852            draw_info->affine.sx=cos(DegreesToRadians(
853              fmod(geometry_info.rho,360.0)));
854            draw_info->affine.rx=sin(DegreesToRadians(
855              fmod(geometry_info.rho,360.0)));
856            draw_info->affine.ry=(-sin(DegreesToRadians(
857              fmod(geometry_info.sigma,360.0))));
858            draw_info->affine.sy=cos(DegreesToRadians(
859              fmod(geometry_info.sigma,360.0)));
860            (void) AnnotateImage(*image,draw_info,exception);
861            break;
862          }
863        if (LocaleCompare("antialias",option+1) == 0)
864          {
865            draw_info->stroke_antialias=(*option == '-') ? MagickTrue :
866              MagickFalse;
867            draw_info->text_antialias=(*option == '-') ? MagickTrue :
868              MagickFalse;
869            break;
870          }
871        if (LocaleCompare("attenuate",option+1) == 0)
872          {
873            if (*option == '+')
874              {
875                attenuate=1.0;
876                break;
877              }
878            attenuate=StringToDouble(argv[i+1],(char **) NULL);
879            break;
880          }
881        if (LocaleCompare("auto-gamma",option+1) == 0)
882          {
883            /*
884              Auto Adjust Gamma of image based on its mean
885            */
886            (void) SyncImageSettings(mogrify_info,*image,exception);
887            (void) AutoGammaImage(*image,exception);
888            break;
889          }
890        if (LocaleCompare("auto-level",option+1) == 0)
891          {
892            /*
893              Perfectly Normalize (max/min stretch) the image
894            */
895            (void) SyncImageSettings(mogrify_info,*image,exception);
896            (void) AutoLevelImage(*image,exception);
897            break;
898          }
899        if (LocaleCompare("auto-orient",option+1) == 0)
900          {
901            (void) SyncImageSettings(mogrify_info,*image,exception);
902            mogrify_image=AutoOrientImage(*image,(*image)->orientation,
903              exception);
904            break;
905          }
906        break;
907      }
908      case 'b':
909      {
910        if (LocaleCompare("black-threshold",option+1) == 0)
911          {
912            /*
913              Black threshold image.
914            */
915            (void) SyncImageSettings(mogrify_info,*image,exception);
916            (void) BlackThresholdImage(*image,argv[i+1],exception);
917            break;
918          }
919        if (LocaleCompare("blue-shift",option+1) == 0)
920          {
921            /*
922              Blue shift image.
923            */
924            (void) SyncImageSettings(mogrify_info,*image,exception);
925            geometry_info.rho=1.5;
926            if (*option == '-')
927              flags=ParseGeometry(argv[i+1],&geometry_info);
928            mogrify_image=BlueShiftImage(*image,geometry_info.rho,exception);
929            break;
930          }
931        if (LocaleCompare("blur",option+1) == 0)
932          {
933            /*
934              Gaussian blur image.
935            */
936            (void) SyncImageSettings(mogrify_info,*image,exception);
937            flags=ParseGeometry(argv[i+1],&geometry_info);
938            if ((flags & SigmaValue) == 0)
939              geometry_info.sigma=1.0;
940            if ((flags & XiValue) == 0)
941              geometry_info.xi=0.0;
942            mogrify_image=BlurImage(*image,geometry_info.rho,
943              geometry_info.sigma,exception);
944            break;
945          }
946        if (LocaleCompare("border",option+1) == 0)
947          {
948            /*
949              Surround image with a border of solid color.
950            */
951            (void) SyncImageSettings(mogrify_info,*image,exception);
952            flags=ParsePageGeometry(*image,argv[i+1],&geometry,exception);
953            mogrify_image=BorderImage(*image,&geometry,compose,exception);
954            break;
955          }
956        if (LocaleCompare("bordercolor",option+1) == 0)
957          {
958            if (*option == '+')
959              {
960                (void) QueryColorCompliance(MogrifyBorderColor,AllCompliance,
961                  &draw_info->border_color,exception);
962                break;
963              }
964            (void) QueryColorCompliance(argv[i+1],AllCompliance,
965              &draw_info->border_color,exception);
966            break;
967          }
968        if (LocaleCompare("box",option+1) == 0)
969          {
970            (void) QueryColorCompliance(argv[i+1],AllCompliance,
971              &draw_info->undercolor,exception);
972            break;
973          }
974        if (LocaleCompare("brightness-contrast",option+1) == 0)
975          {
976            double
977              brightness,
978              contrast;
979
980            /*
981              Brightness / contrast image.
982            */
983            (void) SyncImageSettings(mogrify_info,*image,exception);
984            flags=ParseGeometry(argv[i+1],&geometry_info);
985            brightness=geometry_info.rho;
986            contrast=0.0;
987            if ((flags & SigmaValue) != 0)
988              contrast=geometry_info.sigma;
989            (void) BrightnessContrastImage(*image,brightness,contrast,
990              exception);
991            break;
992          }
993        break;
994      }
995      case 'c':
996      {
997        if (LocaleCompare("canny",option+1) == 0)
998          {
999            /*
1000              Detect edges in the image.
1001            */
1002            (void) SyncImageSettings(mogrify_info,*image,exception);
1003            flags=ParseGeometry(argv[i+1],&geometry_info);
1004            if ((flags & SigmaValue) == 0)
1005              geometry_info.sigma=1.0;
1006            if ((flags & XiValue) == 0)
1007              geometry_info.xi=0.10;
1008            if ((flags & PsiValue) == 0)
1009              geometry_info.psi=0.30;
1010            if ((flags & PercentValue) != 0)
1011              {
1012                geometry_info.xi/=100.0;
1013                geometry_info.psi/=100.0;
1014              }
1015            mogrify_image=CannyEdgeImage(*image,geometry_info.rho,
1016              geometry_info.sigma,geometry_info.xi,geometry_info.psi,exception);
1017            break;
1018          }
1019        if (LocaleCompare("cdl",option+1) == 0)
1020          {
1021            char
1022              *color_correction_collection;
1023
1024            /*
1025              Color correct with a color decision list.
1026            */
1027            (void) SyncImageSettings(mogrify_info,*image,exception);
1028            color_correction_collection=FileToString(argv[i+1],~0UL,exception);
1029            if (color_correction_collection == (char *) NULL)
1030              break;
1031            (void) ColorDecisionListImage(*image,color_correction_collection,
1032              exception);
1033            break;
1034          }
1035        if (LocaleCompare("channel",option+1) == 0)
1036          {
1037            ChannelType
1038              channel;
1039
1040            (void) SyncImageSettings(mogrify_info,*image,exception);
1041            if (*option == '+')
1042              {
1043                (void) SetPixelChannelMask(*image,DefaultChannels);
1044                break;
1045              }
1046            channel=(ChannelType) ParseChannelOption(argv[i+1]);
1047            (void) SetPixelChannelMask(*image,channel);
1048            break;
1049          }
1050        if (LocaleCompare("charcoal",option+1) == 0)
1051          {
1052            /*
1053              Charcoal image.
1054            */
1055            (void) SyncImageSettings(mogrify_info,*image,exception);
1056            flags=ParseGeometry(argv[i+1],&geometry_info);
1057            if ((flags & SigmaValue) == 0)
1058              geometry_info.sigma=1.0;
1059            if ((flags & XiValue) == 0)
1060              geometry_info.xi=1.0;
1061            mogrify_image=CharcoalImage(*image,geometry_info.rho,
1062              geometry_info.sigma,exception);
1063            break;
1064          }
1065        if (LocaleCompare("chop",option+1) == 0)
1066          {
1067            /*
1068              Chop the image.
1069            */
1070            (void) SyncImageSettings(mogrify_info,*image,exception);
1071            (void) ParseGravityGeometry(*image,argv[i+1],&geometry,exception);
1072            mogrify_image=ChopImage(*image,&geometry,exception);
1073            break;
1074          }
1075        if (LocaleCompare("clip",option+1) == 0)
1076          {
1077            (void) SyncImageSettings(mogrify_info,*image,exception);
1078            if (*option == '+')
1079              {
1080                (void) SetImageMask(*image,ReadPixelMask,(Image *) NULL,
1081                  exception);
1082                break;
1083              }
1084            (void) ClipImage(*image,exception);
1085            break;
1086          }
1087        if (LocaleCompare("clip-mask",option+1) == 0)
1088          {
1089            CacheView
1090              *mask_view;
1091
1092            Image
1093              *mask_image;
1094
1095            register Quantum
1096              *magick_restrict q;
1097
1098            register ssize_t
1099              x;
1100
1101            ssize_t
1102              y;
1103
1104            (void) SyncImageSettings(mogrify_info,*image,exception);
1105            if (*option == '+')
1106              {
1107                /*
1108                  Remove a mask.
1109                */
1110                (void) SetImageMask(*image,ReadPixelMask,(Image *) NULL,
1111                  exception);
1112                break;
1113              }
1114            /*
1115              Set the image mask.
1116              FUTURE: This Should Be a SetImageAlphaChannel() call, Or two.
1117            */
1118            mask_image=GetImageCache(mogrify_info,argv[i+1],exception);
1119            if (mask_image == (Image *) NULL)
1120              break;
1121            if (SetImageStorageClass(mask_image,DirectClass,exception) == MagickFalse)
1122              return(MagickFalse);
1123            mask_view=AcquireAuthenticCacheView(mask_image,exception);
1124            for (y=0; y < (ssize_t) mask_image->rows; y++)
1125            {
1126              q=GetCacheViewAuthenticPixels(mask_view,0,y,mask_image->columns,1,
1127                exception);
1128              if (q == (Quantum *) NULL)
1129                break;
1130              for (x=0; x < (ssize_t) mask_image->columns; x++)
1131              {
1132                if (mask_image->alpha_trait == UndefinedPixelTrait)
1133                  SetPixelAlpha(mask_image,(Quantum)
1134                    GetPixelIntensity(mask_image,q),q);
1135                SetPixelRed(mask_image,GetPixelAlpha(mask_image,q),q);
1136                SetPixelGreen(mask_image,GetPixelAlpha(mask_image,q),q);
1137                SetPixelBlue(mask_image,GetPixelAlpha(mask_image,q),q);
1138                q+=GetPixelChannels(mask_image);
1139              }
1140              if (SyncCacheViewAuthenticPixels(mask_view,exception) == MagickFalse)
1141                break;
1142            }
1143            mask_view=DestroyCacheView(mask_view);
1144            mask_image->alpha_trait=BlendPixelTrait;
1145            (void) SetImageMask(*image,ReadPixelMask,mask_image,exception);
1146            break;
1147          }
1148        if (LocaleCompare("clip-path",option+1) == 0)
1149          {
1150            (void) SyncImageSettings(mogrify_info,*image,exception);
1151            (void) ClipImagePath(*image,argv[i+1],*option == '-' ? MagickTrue :
1152              MagickFalse,exception);
1153            break;
1154          }
1155        if (LocaleCompare("colorize",option+1) == 0)
1156          {
1157            /*
1158              Colorize the image.
1159            */
1160            (void) SyncImageSettings(mogrify_info,*image,exception);
1161            mogrify_image=ColorizeImage(*image,argv[i+1],&fill,exception);
1162            break;
1163          }
1164        if (LocaleCompare("color-matrix",option+1) == 0)
1165          {
1166            KernelInfo
1167              *kernel;
1168
1169            (void) SyncImageSettings(mogrify_info,*image,exception);
1170            kernel=AcquireKernelInfo(argv[i+1],exception);
1171            if (kernel == (KernelInfo *) NULL)
1172              break;
1173            /* FUTURE: check on size of the matrix */
1174            mogrify_image=ColorMatrixImage(*image,kernel,exception);
1175            kernel=DestroyKernelInfo(kernel);
1176            break;
1177          }
1178        if (LocaleCompare("colors",option+1) == 0)
1179          {
1180            /*
1181              Reduce the number of colors in the image.
1182            */
1183            (void) SyncImageSettings(mogrify_info,*image,exception);
1184            quantize_info->number_colors=StringToUnsignedLong(argv[i+1]);
1185            if (quantize_info->number_colors == 0)
1186              break;
1187            if (((*image)->storage_class == DirectClass) ||
1188                (*image)->colors > quantize_info->number_colors)
1189              (void) QuantizeImage(quantize_info,*image,exception);
1190            else
1191              (void) CompressImageColormap(*image,exception);
1192            break;
1193          }
1194        if (LocaleCompare("colorspace",option+1) == 0)
1195          {
1196            ColorspaceType
1197              colorspace;
1198
1199            (void) SyncImageSettings(mogrify_info,*image,exception);
1200            if (*option == '+')
1201              {
1202                (void) TransformImageColorspace(*image,sRGBColorspace,
1203                  exception);
1204                break;
1205              }
1206            colorspace=(ColorspaceType) ParseCommandOption(
1207              MagickColorspaceOptions,MagickFalse,argv[i+1]);
1208            (void) TransformImageColorspace(*image,colorspace,exception);
1209            break;
1210          }
1211        if (LocaleCompare("compose",option+1) == 0)
1212          {
1213            (void) SyncImageSettings(mogrify_info,*image,exception);
1214            compose=(CompositeOperator) ParseCommandOption(MagickComposeOptions,
1215              MagickFalse,argv[i+1]);
1216            break;
1217          }
1218        if (LocaleCompare("connected-components",option+1) == 0)
1219          {
1220            (void) SyncImageSettings(mogrify_info,*image,exception);
1221            mogrify_image=ConnectedComponentsImage(*image,(size_t)
1222              StringToInteger(argv[i+1]),(CCObjectInfo **) NULL,exception);
1223            break;
1224          }
1225        if (LocaleCompare("contrast",option+1) == 0)
1226          {
1227            (void) SyncImageSettings(mogrify_info,*image,exception);
1228            (void) ContrastImage(*image,(*option == '-') ? MagickTrue :
1229              MagickFalse,exception);
1230            break;
1231          }
1232        if (LocaleCompare("contrast-stretch",option+1) == 0)
1233          {
1234            double
1235              black_point,
1236              white_point;
1237
1238            /*
1239              Contrast stretch image.
1240            */
1241            (void) SyncImageSettings(mogrify_info,*image,exception);
1242            flags=ParseGeometry(argv[i+1],&geometry_info);
1243            black_point=geometry_info.rho;
1244            white_point=(flags & SigmaValue) != 0 ? geometry_info.sigma :
1245              black_point;
1246            if ((flags & PercentValue) != 0)
1247              {
1248                black_point*=(double) (*image)->columns*(*image)->rows/100.0;
1249                white_point*=(double) (*image)->columns*(*image)->rows/100.0;
1250              }
1251            white_point=(double) (*image)->columns*(*image)->rows-
1252              white_point;
1253            (void) ContrastStretchImage(*image,black_point,white_point,
1254              exception);
1255            break;
1256          }
1257        if (LocaleCompare("convolve",option+1) == 0)
1258          {
1259            double
1260              gamma;
1261
1262            KernelInfo
1263              *kernel_info;
1264
1265            register ssize_t
1266              j;
1267
1268            size_t
1269              extent;
1270
1271            (void) SyncImageSettings(mogrify_info,*image,exception);
1272            kernel_info=AcquireKernelInfo(argv[i+1],exception);
1273            if (kernel_info == (KernelInfo *) NULL)
1274              break;
1275            extent=kernel_info->width*kernel_info->height;
1276            gamma=0.0;
1277            for (j=0; j < (ssize_t) extent; j++)
1278              gamma+=kernel_info->values[j];
1279            gamma=1.0/(fabs((double) gamma) <= MagickEpsilon ? 1.0 : gamma);
1280            for (j=0; j < (ssize_t) extent; j++)
1281              kernel_info->values[j]*=gamma;
1282            mogrify_image=MorphologyImage(*image,CorrelateMorphology,1,
1283              kernel_info,exception);
1284            kernel_info=DestroyKernelInfo(kernel_info);
1285            break;
1286          }
1287        if (LocaleCompare("crop",option+1) == 0)
1288          {
1289            /*
1290              Crop a image to a smaller size
1291            */
1292            (void) SyncImageSettings(mogrify_info,*image,exception);
1293            mogrify_image=CropImageToTiles(*image,argv[i+1],exception);
1294            break;
1295          }
1296        if (LocaleCompare("cycle",option+1) == 0)
1297          {
1298            /*
1299              Cycle an image colormap.
1300            */
1301            (void) SyncImageSettings(mogrify_info,*image,exception);
1302            (void) CycleColormapImage(*image,(ssize_t) StringToLong(argv[i+1]),
1303              exception);
1304            break;
1305          }
1306        break;
1307      }
1308      case 'd':
1309      {
1310        if (LocaleCompare("decipher",option+1) == 0)
1311          {
1312            StringInfo
1313              *passkey;
1314
1315            /*
1316              Decipher pixels.
1317            */
1318            (void) SyncImageSettings(mogrify_info,*image,exception);
1319            passkey=FileToStringInfo(argv[i+1],~0UL,exception);
1320            if (passkey != (StringInfo *) NULL)
1321              {
1322                (void) PasskeyDecipherImage(*image,passkey,exception);
1323                passkey=DestroyStringInfo(passkey);
1324              }
1325            break;
1326          }
1327        if (LocaleCompare("density",option+1) == 0)
1328          {
1329            /*
1330              Set image density.
1331            */
1332            (void) CloneString(&draw_info->density,argv[i+1]);
1333            break;
1334          }
1335        if (LocaleCompare("depth",option+1) == 0)
1336          {
1337            (void) SyncImageSettings(mogrify_info,*image,exception);
1338            if (*option == '+')
1339              {
1340                (void) SetImageDepth(*image,MAGICKCORE_QUANTUM_DEPTH,exception);
1341                break;
1342              }
1343            (void) SetImageDepth(*image,StringToUnsignedLong(argv[i+1]),
1344              exception);
1345            break;
1346          }
1347        if (LocaleCompare("deskew",option+1) == 0)
1348          {
1349            double
1350              threshold;
1351
1352            /*
1353              Straighten the image.
1354            */
1355            (void) SyncImageSettings(mogrify_info,*image,exception);
1356            if (*option == '+')
1357              threshold=40.0*QuantumRange/100.0;
1358            else
1359              threshold=StringToDoubleInterval(argv[i+1],(double) QuantumRange+
1360                1.0);
1361            mogrify_image=DeskewImage(*image,threshold,exception);
1362            break;
1363          }
1364        if (LocaleCompare("despeckle",option+1) == 0)
1365          {
1366            /*
1367              Reduce the speckles within an image.
1368            */
1369            (void) SyncImageSettings(mogrify_info,*image,exception);
1370            mogrify_image=DespeckleImage(*image,exception);
1371            break;
1372          }
1373        if (LocaleCompare("display",option+1) == 0)
1374          {
1375            (void) CloneString(&draw_info->server_name,argv[i+1]);
1376            break;
1377          }
1378        if (LocaleCompare("distort",option+1) == 0)
1379          {
1380            char
1381              *args,
1382              token[MagickPathExtent];
1383
1384            const char
1385              *p;
1386
1387            DistortMethod
1388              method;
1389
1390            double
1391              *arguments;
1392
1393            register ssize_t
1394              x;
1395
1396            size_t
1397              number_arguments;
1398
1399            /*
1400              Distort image.
1401            */
1402            (void) SyncImageSettings(mogrify_info,*image,exception);
1403            method=(DistortMethod) ParseCommandOption(MagickDistortOptions,
1404              MagickFalse,argv[i+1]);
1405            if (method == ResizeDistortion)
1406              {
1407                 double
1408                   resize_args[2];
1409
1410                 /*
1411                   Special Case - Argument is actually a resize geometry!
1412                   Convert that to an appropriate distortion argument array.
1413                 */
1414                 (void) ParseRegionGeometry(*image,argv[i+2],&geometry,
1415                   exception);
1416                 resize_args[0]=(double) geometry.width;
1417                 resize_args[1]=(double) geometry.height;
1418                 mogrify_image=DistortImage(*image,method,(size_t)2,
1419                   resize_args,MagickTrue,exception);
1420                 break;
1421              }
1422            args=InterpretImageProperties(mogrify_info,*image,argv[i+2],
1423              exception);
1424            if (args == (char *) NULL)
1425              break;
1426            p=(char *) args;
1427            for (x=0; *p != '\0'; x++)
1428            {
1429              GetNextToken(p,&p,MagickPathExtent,token);
1430              if (*token == ',')
1431                GetNextToken(p,&p,MagickPathExtent,token);
1432            }
1433            number_arguments=(size_t) x;
1434            arguments=(double *) AcquireQuantumMemory(number_arguments,
1435              sizeof(*arguments));
1436            if (arguments == (double *) NULL)
1437              ThrowWandFatalException(ResourceLimitFatalError,
1438                "MemoryAllocationFailed",(*image)->filename);
1439            (void) ResetMagickMemory(arguments,0,number_arguments*
1440              sizeof(*arguments));
1441            p=(char *) args;
1442            for (x=0; (x < (ssize_t) number_arguments) && (*p != '\0'); x++)
1443            {
1444              GetNextToken(p,&p,MagickPathExtent,token);
1445              if (*token == ',')
1446                GetNextToken(p,&p,MagickPathExtent,token);
1447              arguments[x]=StringToDouble(token,(char **) NULL);
1448            }
1449            args=DestroyString(args);
1450            mogrify_image=DistortImage(*image,method,number_arguments,arguments,
1451              (*option == '+') ? MagickTrue : MagickFalse,exception);
1452            arguments=(double *) RelinquishMagickMemory(arguments);
1453            break;
1454          }
1455        if (LocaleCompare("dither",option+1) == 0)
1456          {
1457            if (*option == '+')
1458              {
1459                quantize_info->dither_method=NoDitherMethod;
1460                break;
1461              }
1462            quantize_info->dither_method=(DitherMethod) ParseCommandOption(
1463              MagickDitherOptions,MagickFalse,argv[i+1]);
1464            break;
1465          }
1466        if (LocaleCompare("draw",option+1) == 0)
1467          {
1468            /*
1469              Draw image.
1470            */
1471            (void) SyncImageSettings(mogrify_info,*image,exception);
1472            (void) CloneString(&draw_info->primitive,argv[i+1]);
1473            (void) DrawImage(*image,draw_info,exception);
1474            break;
1475          }
1476        break;
1477      }
1478      case 'e':
1479      {
1480        if (LocaleCompare("edge",option+1) == 0)
1481          {
1482            /*
1483              Enhance edges in the image.
1484            */
1485            (void) SyncImageSettings(mogrify_info,*image,exception);
1486            flags=ParseGeometry(argv[i+1],&geometry_info);
1487            mogrify_image=EdgeImage(*image,geometry_info.rho,exception);
1488            break;
1489          }
1490        if (LocaleCompare("emboss",option+1) == 0)
1491          {
1492            /*
1493              Emboss image.
1494            */
1495            (void) SyncImageSettings(mogrify_info,*image,exception);
1496            flags=ParseGeometry(argv[i+1],&geometry_info);
1497            if ((flags & SigmaValue) == 0)
1498              geometry_info.sigma=1.0;
1499            mogrify_image=EmbossImage(*image,geometry_info.rho,
1500              geometry_info.sigma,exception);
1501            break;
1502          }
1503        if (LocaleCompare("encipher",option+1) == 0)
1504          {
1505            StringInfo
1506              *passkey;
1507
1508            /*
1509              Encipher pixels.
1510            */
1511            (void) SyncImageSettings(mogrify_info,*image,exception);
1512            passkey=FileToStringInfo(argv[i+1],~0UL,exception);
1513            if (passkey != (StringInfo *) NULL)
1514              {
1515                (void) PasskeyEncipherImage(*image,passkey,exception);
1516                passkey=DestroyStringInfo(passkey);
1517              }
1518            break;
1519          }
1520        if (LocaleCompare("encoding",option+1) == 0)
1521          {
1522            (void) CloneString(&draw_info->encoding,argv[i+1]);
1523            break;
1524          }
1525        if (LocaleCompare("enhance",option+1) == 0)
1526          {
1527            /*
1528              Enhance image.
1529            */
1530            (void) SyncImageSettings(mogrify_info,*image,exception);
1531            mogrify_image=EnhanceImage(*image,exception);
1532            break;
1533          }
1534        if (LocaleCompare("equalize",option+1) == 0)
1535          {
1536            /*
1537              Equalize image.
1538            */
1539            (void) SyncImageSettings(mogrify_info,*image,exception);
1540            (void) EqualizeImage(*image,exception);
1541            break;
1542          }
1543        if (LocaleCompare("evaluate",option+1) == 0)
1544          {
1545            double
1546              constant;
1547
1548            MagickEvaluateOperator
1549              op;
1550
1551            (void) SyncImageSettings(mogrify_info,*image,exception);
1552            op=(MagickEvaluateOperator) ParseCommandOption(
1553              MagickEvaluateOptions,MagickFalse,argv[i+1]);
1554            constant=StringToDoubleInterval(argv[i+2],(double) QuantumRange+
1555              1.0);
1556            (void) EvaluateImage(*image,op,constant,exception);
1557            break;
1558          }
1559        if (LocaleCompare("extent",option+1) == 0)
1560          {
1561            /*
1562              Set the image extent.
1563            */
1564            (void) SyncImageSettings(mogrify_info,*image,exception);
1565            flags=ParseGravityGeometry(*image,argv[i+1],&geometry,exception);
1566            if (geometry.width == 0)
1567              geometry.width=(*image)->columns;
1568            if (geometry.height == 0)
1569              geometry.height=(*image)->rows;
1570            mogrify_image=ExtentImage(*image,&geometry,exception);
1571            break;
1572          }
1573        break;
1574      }
1575      case 'f':
1576      {
1577        if (LocaleCompare("family",option+1) == 0)
1578          {
1579            if (*option == '+')
1580              {
1581                if (draw_info->family != (char *) NULL)
1582                  draw_info->family=DestroyString(draw_info->family);
1583                break;
1584              }
1585            (void) CloneString(&draw_info->family,argv[i+1]);
1586            break;
1587          }
1588        if (LocaleCompare("features",option+1) == 0)
1589          {
1590            if (*option == '+')
1591              {
1592                (void) DeleteImageArtifact(*image,"identify:features");
1593                break;
1594              }
1595            (void) SetImageArtifact(*image,"vdentify:features",argv[i+1]);
1596            (void) SetImageArtifact(*image,"verbose","true");
1597            break;
1598          }
1599        if (LocaleCompare("fill",option+1) == 0)
1600          {
1601            ExceptionInfo
1602              *sans;
1603
1604            PixelInfo
1605              color;
1606
1607            GetPixelInfo(*image,&fill);
1608            if (*option == '+')
1609              {
1610                (void) QueryColorCompliance("none",AllCompliance,&fill,
1611                  exception);
1612                draw_info->fill=fill;
1613                if (draw_info->fill_pattern != (Image *) NULL)
1614                  draw_info->fill_pattern=DestroyImage(draw_info->fill_pattern);
1615                break;
1616              }
1617            sans=AcquireExceptionInfo();
1618            status=QueryColorCompliance(argv[i+1],AllCompliance,&color,sans);
1619            sans=DestroyExceptionInfo(sans);
1620            if (status == MagickFalse)
1621              draw_info->fill_pattern=GetImageCache(mogrify_info,argv[i+1],
1622                exception);
1623            else
1624              draw_info->fill=fill=color;
1625            break;
1626          }
1627        if (LocaleCompare("flip",option+1) == 0)
1628          {
1629            /*
1630              Flip image scanlines.
1631            */
1632            (void) SyncImageSettings(mogrify_info,*image,exception);
1633            mogrify_image=FlipImage(*image,exception);
1634            break;
1635          }
1636        if (LocaleCompare("floodfill",option+1) == 0)
1637          {
1638            PixelInfo
1639              target;
1640
1641            /*
1642              Floodfill image.
1643            */
1644            (void) SyncImageSettings(mogrify_info,*image,exception);
1645            (void) ParsePageGeometry(*image,argv[i+1],&geometry,exception);
1646            (void) QueryColorCompliance(argv[i+2],AllCompliance,&target,
1647              exception);
1648            (void) FloodfillPaintImage(*image,draw_info,&target,geometry.x,
1649              geometry.y,*option == '-' ? MagickFalse : MagickTrue,exception);
1650            break;
1651          }
1652        if (LocaleCompare("flop",option+1) == 0)
1653          {
1654            /*
1655              Flop image scanlines.
1656            */
1657            (void) SyncImageSettings(mogrify_info,*image,exception);
1658            mogrify_image=FlopImage(*image,exception);
1659            break;
1660          }
1661        if (LocaleCompare("font",option+1) == 0)
1662          {
1663            if (*option == '+')
1664              {
1665                if (draw_info->font != (char *) NULL)
1666                  draw_info->font=DestroyString(draw_info->font);
1667                break;
1668              }
1669            (void) CloneString(&draw_info->font,argv[i+1]);
1670            break;
1671          }
1672        if (LocaleCompare("format",option+1) == 0)
1673          {
1674            format=argv[i+1];
1675            break;
1676          }
1677        if (LocaleCompare("frame",option+1) == 0)
1678          {
1679            FrameInfo
1680              frame_info;
1681
1682            /*
1683              Surround image with an ornamental border.
1684            */
1685            (void) SyncImageSettings(mogrify_info,*image,exception);
1686            flags=ParsePageGeometry(*image,argv[i+1],&geometry,exception);
1687            frame_info.width=geometry.width;
1688            frame_info.height=geometry.height;
1689            frame_info.outer_bevel=geometry.x;
1690            frame_info.inner_bevel=geometry.y;
1691            frame_info.x=(ssize_t) frame_info.width;
1692            frame_info.y=(ssize_t) frame_info.height;
1693            frame_info.width=(*image)->columns+2*frame_info.width;
1694            frame_info.height=(*image)->rows+2*frame_info.height;
1695            mogrify_image=FrameImage(*image,&frame_info,compose,exception);
1696            break;
1697          }
1698        if (LocaleCompare("function",option+1) == 0)
1699          {
1700            char
1701              *arguments,
1702              token[MagickPathExtent];
1703
1704            const char
1705              *p;
1706
1707            double
1708              *parameters;
1709
1710            MagickFunction
1711              function;
1712
1713            register ssize_t
1714              x;
1715
1716            size_t
1717              number_parameters;
1718
1719            /*
1720              Function Modify Image Values
1721            */
1722            (void) SyncImageSettings(mogrify_info,*image,exception);
1723            function=(MagickFunction) ParseCommandOption(MagickFunctionOptions,
1724              MagickFalse,argv[i+1]);
1725            arguments=InterpretImageProperties(mogrify_info,*image,argv[i+2],
1726              exception);
1727            if (arguments == (char *) NULL)
1728              break;
1729            p=(char *) arguments;
1730            for (x=0; *p != '\0'; x++)
1731            {
1732              GetNextToken(p,&p,MagickPathExtent,token);
1733              if (*token == ',')
1734                GetNextToken(p,&p,MagickPathExtent,token);
1735            }
1736            number_parameters=(size_t) x;
1737            parameters=(double *) AcquireQuantumMemory(number_parameters,
1738              sizeof(*parameters));
1739            if (parameters == (double *) NULL)
1740              ThrowWandFatalException(ResourceLimitFatalError,
1741                "MemoryAllocationFailed",(*image)->filename);
1742            (void) ResetMagickMemory(parameters,0,number_parameters*
1743              sizeof(*parameters));
1744            p=(char *) arguments;
1745            for (x=0; (x < (ssize_t) number_parameters) && (*p != '\0'); x++)
1746            {
1747              GetNextToken(p,&p,MagickPathExtent,token);
1748              if (*token == ',')
1749                GetNextToken(p,&p,MagickPathExtent,token);
1750              parameters[x]=StringToDouble(token,(char **) NULL);
1751            }
1752            arguments=DestroyString(arguments);
1753            (void) FunctionImage(*image,function,number_parameters,parameters,
1754              exception);
1755            parameters=(double *) RelinquishMagickMemory(parameters);
1756            break;
1757          }
1758        break;
1759      }
1760      case 'g':
1761      {
1762        if (LocaleCompare("gamma",option+1) == 0)
1763          {
1764            /*
1765              Gamma image.
1766            */
1767            (void) SyncImageSettings(mogrify_info,*image,exception);
1768            if (*option == '+')
1769              (*image)->gamma=StringToDouble(argv[i+1],(char **) NULL);
1770            else
1771              (void) GammaImage(*image,StringToDouble(argv[i+1],(char **) NULL),
1772                exception);
1773            break;
1774          }
1775        if ((LocaleCompare("gaussian-blur",option+1) == 0) ||
1776            (LocaleCompare("gaussian",option+1) == 0))
1777          {
1778            /*
1779              Gaussian blur image.
1780            */
1781            (void) SyncImageSettings(mogrify_info,*image,exception);
1782            flags=ParseGeometry(argv[i+1],&geometry_info);
1783            if ((flags & SigmaValue) == 0)
1784              geometry_info.sigma=1.0;
1785            mogrify_image=GaussianBlurImage(*image,geometry_info.rho,
1786              geometry_info.sigma,exception);
1787            break;
1788          }
1789        if (LocaleCompare("geometry",option+1) == 0)
1790          {
1791              /*
1792                Record Image offset, Resize last image.
1793              */
1794            (void) SyncImageSettings(mogrify_info,*image,exception);
1795            if (*option == '+')
1796              {
1797                if ((*image)->geometry != (char *) NULL)
1798                  (*image)->geometry=DestroyString((*image)->geometry);
1799                break;
1800              }
1801            flags=ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
1802            if (((flags & XValue) != 0) || ((flags & YValue) != 0))
1803              (void) CloneString(&(*image)->geometry,argv[i+1]);
1804            else
1805              mogrify_image=ResizeImage(*image,geometry.width,geometry.height,
1806                (*image)->filter,exception);
1807            break;
1808          }
1809        if (LocaleCompare("gravity",option+1) == 0)
1810          {
1811            if (*option == '+')
1812              {
1813                draw_info->gravity=UndefinedGravity;
1814                break;
1815              }
1816            draw_info->gravity=(GravityType) ParseCommandOption(
1817              MagickGravityOptions,MagickFalse,argv[i+1]);
1818            break;
1819          }
1820        if (LocaleCompare("grayscale",option+1) == 0)
1821          {
1822            PixelIntensityMethod
1823              method;
1824
1825            (void) SyncImageSettings(mogrify_info,*image,exception);
1826            method=(PixelIntensityMethod) ParseCommandOption(
1827              MagickPixelIntensityOptions,MagickFalse,argv[i+1]);
1828            (void) GrayscaleImage(*image,method,exception);
1829            break;
1830          }
1831        break;
1832      }
1833      case 'h':
1834      {
1835        if (LocaleCompare("highlight-color",option+1) == 0)
1836          {
1837            (void) SetImageArtifact(*image,option+1,argv[i+1]);
1838            break;
1839          }
1840        if (LocaleCompare("hough-lines",option+1) == 0)
1841          {
1842            /*
1843              Detect edges in the image.
1844            */
1845            (void) SyncImageSettings(mogrify_info,*image,exception);
1846            flags=ParseGeometry(argv[i+1],&geometry_info);
1847            if ((flags & SigmaValue) == 0)
1848              geometry_info.sigma=geometry_info.rho;
1849            if ((flags & XiValue) == 0)
1850              geometry_info.xi=40;
1851            mogrify_image=HoughLineImage(*image,(size_t) geometry_info.rho,
1852              (size_t) geometry_info.sigma,(size_t) geometry_info.xi,exception);
1853            break;
1854          }
1855        break;
1856      }
1857      case 'i':
1858      {
1859        if (LocaleCompare("identify",option+1) == 0)
1860          {
1861            char
1862              *text;
1863
1864            (void) SyncImageSettings(mogrify_info,*image,exception);
1865            if (format == (char *) NULL)
1866              {
1867                (void) IdentifyImage(*image,stdout,mogrify_info->verbose,
1868                  exception);
1869                break;
1870              }
1871            text=InterpretImageProperties(mogrify_info,*image,format,
1872              exception);
1873            if (text == (char *) NULL)
1874              break;
1875            (void) fputs(text,stdout);
1876            text=DestroyString(text);
1877            break;
1878          }
1879        if (LocaleCompare("implode",option+1) == 0)
1880          {
1881            /*
1882              Implode image.
1883            */
1884            (void) SyncImageSettings(mogrify_info,*image,exception);
1885            (void) ParseGeometry(argv[i+1],&geometry_info);
1886            mogrify_image=ImplodeImage(*image,geometry_info.rho,
1887              interpolate_method,exception);
1888            break;
1889          }
1890        if (LocaleCompare("interline-spacing",option+1) == 0)
1891          {
1892            if (*option == '+')
1893              (void) ParseGeometry("0",&geometry_info);
1894            else
1895              (void) ParseGeometry(argv[i+1],&geometry_info);
1896            draw_info->interline_spacing=geometry_info.rho;
1897            break;
1898          }
1899        if (LocaleCompare("interpolate",option+1) == 0)
1900          {
1901            interpolate_method=(PixelInterpolateMethod) ParseCommandOption(
1902              MagickInterpolateOptions,MagickFalse,argv[i+1]);
1903            break;
1904          }
1905        if (LocaleCompare("interword-spacing",option+1) == 0)
1906          {
1907            if (*option == '+')
1908              (void) ParseGeometry("0",&geometry_info);
1909            else
1910              (void) ParseGeometry(argv[i+1],&geometry_info);
1911            draw_info->interword_spacing=geometry_info.rho;
1912            break;
1913          }
1914        if (LocaleCompare("interpolative-resize",option+1) == 0)
1915          {
1916            /*
1917              Interpolative resize image.
1918            */
1919            (void) SyncImageSettings(mogrify_info,*image,exception);
1920            (void) ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
1921            mogrify_image=InterpolativeResizeImage(*image,geometry.width,
1922              geometry.height,interpolate_method,exception);
1923            break;
1924          }
1925        break;
1926      }
1927      case 'k':
1928      {
1929        if (LocaleCompare("kerning",option+1) == 0)
1930          {
1931            if (*option == '+')
1932              (void) ParseGeometry("0",&geometry_info);
1933            else
1934              (void) ParseGeometry(argv[i+1],&geometry_info);
1935            draw_info->kerning=geometry_info.rho;
1936            break;
1937          }
1938        if (LocaleCompare("kuwahara",option+1) == 0)
1939          {
1940            /*
1941              Edge preserving blur.
1942            */
1943            (void) SyncImageSettings(mogrify_info,*image,exception);
1944            flags=ParseGeometry(argv[i+1],&geometry_info);
1945            if ((flags & SigmaValue) == 0)
1946              geometry_info.sigma=geometry_info.rho-0.5;
1947            mogrify_image=KuwaharaImage(*image,geometry_info.rho,
1948              geometry_info.sigma,exception);
1949            break;
1950          }
1951        break;
1952      }
1953      case 'l':
1954      {
1955        if (LocaleCompare("lat",option+1) == 0)
1956          {
1957            /*
1958              Local adaptive threshold image.
1959            */
1960            (void) SyncImageSettings(mogrify_info,*image,exception);
1961            flags=ParseGeometry(argv[i+1],&geometry_info);
1962            if ((flags & PercentValue) != 0)
1963              geometry_info.xi=(double) QuantumRange*geometry_info.xi/100.0;
1964            mogrify_image=AdaptiveThresholdImage(*image,(size_t)
1965              geometry_info.rho,(size_t) geometry_info.sigma,(double)
1966              geometry_info.xi,exception);
1967            break;
1968          }
1969        if (LocaleCompare("level",option+1) == 0)
1970          {
1971            double
1972              black_point,
1973              gamma,
1974              white_point;
1975
1976            /*
1977              Parse levels.
1978            */
1979            (void) SyncImageSettings(mogrify_info,*image,exception);
1980            flags=ParseGeometry(argv[i+1],&geometry_info);
1981            black_point=geometry_info.rho;
1982            white_point=(double) QuantumRange;
1983            if ((flags & SigmaValue) != 0)
1984              white_point=geometry_info.sigma;
1985            gamma=1.0;
1986            if ((flags & XiValue) != 0)
1987              gamma=geometry_info.xi;
1988            if ((flags & PercentValue) != 0)
1989              {
1990                black_point*=(double) (QuantumRange/100.0);
1991                white_point*=(double) (QuantumRange/100.0);
1992              }
1993            if ((flags & SigmaValue) == 0)
1994              white_point=(double) QuantumRange-black_point;
1995            if ((*option == '+') || ((flags & AspectValue) != 0))
1996              (void) LevelizeImage(*image,black_point,white_point,gamma,
1997                exception);
1998            else
1999              (void) LevelImage(*image,black_point,white_point,gamma,
2000                exception);
2001            break;
2002          }
2003        if (LocaleCompare("level-colors",option+1) == 0)
2004          {
2005            char
2006              token[MagickPathExtent];
2007
2008            const char
2009              *p;
2010
2011            PixelInfo
2012              black_point,
2013              white_point;
2014
2015            p=(const char *) argv[i+1];
2016            GetNextToken(p,&p,MagickPathExtent,token);  /* get black point color */
2017            if ((isalpha((int) *token) != 0) || ((*token == '#') != 0))
2018              (void) QueryColorCompliance(token,AllCompliance,
2019                &black_point,exception);
2020            else
2021              (void) QueryColorCompliance("#000000",AllCompliance,
2022                &black_point,exception);
2023            if (isalpha((int) token[0]) || (token[0] == '#'))
2024              GetNextToken(p,&p,MagickPathExtent,token);
2025            if (*token == '\0')
2026              white_point=black_point; /* set everything to that color */
2027            else
2028              {
2029                if ((isalpha((int) *token) == 0) && ((*token == '#') == 0))
2030                  GetNextToken(p,&p,MagickPathExtent,token); /* Get white point color. */
2031                if ((isalpha((int) *token) != 0) || ((*token == '#') != 0))
2032                  (void) QueryColorCompliance(token,AllCompliance,
2033                    &white_point,exception);
2034                else
2035                  (void) QueryColorCompliance("#ffffff",AllCompliance,
2036                    &white_point,exception);
2037              }
2038            (void) LevelImageColors(*image,&black_point,&white_point,
2039              *option == '+' ? MagickTrue : MagickFalse,exception);
2040            break;
2041          }
2042        if (LocaleCompare("linear-stretch",option+1) == 0)
2043          {
2044            double
2045              black_point,
2046              white_point;
2047
2048            (void) SyncImageSettings(mogrify_info,*image,exception);
2049            flags=ParseGeometry(argv[i+1],&geometry_info);
2050            black_point=geometry_info.rho;
2051            white_point=(double) (*image)->columns*(*image)->rows;
2052            if ((flags & SigmaValue) != 0)
2053              white_point=geometry_info.sigma;
2054            if ((flags & PercentValue) != 0)
2055              {
2056                black_point*=(double) (*image)->columns*(*image)->rows/100.0;
2057                white_point*=(double) (*image)->columns*(*image)->rows/100.0;
2058              }
2059            if ((flags & SigmaValue) == 0)
2060              white_point=(double) (*image)->columns*(*image)->rows-
2061                black_point;
2062            (void) LinearStretchImage(*image,black_point,white_point,exception);
2063            break;
2064          }
2065        if (LocaleCompare("liquid-rescale",option+1) == 0)
2066          {
2067            /*
2068              Liquid rescale image.
2069            */
2070            (void) SyncImageSettings(mogrify_info,*image,exception);
2071            flags=ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
2072            if ((flags & XValue) == 0)
2073              geometry.x=1;
2074            if ((flags & YValue) == 0)
2075              geometry.y=0;
2076            mogrify_image=LiquidRescaleImage(*image,geometry.width,
2077              geometry.height,1.0*geometry.x,1.0*geometry.y,exception);
2078            break;
2079          }
2080        if (LocaleCompare("local-contrast",option+1) == 0)
2081          {
2082            (void) SyncImageSettings(mogrify_info,*image,exception);
2083            flags=ParseGeometry(argv[i+1],&geometry_info);
2084            if ((flags & RhoValue) == 0)
2085              geometry_info.rho=10;
2086            if ((flags & SigmaValue) == 0)
2087              geometry_info.sigma=12.5;
2088            mogrify_image=LocalContrastImage(*image,geometry_info.rho,
2089              geometry_info.sigma,exception);
2090            break;
2091          }
2092        if (LocaleCompare("lowlight-color",option+1) == 0)
2093          {
2094            (void) SetImageArtifact(*image,option+1,argv[i+1]);
2095            break;
2096          }
2097        break;
2098      }
2099      case 'm':
2100      {
2101        if (LocaleCompare("magnify",option+1) == 0)
2102          {
2103            /*
2104              Double image size.
2105            */
2106            (void) SyncImageSettings(mogrify_info,*image,exception);
2107            mogrify_image=MagnifyImage(*image,exception);
2108            break;
2109          }
2110        if (LocaleCompare("map",option+1) == 0)
2111          {
2112            Image
2113              *remap_image;
2114
2115            /*
2116              Transform image colors to match this set of colors.
2117            */
2118            (void) SyncImageSettings(mogrify_info,*image,exception);
2119            if (*option == '+')
2120              break;
2121            remap_image=GetImageCache(mogrify_info,argv[i+1],exception);
2122            if (remap_image == (Image *) NULL)
2123              break;
2124            (void) RemapImage(quantize_info,*image,remap_image,exception);
2125            remap_image=DestroyImage(remap_image);
2126            break;
2127          }
2128        if (LocaleCompare("mask",option+1) == 0)
2129          {
2130            Image
2131              *mask;
2132
2133            (void) SyncImageSettings(mogrify_info,*image,exception);
2134            if (*option == '+')
2135              {
2136                /*
2137                  Remove a mask.
2138                */
2139                (void) SetImageMask(*image,ReadPixelMask,(Image *) NULL,
2140                  exception);
2141                break;
2142              }
2143            /*
2144              Set the image mask.
2145            */
2146            mask=GetImageCache(mogrify_info,argv[i+1],exception);
2147            if (mask == (Image *) NULL)
2148              break;
2149            (void) SetImageMask(*image,ReadPixelMask,mask,exception);
2150            mask=DestroyImage(mask);
2151            break;
2152          }
2153        if (LocaleCompare("matte",option+1) == 0)
2154          {
2155            (void) SetImageAlphaChannel(*image,(*option == '-') ?
2156              SetAlphaChannel : DeactivateAlphaChannel,exception);
2157            break;
2158          }
2159        if (LocaleCompare("mean-shift",option+1) == 0)
2160          {
2161            /*
2162              Detect edges in the image.
2163            */
2164            (void) SyncImageSettings(mogrify_info,*image,exception);
2165            flags=ParseGeometry(argv[i+1],&geometry_info);
2166            if ((flags & SigmaValue) == 0)
2167              geometry_info.sigma=geometry_info.rho;
2168            if ((flags & XiValue) == 0)
2169              geometry_info.xi=0.10*QuantumRange;
2170            if ((flags & PercentValue) != 0)
2171              geometry_info.xi=(double) QuantumRange*geometry_info.xi/100.0;
2172            mogrify_image=MeanShiftImage(*image,(size_t) geometry_info.rho,
2173              (size_t) geometry_info.sigma,geometry_info.xi,exception);
2174            break;
2175          }
2176        if (LocaleCompare("median",option+1) == 0)
2177          {
2178            /*
2179              Median filter image.
2180            */
2181            (void) SyncImageSettings(mogrify_info,*image,exception);
2182            flags=ParseGeometry(argv[i+1],&geometry_info);
2183            if ((flags & SigmaValue) == 0)
2184              geometry_info.sigma=geometry_info.rho;
2185            mogrify_image=StatisticImage(*image,MedianStatistic,(size_t)
2186              geometry_info.rho,(size_t) geometry_info.sigma,exception);
2187            break;
2188          }
2189        if (LocaleCompare("mode",option+1) == 0)
2190          {
2191            /*
2192              Mode image.
2193            */
2194            (void) SyncImageSettings(mogrify_info,*image,exception);
2195            flags=ParseGeometry(argv[i+1],&geometry_info);
2196            if ((flags & SigmaValue) == 0)
2197              geometry_info.sigma=geometry_info.rho;
2198            mogrify_image=StatisticImage(*image,ModeStatistic,(size_t)
2199              geometry_info.rho,(size_t) geometry_info.sigma,exception);
2200            break;
2201          }
2202        if (LocaleCompare("modulate",option+1) == 0)
2203          {
2204            (void) SyncImageSettings(mogrify_info,*image,exception);
2205            (void) ModulateImage(*image,argv[i+1],exception);
2206            break;
2207          }
2208        if (LocaleCompare("moments",option+1) == 0)
2209          {
2210            if (*option == '+')
2211              {
2212                (void) DeleteImageArtifact(*image,"identify:moments");
2213                break;
2214              }
2215            (void) SetImageArtifact(*image,"identify:moments",argv[i+1]);
2216            (void) SetImageArtifact(*image,"verbose","true");
2217            break;
2218          }
2219        if (LocaleCompare("monitor",option+1) == 0)
2220          {
2221            if (*option == '+')
2222              {
2223                (void) SetImageProgressMonitor(*image,
2224                  (MagickProgressMonitor) NULL,(void *) NULL);
2225                break;
2226              }
2227            (void) SetImageProgressMonitor(*image,MonitorProgress,
2228              (void *) NULL);
2229            break;
2230          }
2231        if (LocaleCompare("monochrome",option+1) == 0)
2232          {
2233            (void) SyncImageSettings(mogrify_info,*image,exception);
2234            (void) SetImageType(*image,BilevelType,exception);
2235            break;
2236          }
2237        if (LocaleCompare("morphology",option+1) == 0)
2238          {
2239            char
2240              token[MagickPathExtent];
2241
2242            const char
2243              *p;
2244
2245            KernelInfo
2246              *kernel;
2247
2248            MorphologyMethod
2249              method;
2250
2251            ssize_t
2252              iterations;
2253
2254            /*
2255              Morphological Image Operation
2256            */
2257            (void) SyncImageSettings(mogrify_info,*image,exception);
2258            p=argv[i+1];
2259            GetNextToken(p,&p,MagickPathExtent,token);
2260            method=(MorphologyMethod) ParseCommandOption(
2261              MagickMorphologyOptions,MagickFalse,token);
2262            iterations=1L;
2263            GetNextToken(p,&p,MagickPathExtent,token);
2264            if ((*p == ':') || (*p == ','))
2265              GetNextToken(p,&p,MagickPathExtent,token);
2266            if ((*p != '\0'))
2267              iterations=(ssize_t) StringToLong(p);
2268            kernel=AcquireKernelInfo(argv[i+2],exception);
2269            if (kernel == (KernelInfo *) NULL)
2270              {
2271                (void) ThrowMagickException(exception,GetMagickModule(),
2272                  OptionError,"UnabletoParseKernel","morphology");
2273                status=MagickFalse;
2274                break;
2275              }
2276            mogrify_image=MorphologyImage(*image,method,iterations,kernel,
2277              exception);
2278            kernel=DestroyKernelInfo(kernel);
2279            break;
2280          }
2281        if (LocaleCompare("motion-blur",option+1) == 0)
2282          {
2283            /*
2284              Motion blur image.
2285            */
2286            (void) SyncImageSettings(mogrify_info,*image,exception);
2287            flags=ParseGeometry(argv[i+1],&geometry_info);
2288            if ((flags & SigmaValue) == 0)
2289              geometry_info.sigma=1.0;
2290            mogrify_image=MotionBlurImage(*image,geometry_info.rho,
2291              geometry_info.sigma,geometry_info.xi,exception);
2292            break;
2293          }
2294        break;
2295      }
2296      case 'n':
2297      {
2298        if (LocaleCompare("negate",option+1) == 0)
2299          {
2300            (void) SyncImageSettings(mogrify_info,*image,exception);
2301            (void) NegateImage(*image,*option == '+' ? MagickTrue :
2302              MagickFalse,exception);
2303            break;
2304          }
2305        if (LocaleCompare("noise",option+1) == 0)
2306          {
2307            (void) SyncImageSettings(mogrify_info,*image,exception);
2308            if (*option == '-')
2309              {
2310                flags=ParseGeometry(argv[i+1],&geometry_info);
2311                if ((flags & SigmaValue) == 0)
2312                  geometry_info.sigma=geometry_info.rho;
2313                mogrify_image=StatisticImage(*image,NonpeakStatistic,(size_t)
2314                  geometry_info.rho,(size_t) geometry_info.sigma,exception);
2315              }
2316            else
2317              {
2318                NoiseType
2319                  noise;
2320
2321                noise=(NoiseType) ParseCommandOption(MagickNoiseOptions,
2322                  MagickFalse,argv[i+1]);
2323                mogrify_image=AddNoiseImage(*image,noise,attenuate,exception);
2324              }
2325            break;
2326          }
2327        if (LocaleCompare("normalize",option+1) == 0)
2328          {
2329            (void) SyncImageSettings(mogrify_info,*image,exception);
2330            (void) NormalizeImage(*image,exception);
2331            break;
2332          }
2333        break;
2334      }
2335      case 'o':
2336      {
2337        if (LocaleCompare("opaque",option+1) == 0)
2338          {
2339            PixelInfo
2340              target;
2341
2342            (void) SyncImageSettings(mogrify_info,*image,exception);
2343            (void) QueryColorCompliance(argv[i+1],AllCompliance,&target,
2344              exception);
2345            (void) OpaquePaintImage(*image,&target,&fill,*option == '-' ?
2346              MagickFalse : MagickTrue,exception);
2347            break;
2348          }
2349        if (LocaleCompare("ordered-dither",option+1) == 0)
2350          {
2351            (void) SyncImageSettings(mogrify_info,*image,exception);
2352            (void) OrderedDitherImage(*image,argv[i+1],exception);
2353            break;
2354          }
2355        break;
2356      }
2357      case 'p':
2358      {
2359        if (LocaleCompare("paint",option+1) == 0)
2360          {
2361            (void) SyncImageSettings(mogrify_info,*image,exception);
2362            (void) ParseGeometry(argv[i+1],&geometry_info);
2363            mogrify_image=OilPaintImage(*image,geometry_info.rho,
2364              geometry_info.sigma,exception);
2365            break;
2366          }
2367        if (LocaleCompare("perceptible",option+1) == 0)
2368          {
2369            /*
2370              Perceptible image.
2371            */
2372            (void) SyncImageSettings(mogrify_info,*image,exception);
2373            (void) PerceptibleImage(*image,StringToDouble(argv[i+1],
2374              (char **) NULL),exception);
2375            break;
2376          }
2377        if (LocaleCompare("pointsize",option+1) == 0)
2378          {
2379            if (*option == '+')
2380              (void) ParseGeometry("12",&geometry_info);
2381            else
2382              (void) ParseGeometry(argv[i+1],&geometry_info);
2383            draw_info->pointsize=geometry_info.rho;
2384            break;
2385          }
2386        if (LocaleCompare("polaroid",option+1) == 0)
2387          {
2388            const char
2389              *caption;
2390
2391            double
2392              angle;
2393
2394            RandomInfo
2395              *random_info;
2396
2397            /*
2398              Simulate a Polaroid picture.
2399            */
2400            (void) SyncImageSettings(mogrify_info,*image,exception);
2401            random_info=AcquireRandomInfo();
2402            angle=22.5*(GetPseudoRandomValue(random_info)-0.5);
2403            random_info=DestroyRandomInfo(random_info);
2404            if (*option == '-')
2405              {
2406                SetGeometryInfo(&geometry_info);
2407                flags=ParseGeometry(argv[i+1],&geometry_info);
2408                angle=geometry_info.rho;
2409              }
2410            caption=GetImageProperty(*image,"caption",exception);
2411            mogrify_image=PolaroidImage(*image,draw_info,caption,angle,
2412              interpolate_method,exception);
2413            break;
2414          }
2415        if (LocaleCompare("posterize",option+1) == 0)
2416          {
2417            /*
2418              Posterize image.
2419            */
2420            (void) SyncImageSettings(mogrify_info,*image,exception);
2421            (void) PosterizeImage(*image,StringToUnsignedLong(argv[i+1]),
2422              quantize_info->dither_method,exception);
2423            break;
2424          }
2425        if (LocaleCompare("preview",option+1) == 0)
2426          {
2427            PreviewType
2428              preview_type;
2429
2430            /*
2431              Preview image.
2432            */
2433            (void) SyncImageSettings(mogrify_info,*image,exception);
2434            if (*option == '+')
2435              preview_type=UndefinedPreview;
2436            else
2437              preview_type=(PreviewType) ParseCommandOption(
2438                MagickPreviewOptions,MagickFalse,argv[i+1]);
2439            mogrify_image=PreviewImage(*image,preview_type,exception);
2440            break;
2441          }
2442        if (LocaleCompare("profile",option+1) == 0)
2443          {
2444            const char
2445              *name;
2446
2447            const StringInfo
2448              *profile;
2449
2450            Image
2451              *profile_image;
2452
2453            ImageInfo
2454              *profile_info;
2455
2456            (void) SyncImageSettings(mogrify_info,*image,exception);
2457            if (*option == '+')
2458              {
2459                /*
2460                  Remove a profile from the image.
2461                */
2462                (void) ProfileImage(*image,argv[i+1],(const unsigned char *)
2463                  NULL,0,exception);
2464                break;
2465              }
2466            /*
2467              Associate a profile with the image.
2468            */
2469            profile_info=CloneImageInfo(mogrify_info);
2470            profile=GetImageProfile(*image,"iptc");
2471            if (profile != (StringInfo *) NULL)
2472              profile_info->profile=(void *) CloneStringInfo(profile);
2473            profile_image=GetImageCache(profile_info,argv[i+1],exception);
2474            profile_info=DestroyImageInfo(profile_info);
2475            if (profile_image == (Image *) NULL)
2476              {
2477                StringInfo
2478                  *file_data;
2479
2480                profile_info=CloneImageInfo(mogrify_info);
2481                (void) CopyMagickString(profile_info->filename,argv[i+1],
2482                  MagickPathExtent);
2483                file_data=FileToStringInfo(profile_info->filename,~0UL,
2484                  exception);
2485                if (file_data != (StringInfo *) NULL)
2486                  {
2487                    (void) ProfileImage(*image,profile_info->magick,
2488                      GetStringInfoDatum(file_data),
2489                      GetStringInfoLength(file_data),exception);
2490                    file_data=DestroyStringInfo(file_data);
2491                  }
2492                profile_info=DestroyImageInfo(profile_info);
2493                break;
2494              }
2495            ResetImageProfileIterator(profile_image);
2496            name=GetNextImageProfile(profile_image);
2497            while (name != (const char *) NULL)
2498            {
2499              profile=GetImageProfile(profile_image,name);
2500              if (profile != (StringInfo *) NULL)
2501                (void) ProfileImage(*image,name,GetStringInfoDatum(profile),
2502                  (size_t) GetStringInfoLength(profile),exception);
2503              name=GetNextImageProfile(profile_image);
2504            }
2505            profile_image=DestroyImage(profile_image);
2506            break;
2507          }
2508        break;
2509      }
2510      case 'q':
2511      {
2512        if (LocaleCompare("quantize",option+1) == 0)
2513          {
2514            if (*option == '+')
2515              {
2516                quantize_info->colorspace=UndefinedColorspace;
2517                break;
2518              }
2519            quantize_info->colorspace=(ColorspaceType) ParseCommandOption(
2520              MagickColorspaceOptions,MagickFalse,argv[i+1]);
2521            break;
2522          }
2523        break;
2524      }
2525      case 'r':
2526      {
2527        if (LocaleCompare("rotational-blur",option+1) == 0)
2528          {
2529            /*
2530              Rotational blur image.
2531            */
2532            (void) SyncImageSettings(mogrify_info,*image,exception);
2533            flags=ParseGeometry(argv[i+1],&geometry_info);
2534            mogrify_image=RotationalBlurImage(*image,geometry_info.rho,exception);
2535            break;
2536          }
2537        if (LocaleCompare("raise",option+1) == 0)
2538          {
2539            /*
2540              Surround image with a raise of solid color.
2541            */
2542            flags=ParsePageGeometry(*image,argv[i+1],&geometry,exception);
2543            (void) RaiseImage(*image,&geometry,*option == '-' ? MagickTrue :
2544              MagickFalse,exception);
2545            break;
2546          }
2547        if (LocaleCompare("random-threshold",option+1) == 0)
2548          {
2549            /*
2550              Threshold image.
2551            */
2552            double
2553              min_threshold,
2554              max_threshold;
2555
2556            (void) SyncImageSettings(mogrify_info,*image,exception);
2557            min_threshold=0.0;
2558            max_threshold=(double) QuantumRange;
2559            flags=ParseGeometry(argv[i+1],&geometry_info);
2560            min_threshold=geometry_info.rho;
2561            max_threshold=geometry_info.sigma;
2562            if ((flags & SigmaValue) == 0)
2563              max_threshold=min_threshold;
2564            if (strchr(argv[i+1],'%') != (char *) NULL)
2565              {
2566                max_threshold*=(double) (0.01*QuantumRange);
2567                min_threshold*=(double) (0.01*QuantumRange);
2568              }
2569            (void) RandomThresholdImage(*image,min_threshold,max_threshold,
2570              exception);
2571            break;
2572          }
2573        if (LocaleCompare("read-mask",option+1) == 0)
2574          {
2575            Image
2576              *mask;
2577
2578            (void) SyncImageSettings(mogrify_info,*image,exception);
2579            if (*option == '+')
2580              {
2581                /*
2582                  Remove a mask.
2583                */
2584                (void) SetImageMask(*image,ReadPixelMask,(Image *) NULL,
2585                  exception);
2586                break;
2587              }
2588            /*
2589              Set the image mask.
2590            */
2591            mask=GetImageCache(mogrify_info,argv[i+1],exception);
2592            if (mask == (Image *) NULL)
2593              break;
2594            (void) SetImageMask(*image,ReadPixelMask,mask,exception);
2595            mask=DestroyImage(mask);
2596            break;
2597          }
2598        if (LocaleCompare("region",option+1) == 0)
2599          {
2600            (void) SyncImageSettings(mogrify_info,*image,exception);
2601            if (region_image != (Image *) NULL)
2602              {
2603                /*
2604                  Composite region.
2605                */
2606                (void) CompositeImage(region_image,*image,
2607                   region_image->alpha_trait != UndefinedPixelTrait ?
2608                   CopyCompositeOp : OverCompositeOp,MagickTrue,
2609                   region_geometry.x,region_geometry.y,exception);
2610                *image=DestroyImage(*image);
2611                *image=region_image;
2612                region_image = (Image *) NULL;
2613              }
2614            if (*option == '+')
2615              break;
2616            /*
2617              Apply transformations to a selected region of the image.
2618            */
2619            (void) ParseGravityGeometry(*image,argv[i+1],&region_geometry,
2620              exception);
2621            mogrify_image=CropImage(*image,&region_geometry,exception);
2622            if (mogrify_image == (Image *) NULL)
2623              break;
2624            region_image=(*image);
2625            *image=mogrify_image;
2626            mogrify_image=(Image *) NULL;
2627            break;
2628          }
2629        if (LocaleCompare("render",option+1) == 0)
2630          {
2631            (void) SyncImageSettings(mogrify_info,*image,exception);
2632            draw_info->render=(*option == '+') ? MagickTrue : MagickFalse;
2633            break;
2634          }
2635        if (LocaleCompare("remap",option+1) == 0)
2636          {
2637            Image
2638              *remap_image;
2639
2640            /*
2641              Transform image colors to match this set of colors.
2642            */
2643            (void) SyncImageSettings(mogrify_info,*image,exception);
2644            if (*option == '+')
2645              break;
2646            remap_image=GetImageCache(mogrify_info,argv[i+1],exception);
2647            if (remap_image == (Image *) NULL)
2648              break;
2649            (void) RemapImage(quantize_info,*image,remap_image,exception);
2650            remap_image=DestroyImage(remap_image);
2651            break;
2652          }
2653        if (LocaleCompare("repage",option+1) == 0)
2654          {
2655            if (*option == '+')
2656              {
2657                (void) ParseAbsoluteGeometry("0x0+0+0",&(*image)->page);
2658                break;
2659              }
2660            (void) ResetImagePage(*image,argv[i+1]);
2661            break;
2662          }
2663        if (LocaleCompare("resample",option+1) == 0)
2664          {
2665            /*
2666              Resample image.
2667            */
2668            (void) SyncImageSettings(mogrify_info,*image,exception);
2669            flags=ParseGeometry(argv[i+1],&geometry_info);
2670            if ((flags & SigmaValue) == 0)
2671              geometry_info.sigma=geometry_info.rho;
2672            mogrify_image=ResampleImage(*image,geometry_info.rho,
2673              geometry_info.sigma,(*image)->filter,exception);
2674            break;
2675          }
2676        if (LocaleCompare("resize",option+1) == 0)
2677          {
2678            /*
2679              Resize image.
2680            */
2681            (void) SyncImageSettings(mogrify_info,*image,exception);
2682            (void) ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
2683            mogrify_image=ResizeImage(*image,geometry.width,geometry.height,
2684              (*image)->filter,exception);
2685            break;
2686          }
2687        if (LocaleCompare("roll",option+1) == 0)
2688          {
2689            /*
2690              Roll image.
2691            */
2692            (void) SyncImageSettings(mogrify_info,*image,exception);
2693            (void) ParsePageGeometry(*image,argv[i+1],&geometry,exception);
2694            mogrify_image=RollImage(*image,geometry.x,geometry.y,exception);
2695            break;
2696          }
2697        if (LocaleCompare("rotate",option+1) == 0)
2698          {
2699            char
2700              *rotation;
2701
2702            /*
2703              Check for conditional image rotation.
2704            */
2705            (void) SyncImageSettings(mogrify_info,*image,exception);
2706            if (strchr(argv[i+1],'>') != (char *) NULL)
2707              if ((*image)->columns <= (*image)->rows)
2708                break;
2709            if (strchr(argv[i+1],'<') != (char *) NULL)
2710              if ((*image)->columns >= (*image)->rows)
2711                break;
2712            /*
2713              Rotate image.
2714            */
2715            rotation=ConstantString(argv[i+1]);
2716            (void) SubstituteString(&rotation,">","");
2717            (void) SubstituteString(&rotation,"<","");
2718            (void) ParseGeometry(rotation,&geometry_info);
2719            rotation=DestroyString(rotation);
2720            mogrify_image=RotateImage(*image,geometry_info.rho,exception);
2721            break;
2722          }
2723        break;
2724      }
2725      case 's':
2726      {
2727        if (LocaleCompare("sample",option+1) == 0)
2728          {
2729            /*
2730              Sample image with pixel replication.
2731            */
2732            (void) SyncImageSettings(mogrify_info,*image,exception);
2733            (void) ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
2734            mogrify_image=SampleImage(*image,geometry.width,geometry.height,
2735              exception);
2736            break;
2737          }
2738        if (LocaleCompare("scale",option+1) == 0)
2739          {
2740            /*
2741              Resize image.
2742            */
2743            (void) SyncImageSettings(mogrify_info,*image,exception);
2744            (void) ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
2745            mogrify_image=ScaleImage(*image,geometry.width,geometry.height,
2746              exception);
2747            break;
2748          }
2749        if (LocaleCompare("selective-blur",option+1) == 0)
2750          {
2751            /*
2752              Selectively blur pixels within a contrast threshold.
2753            */
2754            (void) SyncImageSettings(mogrify_info,*image,exception);
2755            flags=ParseGeometry(argv[i+1],&geometry_info);
2756            if ((flags & PercentValue) != 0)
2757              geometry_info.xi=(double) QuantumRange*geometry_info.xi/100.0;
2758            mogrify_image=SelectiveBlurImage(*image,geometry_info.rho,
2759              geometry_info.sigma,geometry_info.xi,exception);
2760            break;
2761          }
2762        if (LocaleCompare("separate",option+1) == 0)
2763          {
2764            /*
2765              Break channels into separate images.
2766            */
2767            (void) SyncImageSettings(mogrify_info,*image,exception);
2768            mogrify_image=SeparateImages(*image,exception);
2769            break;
2770          }
2771        if (LocaleCompare("sepia-tone",option+1) == 0)
2772          {
2773            double
2774              threshold;
2775
2776            /*
2777              Sepia-tone image.
2778            */
2779            (void) SyncImageSettings(mogrify_info,*image,exception);
2780            threshold=StringToDoubleInterval(argv[i+1],(double) QuantumRange+
2781              1.0);
2782            mogrify_image=SepiaToneImage(*image,threshold,exception);
2783            break;
2784          }
2785        if (LocaleCompare("segment",option+1) == 0)
2786          {
2787            /*
2788              Segment image.
2789            */
2790            (void) SyncImageSettings(mogrify_info,*image,exception);
2791            flags=ParseGeometry(argv[i+1],&geometry_info);
2792            if ((flags & SigmaValue) == 0)
2793              geometry_info.sigma=1.0;
2794            (void) SegmentImage(*image,(*image)->colorspace,
2795              mogrify_info->verbose,geometry_info.rho,geometry_info.sigma,
2796              exception);
2797            break;
2798          }
2799        if (LocaleCompare("set",option+1) == 0)
2800          {
2801            char
2802              *value;
2803
2804            /*
2805              Set image option.
2806            */
2807            if (*option == '+')
2808              {
2809                if (LocaleNCompare(argv[i+1],"registry:",9) == 0)
2810                  (void) DeleteImageRegistry(argv[i+1]+9);
2811                else
2812                  if (LocaleNCompare(argv[i+1],"option:",7) == 0)
2813                    {
2814                      (void) DeleteImageOption(mogrify_info,argv[i+1]+7);
2815                      (void) DeleteImageArtifact(*image,argv[i+1]+7);
2816                    }
2817                  else
2818                    (void) DeleteImageProperty(*image,argv[i+1]);
2819                break;
2820              }
2821            value=InterpretImageProperties(mogrify_info,*image,argv[i+2],
2822              exception);
2823            if (value == (char *) NULL)
2824              break;
2825            if (LocaleNCompare(argv[i+1],"registry:",9) == 0)
2826              (void) SetImageRegistry(StringRegistryType,argv[i+1]+9,value,
2827                exception);
2828            else
2829              if (LocaleNCompare(argv[i+1],"option:",7) == 0)
2830                {
2831                  (void) SetImageOption(image_info,argv[i+1]+7,value);
2832                  (void) SetImageOption(mogrify_info,argv[i+1]+7,value);
2833                  (void) SetImageArtifact(*image,argv[i+1]+7,value);
2834                }
2835              else
2836                (void) SetImageProperty(*image,argv[i+1],value,exception);
2837            value=DestroyString(value);
2838            break;
2839          }
2840        if (LocaleCompare("shade",option+1) == 0)
2841          {
2842            /*
2843              Shade image.
2844            */
2845            (void) SyncImageSettings(mogrify_info,*image,exception);
2846            flags=ParseGeometry(argv[i+1],&geometry_info);
2847            if ((flags & SigmaValue) == 0)
2848              geometry_info.sigma=1.0;
2849            mogrify_image=ShadeImage(*image,(*option == '-') ? MagickTrue :
2850              MagickFalse,geometry_info.rho,geometry_info.sigma,exception);
2851            break;
2852          }
2853        if (LocaleCompare("shadow",option+1) == 0)
2854          {
2855            /*
2856              Shadow image.
2857            */
2858            (void) SyncImageSettings(mogrify_info,*image,exception);
2859            flags=ParseGeometry(argv[i+1],&geometry_info);
2860            if ((flags & SigmaValue) == 0)
2861              geometry_info.sigma=1.0;
2862            if ((flags & XiValue) == 0)
2863              geometry_info.xi=4.0;
2864            if ((flags & PsiValue) == 0)
2865              geometry_info.psi=4.0;
2866            mogrify_image=ShadowImage(*image,geometry_info.rho,
2867              geometry_info.sigma,(ssize_t) ceil(geometry_info.xi-0.5),
2868              (ssize_t) ceil(geometry_info.psi-0.5),exception);
2869            break;
2870          }
2871        if (LocaleCompare("sharpen",option+1) == 0)
2872          {
2873            /*
2874              Sharpen image.
2875            */
2876            (void) SyncImageSettings(mogrify_info,*image,exception);
2877            flags=ParseGeometry(argv[i+1],&geometry_info);
2878            if ((flags & SigmaValue) == 0)
2879              geometry_info.sigma=1.0;
2880            if ((flags & XiValue) == 0)
2881              geometry_info.xi=0.0;
2882            mogrify_image=SharpenImage(*image,geometry_info.rho,
2883              geometry_info.sigma,exception);
2884            break;
2885          }
2886        if (LocaleCompare("shave",option+1) == 0)
2887          {
2888            /*
2889              Shave the image edges.
2890            */
2891            (void) SyncImageSettings(mogrify_info,*image,exception);
2892            flags=ParsePageGeometry(*image,argv[i+1],&geometry,exception);
2893            mogrify_image=ShaveImage(*image,&geometry,exception);
2894            break;
2895          }
2896        if (LocaleCompare("shear",option+1) == 0)
2897          {
2898            /*
2899              Shear image.
2900            */
2901            (void) SyncImageSettings(mogrify_info,*image,exception);
2902            flags=ParseGeometry(argv[i+1],&geometry_info);
2903            if ((flags & SigmaValue) == 0)
2904              geometry_info.sigma=geometry_info.rho;
2905            mogrify_image=ShearImage(*image,geometry_info.rho,
2906              geometry_info.sigma,exception);
2907            break;
2908          }
2909        if (LocaleCompare("sigmoidal-contrast",option+1) == 0)
2910          {
2911            /*
2912              Sigmoidal non-linearity contrast control.
2913            */
2914            (void) SyncImageSettings(mogrify_info,*image,exception);
2915            flags=ParseGeometry(argv[i+1],&geometry_info);
2916            if ((flags & SigmaValue) == 0)
2917              geometry_info.sigma=(double) QuantumRange/2.0;
2918            if ((flags & PercentValue) != 0)
2919              geometry_info.sigma=(double) QuantumRange*geometry_info.sigma/
2920                100.0;
2921            (void) SigmoidalContrastImage(*image,(*option == '-') ?
2922              MagickTrue : MagickFalse,geometry_info.rho,geometry_info.sigma,
2923              exception);
2924            break;
2925          }
2926        if (LocaleCompare("sketch",option+1) == 0)
2927          {
2928            /*
2929              Sketch image.
2930            */
2931            (void) SyncImageSettings(mogrify_info,*image,exception);
2932            flags=ParseGeometry(argv[i+1],&geometry_info);
2933            if ((flags & SigmaValue) == 0)
2934              geometry_info.sigma=1.0;
2935            mogrify_image=SketchImage(*image,geometry_info.rho,
2936              geometry_info.sigma,geometry_info.xi,exception);
2937            break;
2938          }
2939        if (LocaleCompare("solarize",option+1) == 0)
2940          {
2941            double
2942              threshold;
2943
2944            (void) SyncImageSettings(mogrify_info,*image,exception);
2945            threshold=StringToDoubleInterval(argv[i+1],(double) QuantumRange+
2946              1.0);
2947            (void) SolarizeImage(*image,threshold,exception);
2948            break;
2949          }
2950        if (LocaleCompare("sparse-color",option+1) == 0)
2951          {
2952            SparseColorMethod
2953              method;
2954
2955            char
2956              *arguments;
2957
2958            /*
2959              Sparse Color Interpolated Gradient
2960            */
2961            (void) SyncImageSettings(mogrify_info,*image,exception);
2962            method=(SparseColorMethod) ParseCommandOption(
2963              MagickSparseColorOptions,MagickFalse,argv[i+1]);
2964            arguments=InterpretImageProperties(mogrify_info,*image,argv[i+2],
2965              exception);
2966            if (arguments == (char *) NULL)
2967              break;
2968            mogrify_image=SparseColorOption(*image,method,arguments,
2969              option[0] == '+' ? MagickTrue : MagickFalse,exception);
2970            arguments=DestroyString(arguments);
2971            break;
2972          }
2973        if (LocaleCompare("splice",option+1) == 0)
2974          {
2975            /*
2976              Splice a solid color into the image.
2977            */
2978            (void) SyncImageSettings(mogrify_info,*image,exception);
2979            (void) ParseGravityGeometry(*image,argv[i+1],&geometry,exception);
2980            mogrify_image=SpliceImage(*image,&geometry,exception);
2981            break;
2982          }
2983        if (LocaleCompare("spread",option+1) == 0)
2984          {
2985            /*
2986              Spread an image.
2987            */
2988            (void) SyncImageSettings(mogrify_info,*image,exception);
2989            (void) ParseGeometry(argv[i+1],&geometry_info);
2990            mogrify_image=SpreadImage(*image,interpolate_method,
2991              geometry_info.rho,exception);
2992            break;
2993          }
2994        if (LocaleCompare("statistic",option+1) == 0)
2995          {
2996            StatisticType
2997              type;
2998
2999            (void) SyncImageSettings(mogrify_info,*image,exception);
3000            type=(StatisticType) ParseCommandOption(MagickStatisticOptions,
3001              MagickFalse,argv[i+1]);
3002            (void) ParseGeometry(argv[i+2],&geometry_info);
3003            mogrify_image=StatisticImage(*image,type,(size_t) geometry_info.rho,
3004              (size_t) geometry_info.sigma,exception);
3005            break;
3006          }
3007        if (LocaleCompare("stretch",option+1) == 0)
3008          {
3009            if (*option == '+')
3010              {
3011                draw_info->stretch=UndefinedStretch;
3012                break;
3013              }
3014            draw_info->stretch=(StretchType) ParseCommandOption(
3015              MagickStretchOptions,MagickFalse,argv[i+1]);
3016            break;
3017          }
3018        if (LocaleCompare("strip",option+1) == 0)
3019          {
3020            /*
3021              Strip image of profiles and comments.
3022            */
3023            (void) SyncImageSettings(mogrify_info,*image,exception);
3024            (void) StripImage(*image,exception);
3025            break;
3026          }
3027        if (LocaleCompare("stroke",option+1) == 0)
3028          {
3029            ExceptionInfo
3030              *sans;
3031
3032            PixelInfo
3033              color;
3034
3035            if (*option == '+')
3036              {
3037                (void) QueryColorCompliance("none",AllCompliance,
3038                  &draw_info->stroke,exception);
3039                if (draw_info->stroke_pattern != (Image *) NULL)
3040                  draw_info->stroke_pattern=DestroyImage(
3041                    draw_info->stroke_pattern);
3042                break;
3043              }
3044            sans=AcquireExceptionInfo();
3045            status=QueryColorCompliance(argv[i+1],AllCompliance,&color,sans);
3046            sans=DestroyExceptionInfo(sans);
3047            if (status == MagickFalse)
3048              draw_info->stroke_pattern=GetImageCache(mogrify_info,argv[i+1],
3049                exception);
3050            else
3051              draw_info->stroke=color;
3052            break;
3053          }
3054        if (LocaleCompare("strokewidth",option+1) == 0)
3055          {
3056            draw_info->stroke_width=StringToDouble(argv[i+1],(char **) NULL);
3057            break;
3058          }
3059        if (LocaleCompare("style",option+1) == 0)
3060          {
3061            if (*option == '+')
3062              {
3063                draw_info->style=UndefinedStyle;
3064                break;
3065              }
3066            draw_info->style=(StyleType) ParseCommandOption(MagickStyleOptions,
3067              MagickFalse,argv[i+1]);
3068            break;
3069          }
3070        if (LocaleCompare("swirl",option+1) == 0)
3071          {
3072            /*
3073              Swirl image.
3074            */
3075            (void) SyncImageSettings(mogrify_info,*image,exception);
3076            (void) ParseGeometry(argv[i+1],&geometry_info);
3077            mogrify_image=SwirlImage(*image,geometry_info.rho,
3078              interpolate_method,exception);
3079            break;
3080          }
3081        break;
3082      }
3083      case 't':
3084      {
3085        if (LocaleCompare("threshold",option+1) == 0)
3086          {
3087            double
3088              threshold;
3089
3090            /*
3091              Threshold image.
3092            */
3093            (void) SyncImageSettings(mogrify_info,*image,exception);
3094            if (*option == '+')
3095              threshold=(double) QuantumRange/2;
3096            else
3097              threshold=StringToDoubleInterval(argv[i+1],(double) QuantumRange+
3098                1.0);
3099            (void) BilevelImage(*image,threshold,exception);
3100            break;
3101          }
3102        if (LocaleCompare("thumbnail",option+1) == 0)
3103          {
3104            /*
3105              Thumbnail image.
3106            */
3107            (void) SyncImageSettings(mogrify_info,*image,exception);
3108            (void) ParseRegionGeometry(*image,argv[i+1],&geometry,exception);
3109            mogrify_image=ThumbnailImage(*image,geometry.width,geometry.height,
3110              exception);
3111            break;
3112          }
3113        if (LocaleCompare("tile",option+1) == 0)
3114          {
3115            if (*option == '+')
3116              {
3117                if (draw_info->fill_pattern != (Image *) NULL)
3118                  draw_info->fill_pattern=DestroyImage(draw_info->fill_pattern);
3119                break;
3120              }
3121            draw_info->fill_pattern=GetImageCache(mogrify_info,argv[i+1],
3122              exception);
3123            break;
3124          }
3125        if (LocaleCompare("tint",option+1) == 0)
3126          {
3127            /*
3128              Tint the image.
3129            */
3130            (void) SyncImageSettings(mogrify_info,*image,exception);
3131            mogrify_image=TintImage(*image,argv[i+1],&fill,exception);
3132            break;
3133          }
3134        if (LocaleCompare("transform",option+1) == 0)
3135          {
3136            /*
3137              Affine transform image.
3138            */
3139            (void) SyncImageSettings(mogrify_info,*image,exception);
3140            mogrify_image=AffineTransformImage(*image,&draw_info->affine,
3141              exception);
3142            break;
3143          }
3144        if (LocaleCompare("transparent",option+1) == 0)
3145          {
3146            PixelInfo
3147              target;
3148
3149            (void) SyncImageSettings(mogrify_info,*image,exception);
3150            (void) QueryColorCompliance(argv[i+1],AllCompliance,&target,
3151              exception);
3152            (void) TransparentPaintImage(*image,&target,(Quantum)
3153              TransparentAlpha,*option == '-' ? MagickFalse : MagickTrue,
3154              exception);
3155            break;
3156          }
3157        if (LocaleCompare("transpose",option+1) == 0)
3158          {
3159            /*
3160              Transpose image scanlines.
3161            */
3162            (void) SyncImageSettings(mogrify_info,*image,exception);
3163            mogrify_image=TransposeImage(*image,exception);
3164            break;
3165          }
3166        if (LocaleCompare("transverse",option+1) == 0)
3167          {
3168            /*
3169              Transverse image scanlines.
3170            */
3171            (void) SyncImageSettings(mogrify_info,*image,exception);
3172            mogrify_image=TransverseImage(*image,exception);
3173            break;
3174          }
3175        if (LocaleCompare("treedepth",option+1) == 0)
3176          {
3177            quantize_info->tree_depth=StringToUnsignedLong(argv[i+1]);
3178            break;
3179          }
3180        if (LocaleCompare("trim",option+1) == 0)
3181          {
3182            /*
3183              Trim image.
3184            */
3185            (void) SyncImageSettings(mogrify_info,*image,exception);
3186            mogrify_image=TrimImage(*image,exception);
3187            break;
3188          }
3189        if (LocaleCompare("type",option+1) == 0)
3190          {
3191            ImageType
3192              type;
3193
3194            (void) SyncImageSettings(mogrify_info,*image,exception);
3195            if (*option == '+')
3196              type=UndefinedType;
3197            else
3198              type=(ImageType) ParseCommandOption(MagickTypeOptions,MagickFalse,
3199                argv[i+1]);
3200            (*image)->type=UndefinedType;
3201            (void) SetImageType(*image,type,exception);
3202            break;
3203          }
3204        break;
3205      }
3206      case 'u':
3207      {
3208        if (LocaleCompare("undercolor",option+1) == 0)
3209          {
3210            (void) QueryColorCompliance(argv[i+1],AllCompliance,
3211              &draw_info->undercolor,exception);
3212            break;
3213          }
3214        if (LocaleCompare("unique",option+1) == 0)
3215          {
3216            if (*option == '+')
3217              {
3218                (void) DeleteImageArtifact(*image,"identify:unique-colors");
3219                break;
3220              }
3221            (void) SetImageArtifact(*image,"identify:unique-colors","true");
3222            (void) SetImageArtifact(*image,"verbose","true");
3223            break;
3224          }
3225        if (LocaleCompare("unique-colors",option+1) == 0)
3226          {
3227            /*
3228              Unique image colors.
3229            */
3230            (void) SyncImageSettings(mogrify_info,*image,exception);
3231            mogrify_image=UniqueImageColors(*image,exception);
3232            break;
3233          }
3234        if (LocaleCompare("unsharp",option+1) == 0)
3235          {
3236            /*
3237              Unsharp mask image.
3238            */
3239            (void) SyncImageSettings(mogrify_info,*image,exception);
3240            flags=ParseGeometry(argv[i+1],&geometry_info);
3241            if ((flags & SigmaValue) == 0)
3242              geometry_info.sigma=1.0;
3243            if ((flags & XiValue) == 0)
3244              geometry_info.xi=1.0;
3245            if ((flags & PsiValue) == 0)
3246              geometry_info.psi=0.05;
3247            mogrify_image=UnsharpMaskImage(*image,geometry_info.rho,
3248              geometry_info.sigma,geometry_info.xi,geometry_info.psi,
3249              exception);
3250            break;
3251          }
3252        break;
3253      }
3254      case 'v':
3255      {
3256        if (LocaleCompare("verbose",option+1) == 0)
3257          {
3258            (void) SetImageArtifact(*image,option+1,
3259              *option == '+' ? "false" : "true");
3260            break;
3261          }
3262        if (LocaleCompare("vignette",option+1) == 0)
3263          {
3264            /*
3265              Vignette image.
3266            */
3267            (void) SyncImageSettings(mogrify_info,*image,exception);
3268            flags=ParseGeometry(argv[i+1],&geometry_info);
3269            if ((flags & SigmaValue) == 0)
3270              geometry_info.sigma=1.0;
3271            if ((flags & XiValue) == 0)
3272              geometry_info.xi=0.1*(*image)->columns;
3273            if ((flags & PsiValue) == 0)
3274              geometry_info.psi=0.1*(*image)->rows;
3275            if ((flags & PercentValue) != 0)
3276              {
3277                geometry_info.xi*=(double) (*image)->columns/100.0;
3278                geometry_info.psi*=(double) (*image)->rows/100.0;
3279              }
3280            mogrify_image=VignetteImage(*image,geometry_info.rho,
3281              geometry_info.sigma,(ssize_t) ceil(geometry_info.xi-0.5),
3282              (ssize_t) ceil(geometry_info.psi-0.5),exception);
3283            break;
3284          }
3285        if (LocaleCompare("virtual-pixel",option+1) == 0)
3286          {
3287            if (*option == '+')
3288              {
3289                (void) SetImageVirtualPixelMethod(*image,
3290                  UndefinedVirtualPixelMethod,exception);
3291                break;
3292              }
3293            (void) SetImageVirtualPixelMethod(*image,(VirtualPixelMethod)
3294              ParseCommandOption(MagickVirtualPixelOptions,MagickFalse,
3295              argv[i+1]),exception);
3296            break;
3297          }
3298        break;
3299      }
3300      case 'w':
3301      {
3302        if (LocaleCompare("wave",option+1) == 0)
3303          {
3304            /*
3305              Wave image.
3306            */
3307            (void) SyncImageSettings(mogrify_info,*image,exception);
3308            flags=ParseGeometry(argv[i+1],&geometry_info);
3309            if ((flags & SigmaValue) == 0)
3310              geometry_info.sigma=1.0;
3311            mogrify_image=WaveImage(*image,geometry_info.rho,
3312              geometry_info.sigma,interpolate_method,exception);
3313            break;
3314          }
3315        if (LocaleCompare("wavelet-denoise",option+1) == 0)
3316          {
3317            /*
3318              Wavelet denoise image.
3319            */
3320            (void) SyncImageSettings(mogrify_info,*image,exception);
3321            flags=ParseGeometry(argv[i+1],&geometry_info);
3322            if ((flags & PercentValue) != 0)
3323              {
3324                geometry_info.rho=QuantumRange*geometry_info.rho/100.0;
3325                geometry_info.sigma=QuantumRange*geometry_info.sigma/100.0;
3326              }
3327            if ((flags & SigmaValue) == 0)
3328              geometry_info.sigma=0.0;
3329            mogrify_image=WaveletDenoiseImage(*image,geometry_info.rho,
3330              geometry_info.sigma,exception);
3331            break;
3332          }
3333        if (LocaleCompare("weight",option+1) == 0)
3334          {
3335            ssize_t
3336              weight;
3337
3338            weight=ParseCommandOption(MagickWeightOptions,MagickFalse,
3339              argv[i+1]);
3340            if (weight == -1)
3341              weight=(ssize_t) StringToUnsignedLong(argv[i+1]);
3342            draw_info->weight=(size_t) weight;
3343            break;
3344          }
3345        if (LocaleCompare("white-threshold",option+1) == 0)
3346          {
3347            /*
3348              White threshold image.
3349            */
3350            (void) SyncImageSettings(mogrify_info,*image,exception);
3351            (void) WhiteThresholdImage(*image,argv[i+1],exception);
3352            break;
3353          }
3354        if (LocaleCompare("write-mask",option+1) == 0)
3355          {
3356            Image
3357              *mask;
3358
3359            (void) SyncImageSettings(mogrify_info,*image,exception);
3360            if (*option == '+')
3361              {
3362                /*
3363                  Remove a mask.
3364                */
3365                (void) SetImageMask(*image,WritePixelMask,(Image *) NULL,
3366                  exception);
3367                break;
3368              }
3369            /*
3370              Set the image mask.
3371            */
3372            mask=GetImageCache(mogrify_info,argv[i+1],exception);
3373            if (mask == (Image *) NULL)
3374              break;
3375            (void) SetImageMask(*image,WritePixelMask,mask,exception);
3376            mask=DestroyImage(mask);
3377            break;
3378          }
3379        break;
3380      }
3381      default:
3382        break;
3383    }
3384    /*
3385       Replace current image with any image that was generated
3386    */
3387    if (mogrify_image != (Image *) NULL)
3388      ReplaceImageInListReturnLast(image,mogrify_image);
3389    i+=count;
3390  }
3391  if (region_image != (Image *) NULL)
3392    {
3393      /*
3394        Composite transformed region onto image.
3395      */
3396      (void) SyncImageSettings(mogrify_info,*image,exception);
3397      (void) CompositeImage(region_image,*image,
3398         region_image->alpha_trait != UndefinedPixelTrait ? CopyCompositeOp :
3399         OverCompositeOp,MagickTrue,region_geometry.x,region_geometry.y,
3400         exception);
3401      *image=DestroyImage(*image);
3402      *image=region_image;
3403      region_image = (Image *) NULL;
3404    }
3405  /*
3406    Free resources.
3407  */
3408  quantize_info=DestroyQuantizeInfo(quantize_info);
3409  draw_info=DestroyDrawInfo(draw_info);
3410  mogrify_info=DestroyImageInfo(mogrify_info);
3411  status=(MagickStatusType) (exception->severity < ErrorException ? 1 : 0);
3412  return(status == 0 ? MagickFalse : MagickTrue);
3413}
3414
3415/*
3416%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3417%                                                                             %
3418%                                                                             %
3419%                                                                             %
3420+    M o g r i f y I m a g e C o m m a n d                                    %
3421%                                                                             %
3422%                                                                             %
3423%                                                                             %
3424%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3425%
3426%  MogrifyImageCommand() transforms an image or a sequence of images. These
3427%  transforms include image scaling, image rotation, color reduction, and
3428%  others. The transmogrified image overwrites the original image.
3429%
3430%  The format of the MogrifyImageCommand method is:
3431%
3432%      MagickBooleanType MogrifyImageCommand(ImageInfo *image_info,int argc,
3433%        const char **argv,char **metadata,ExceptionInfo *exception)
3434%
3435%  A description of each parameter follows:
3436%
3437%    o image_info: the image info.
3438%
3439%    o argc: the number of elements in the argument vector.
3440%
3441%    o argv: A text array containing the command line arguments.
3442%
3443%    o metadata: any metadata is returned here.
3444%
3445%    o exception: return any errors or warnings in this structure.
3446%
3447*/
3448
3449static MagickBooleanType MogrifyUsage(void)
3450{
3451  static const char
3452    *channel_operators[]=
3453    {
3454      "-channel-fx expression",
3455      "                     exchange, extract, or transfer one or more image channels",
3456      "-separate            separate an image channel into a grayscale image",
3457      (char *) NULL
3458    },
3459    *miscellaneous[]=
3460    {
3461      "-debug events        display copious debugging information",
3462      "-distribute-cache port",
3463      "                     distributed pixel cache spanning one or more servers",
3464      "-help                print program options",
3465      "-list type           print a list of supported option arguments",
3466      "-log format          format of debugging information",
3467      "-version             print version information",
3468      (char *) NULL
3469    },
3470    *operators[]=
3471    {
3472      "-adaptive-blur geometry",
3473      "                     adaptively blur pixels; decrease effect near edges",
3474      "-adaptive-resize geometry",
3475      "                     adaptively resize image using 'mesh' interpolation",
3476      "-adaptive-sharpen geometry",
3477      "                     adaptively sharpen pixels; increase effect near edges",
3478      "-alpha option        on, activate, off, deactivate, set, opaque, copy",
3479      "                     transparent, extract, background, or shape",
3480      "-annotate geometry text",
3481      "                     annotate the image with text",
3482      "-auto-gamma          automagically adjust gamma level of image",
3483      "-auto-level          automagically adjust color levels of image",
3484      "-auto-orient         automagically orient (rotate) image",
3485      "-bench iterations    measure performance",
3486      "-black-threshold value",
3487      "                     force all pixels below the threshold into black",
3488      "-blue-shift          simulate a scene at nighttime in the moonlight",
3489      "-blur geometry       reduce image noise and reduce detail levels",
3490      "-border geometry     surround image with a border of color",
3491      "-bordercolor color   border color",
3492      "-brightness-contrast geometry",
3493      "                     improve brightness / contrast of the image",
3494      "-canny geometry      detect edges in the image",
3495      "-cdl filename        color correct with a color decision list",
3496      "-channel mask        set the image channel mask",
3497      "-charcoal geometry   simulate a charcoal drawing",
3498      "-chop geometry       remove pixels from the image interior",
3499      "-clamp               keep pixel values in range (0-QuantumRange)",
3500      "-clip                clip along the first path from the 8BIM profile",
3501      "-clip-mask filename  associate a clip mask with the image",
3502      "-clip-path id        clip along a named path from the 8BIM profile",
3503      "-colorize value      colorize the image with the fill color",
3504      "-color-matrix matrix apply color correction to the image",
3505      "-connected-components connectivity",
3506      "                     connected-components uniquely labeled",
3507      "-contrast            enhance or reduce the image contrast",
3508      "-contrast-stretch geometry",
3509      "                     improve contrast by 'stretching' the intensity range",
3510      "-convolve coefficients",
3511      "                     apply a convolution kernel to the image",
3512      "-cycle amount        cycle the image colormap",
3513      "-decipher filename   convert cipher pixels to plain pixels",
3514      "-deskew threshold    straighten an image",
3515      "-despeckle           reduce the speckles within an image",
3516      "-distort method args",
3517      "                     distort images according to given method ad args",
3518      "-draw string         annotate the image with a graphic primitive",
3519      "-edge radius         apply a filter to detect edges in the image",
3520      "-encipher filename   convert plain pixels to cipher pixels",
3521      "-emboss radius       emboss an image",
3522      "-enhance             apply a digital filter to enhance a noisy image",
3523      "-equalize            perform histogram equalization to an image",
3524      "-evaluate operator value",
3525      "                     evaluate an arithmetic, relational, or logical expression",
3526      "-extent geometry     set the image size",
3527      "-extract geometry    extract area from image",
3528      "-fft                 implements the discrete Fourier transform (DFT)",
3529      "-flip                flip image vertically",
3530      "-floodfill geometry color",
3531      "                     floodfill the image with color",
3532      "-flop                flop image horizontally",
3533      "-frame geometry      surround image with an ornamental border",
3534      "-function name parameters",
3535      "                     apply function over image values",
3536      "-gamma value         level of gamma correction",
3537      "-gaussian-blur geometry",
3538      "                     reduce image noise and reduce detail levels",
3539      "-geometry geometry   preferred size or location of the image",
3540      "-grayscale method    convert image to grayscale",
3541      "-hough-lines geometry",
3542      "                     identify lines in the image",
3543      "-identify            identify the format and characteristics of the image",
3544      "-ift                 implements the inverse discrete Fourier transform (DFT)",
3545      "-implode amount      implode image pixels about the center",
3546      "-interpolative-resize geometry",
3547      "                     resize image using interpolation",
3548      "-kuwahara geometry   edge preserving noise reduction filter",
3549      "-lat geometry        local adaptive thresholding",
3550      "-level value         adjust the level of image contrast",
3551      "-level-colors color,color",
3552      "                     level image with the given colors",
3553      "-linear-stretch geometry",
3554      "                     improve contrast by 'stretching with saturation'",
3555      "-liquid-rescale geometry",
3556      "                     rescale image with seam-carving",
3557      "-local-contrast geometry",
3558      "                     enhance local contrast",
3559      "-magnify             double the size of the image with pixel art scaling",
3560      "-mean-shift geometry delineate arbitrarily shaped clusters in the image",
3561      "-median geometry     apply a median filter to the image",
3562      "-mode geometry       make each pixel the 'predominant color' of the",
3563      "                     neighborhood",
3564      "-modulate value      vary the brightness, saturation, and hue",
3565      "-monochrome          transform image to black and white",
3566      "-morphology method kernel",
3567      "                     apply a morphology method to the image",
3568      "-motion-blur geometry",
3569      "                     simulate motion blur",
3570      "-negate              replace every pixel with its complementary color ",
3571      "-noise geometry      add or reduce noise in an image",
3572      "-normalize           transform image to span the full range of colors",
3573      "-opaque color        change this color to the fill color",
3574      "-ordered-dither NxN",
3575      "                     add a noise pattern to the image with specific",
3576      "                     amplitudes",
3577      "-paint radius        simulate an oil painting",
3578      "-perceptible epsilon",
3579      "                     pixel value less than |epsilon| become epsilon or",
3580      "                     -epsilon",
3581      "-polaroid angle      simulate a Polaroid picture",
3582      "-posterize levels    reduce the image to a limited number of color levels",
3583      "-profile filename    add, delete, or apply an image profile",
3584      "-quantize colorspace reduce colors in this colorspace",
3585      "-raise value         lighten/darken image edges to create a 3-D effect",
3586      "-random-threshold low,high",
3587      "                     random threshold the image",
3588      "-region geometry     apply options to a portion of the image",
3589      "-render              render vector graphics",
3590      "-repage geometry     size and location of an image canvas",
3591      "-resample geometry   change the resolution of an image",
3592      "-resize geometry     resize the image",
3593      "-roll geometry       roll an image vertically or horizontally",
3594      "-rotate degrees      apply Paeth rotation to the image",
3595      "-rotational-blur angle",
3596      "                     rotational blur the image",
3597      "-sample geometry     scale image with pixel sampling",
3598      "-scale geometry      scale the image",
3599      "-segment values      segment an image",
3600      "-selective-blur geometry",
3601      "                     selectively blur pixels within a contrast threshold",
3602      "-sepia-tone threshold",
3603      "                     simulate a sepia-toned photo",
3604      "-set property value  set an image property",
3605      "-shade degrees       shade the image using a distant light source",
3606      "-shadow geometry     simulate an image shadow",
3607      "-sharpen geometry    sharpen the image",
3608      "-shave geometry      shave pixels from the image edges",
3609      "-shear geometry      slide one edge of the image along the X or Y axis",
3610      "-sigmoidal-contrast geometry",
3611      "                     increase the contrast without saturating highlights or",
3612      "                     shadows",
3613      "-sketch geometry     simulate a pencil sketch",
3614      "-solarize threshold  negate all pixels above the threshold level",
3615      "-sparse-color method args",
3616      "                     fill in a image based on a few color points",
3617      "-splice geometry     splice the background color into the image",
3618      "-spread radius       displace image pixels by a random amount",
3619      "-statistic type radius",
3620      "                     replace each pixel with corresponding statistic from the neighborhood",
3621      "-strip               strip image of all profiles and comments",
3622      "-swirl degrees       swirl image pixels about the center",
3623      "-threshold value     threshold the image",
3624      "-thumbnail geometry  create a thumbnail of the image",
3625      "-tile filename       tile image when filling a graphic primitive",
3626      "-tint value          tint the image with the fill color",
3627      "-transform           affine transform image",
3628      "-transparent color   make this color transparent within the image",
3629      "-transpose           flip image vertically and rotate 90 degrees",
3630      "-transverse          flop image horizontally and rotate 270 degrees",
3631      "-trim                trim image edges",
3632      "-type type           image type",
3633      "-unique-colors       discard all but one of any pixel color",
3634      "-unsharp geometry    sharpen the image",
3635      "-vignette geometry   soften the edges of the image in vignette style",
3636      "-wave geometry       alter an image along a sine wave",
3637      "-wavelet-denoise threshold",
3638      "                     removes noise from the image using a wavelet transform",
3639      "-white-threshold value",
3640      "                     force all pixels above the threshold into white",
3641      (char *) NULL
3642    },
3643    *sequence_operators[]=
3644    {
3645      "-affinity filename   transform image colors to match this set of colors",
3646      "-append              append an image sequence",
3647      "-clut                apply a color lookup table to the image",
3648      "-coalesce            merge a sequence of images",
3649      "-combine             combine a sequence of images",
3650      "-compare             mathematically and visually annotate the difference between an image and its reconstruction",
3651      "-complex operator    perform complex mathematics on an image sequence",
3652      "-composite           composite image",
3653      "-copy geometry offset",
3654      "                     copy pixels from one area of an image to another",
3655      "-crop geometry       cut out a rectangular region of the image",
3656      "-deconstruct         break down an image sequence into constituent parts",
3657      "-evaluate-sequence operator",
3658      "                     evaluate an arithmetic, relational, or logical expression",
3659      "-flatten             flatten a sequence of images",
3660      "-fx expression       apply mathematical expression to an image channel(s)",
3661      "-hald-clut           apply a Hald color lookup table to the image",
3662      "-layers method       optimize, merge, or compare image layers",
3663      "-morph value         morph an image sequence",
3664      "-mosaic              create a mosaic from an image sequence",
3665      "-poly terms          build a polynomial from the image sequence and the corresponding",
3666      "                     terms (coefficients and degree pairs).",
3667      "-print string        interpret string and print to console",
3668      "-process arguments   process the image with a custom image filter",
3669      "-smush geometry      smush an image sequence together",
3670      "-write filename      write images to this file",
3671      (char *) NULL
3672    },
3673    *settings[]=
3674    {
3675      "-adjoin              join images into a single multi-image file",
3676      "-affine matrix       affine transform matrix",
3677      "-alpha option        activate, deactivate, reset, or set the alpha channel",
3678      "-alpha-color color   frame color",
3679      "-antialias           remove pixel-aliasing",
3680      "-authenticate password",
3681      "                     decipher image with this password",
3682      "-attenuate value     lessen (or intensify) when adding noise to an image",
3683      "-background color    background color",
3684      "-bias value          add bias when convolving an image",
3685      "-black-point-compensation",
3686      "                     use black point compensation",
3687      "-blue-primary point  chromaticity blue primary point",
3688      "-bordercolor color   border color",
3689      "-caption string      assign a caption to an image",
3690      "-colors value        preferred number of colors in the image",
3691      "-colorspace type     alternate image colorspace",
3692      "-comment string      annotate image with comment",
3693      "-compose operator    set image composite operator",
3694      "-compress type       type of pixel compression when writing the image",
3695      "-define format:option=value",
3696      "                     define one or more image format options",
3697      "-delay value         display the next image after pausing",
3698      "-density geometry    horizontal and vertical density of the image",
3699      "-depth value         image depth",
3700      "-direction type      render text right-to-left or left-to-right",
3701      "-display server      get image or font from this X server",
3702      "-dispose method      layer disposal method",
3703      "-dither method       apply error diffusion to image",
3704      "-encoding type       text encoding type",
3705      "-endian type         endianness (MSB or LSB) of the image",
3706      "-family name         render text with this font family",
3707      "-features distance   analyze image features (e.g. contrast, correlation)",
3708      "-fill color          color to use when filling a graphic primitive",
3709      "-filter type         use this filter when resizing an image",
3710      "-font name           render text with this font",
3711      "-format \"string\"   output formatted image characteristics",
3712      "-fuzz distance       colors within this distance are considered equal",
3713      "-gravity type        horizontal and vertical text placement",
3714      "-green-primary point chromaticity green primary point",
3715      "-intensity method    method to generate an intensity value from a pixel",
3716      "-intent type         type of rendering intent when managing the image color",
3717      "-interlace type      type of image interlacing scheme",
3718      "-interline-spacing value",
3719      "                     set the space between two text lines",
3720      "-interpolate method  pixel color interpolation method",
3721      "-interword-spacing value",
3722      "                     set the space between two words",
3723      "-kerning value       set the space between two letters",
3724      "-label string        assign a label to an image",
3725      "-limit type value    pixel cache resource limit",
3726      "-loop iterations     add Netscape loop extension to your GIF animation",
3727      "-matte               store matte channel if the image has one",
3728      "-monitor             monitor progress",
3729      "-orient type         image orientation",
3730      "-page geometry       size and location of an image canvas (setting)",
3731      "-path path           write images to this path on disk",
3732      "-ping                efficiently determine image attributes",
3733      "-pointsize value     font point size",
3734      "-precision value     maximum number of significant digits to print",
3735      "-preview type        image preview type",
3736      "-quality value       JPEG/MIFF/PNG compression level",
3737      "-quiet               suppress all warning messages",
3738      "-read-mask filename  associate a read mask with the image",
3739      "-red-primary point   chromaticity red primary point",
3740      "-regard-warnings     pay attention to warning messages",
3741      "-remap filename      transform image colors to match this set of colors",
3742      "-respect-parentheses settings remain in effect until parenthesis boundary",
3743      "-sampling-factor geometry",
3744      "                     horizontal and vertical sampling factor",
3745      "-scene value         image scene number",
3746      "-seed value          seed a new sequence of pseudo-random numbers",
3747      "-size geometry       width and height of image",
3748      "-stretch type        render text with this font stretch",
3749      "-stroke color        graphic primitive stroke color",
3750      "-strokewidth value   graphic primitive stroke width",
3751      "-style type          render text with this font style",
3752      "-synchronize         synchronize image to storage device",
3753      "-taint               declare the image as modified",
3754      "-texture filename    name of texture to tile onto the image background",
3755      "-tile-offset geometry",
3756      "                     tile offset",
3757      "-treedepth value     color tree depth",
3758      "-transparent-color color",
3759      "                     transparent color",
3760      "-undercolor color    annotation bounding box color",
3761      "-units type          the units of image resolution",
3762      "-verbose             print detailed information about the image",
3763      "-view                FlashPix viewing transforms",
3764      "-virtual-pixel method",
3765      "                     virtual pixel access method",
3766      "-weight type         render text with this font weight",
3767      "-white-point point   chromaticity white point",
3768      "-write-mask filename associate a write mask with the image",
3769      (char *) NULL
3770    },
3771    *stack_operators[]=
3772    {
3773      "-delete indexes      delete the image from the image sequence",
3774      "-duplicate count,indexes",
3775      "                     duplicate an image one or more times",
3776      "-insert index        insert last image into the image sequence",
3777      "-reverse             reverse image sequence",
3778      "-swap indexes        swap two images in the image sequence",
3779      (char *) NULL
3780    };
3781
3782  const char
3783    **p;
3784
3785  ListMagickVersion(stdout);
3786  (void) printf("Usage: %s [options ...] file [ [options ...] file ...]\n",
3787    GetClientName());
3788  (void) printf("\nImage Settings:\n");
3789  for (p=settings; *p != (char *) NULL; p++)
3790    (void) printf("  %s\n",*p);
3791  (void) printf("\nImage Operators:\n");
3792  for (p=operators; *p != (char *) NULL; p++)
3793    (void) printf("  %s\n",*p);
3794  (void) printf("\nImage Channel Operators:\n");
3795  for (p=channel_operators; *p != (char *) NULL; p++)
3796    (void) printf("  %s\n",*p);
3797  (void) printf("\nImage Sequence Operators:\n");
3798  for (p=sequence_operators; *p != (char *) NULL; p++)
3799    (void) printf("  %s\n",*p);
3800  (void) printf("\nImage Stack Operators:\n");
3801  for (p=stack_operators; *p != (char *) NULL; p++)
3802    (void) printf("  %s\n",*p);
3803  (void) printf("\nMiscellaneous Options:\n");
3804  for (p=miscellaneous; *p != (char *) NULL; p++)
3805    (void) printf("  %s\n",*p);
3806  (void) printf(
3807    "\nBy default, the image format of 'file' is determined by its magic\n");
3808  (void) printf(
3809    "number.  To specify a particular image format, precede the filename\n");
3810  (void) printf(
3811    "with an image format name and a colon (i.e. ps:image) or specify the\n");
3812  (void) printf(
3813    "image type as the filename suffix (i.e. image.ps).  Specify 'file' as\n");
3814  (void) printf("'-' for standard input or output.\n");
3815  return(MagickFalse);
3816}
3817
3818WandExport MagickBooleanType MogrifyImageCommand(ImageInfo *image_info,
3819  int argc,char **argv,char **wand_unused(metadata),ExceptionInfo *exception)
3820{
3821#define DestroyMogrify() \
3822{ \
3823  if (format != (char *) NULL) \
3824    format=DestroyString(format); \
3825  if (path != (char *) NULL) \
3826    path=DestroyString(path); \
3827  DestroyImageStack(); \
3828  for (i=0; i < (ssize_t) argc; i++) \
3829    argv[i]=DestroyString(argv[i]); \
3830  argv=(char **) RelinquishMagickMemory(argv); \
3831}
3832#define ThrowMogrifyException(asperity,tag,option) \
3833{ \
3834  (void) ThrowMagickException(exception,GetMagickModule(),asperity,tag,"`%s'", \
3835    option); \
3836  DestroyMogrify(); \
3837  return(MagickFalse); \
3838}
3839#define ThrowMogrifyInvalidArgumentException(option,argument) \
3840{ \
3841  (void) ThrowMagickException(exception,GetMagickModule(),OptionError, \
3842    "InvalidArgument","'%s': %s",argument,option); \
3843  DestroyMogrify(); \
3844  return(MagickFalse); \
3845}
3846
3847  char
3848    *format,
3849    *option,
3850    *path;
3851
3852  Image
3853    *image;
3854
3855  ImageStack
3856    image_stack[MaxImageStackDepth+1];
3857
3858  MagickBooleanType
3859    global_colormap;
3860
3861  MagickBooleanType
3862    fire,
3863    pend,
3864    respect_parenthesis;
3865
3866  MagickStatusType
3867    status;
3868
3869  register ssize_t
3870    i;
3871
3872  ssize_t
3873    j,
3874    k;
3875
3876  /*
3877    Set defaults.
3878  */
3879  assert(image_info != (ImageInfo *) NULL);
3880  assert(image_info->signature == MagickCoreSignature);
3881  if (image_info->debug != MagickFalse)
3882    (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
3883  assert(exception != (ExceptionInfo *) NULL);
3884  if (argc == 2)
3885    {
3886      option=argv[1];
3887      if ((LocaleCompare("version",option+1) == 0) ||
3888          (LocaleCompare("-version",option+1) == 0))
3889        {
3890          ListMagickVersion(stdout);
3891          return(MagickTrue);
3892        }
3893    }
3894  if (argc < 2)
3895    return(MogrifyUsage());
3896  format=(char *) NULL;
3897  path=(char *) NULL;
3898  global_colormap=MagickFalse;
3899  k=0;
3900  j=1;
3901  NewImageStack();
3902  option=(char *) NULL;
3903  pend=MagickFalse;
3904  respect_parenthesis=MagickFalse;
3905  status=MagickTrue;
3906  /*
3907    Parse command line.
3908  */
3909  ReadCommandlLine(argc,&argv);
3910  status=ExpandFilenames(&argc,&argv);
3911  if (status == MagickFalse)
3912    ThrowMogrifyException(ResourceLimitError,"MemoryAllocationFailed",
3913      GetExceptionMessage(errno));
3914  for (i=1; i < (ssize_t) argc; i++)
3915  {
3916    option=argv[i];
3917    if (LocaleCompare(option,"(") == 0)
3918      {
3919        FireImageStack(MagickFalse,MagickTrue,pend);
3920        if (k == MaxImageStackDepth)
3921          ThrowMogrifyException(OptionError,"ParenthesisNestedTooDeeply",
3922            option);
3923        PushImageStack();
3924        continue;
3925      }
3926    if (LocaleCompare(option,")") == 0)
3927      {
3928        FireImageStack(MagickFalse,MagickTrue,MagickTrue);
3929        if (k == 0)
3930          ThrowMogrifyException(OptionError,"UnableToParseExpression",option);
3931        PopImageStack();
3932        continue;
3933      }
3934    if (IsCommandOption(option) == MagickFalse)
3935      {
3936        char
3937          backup_filename[MagickPathExtent],
3938          *filename;
3939
3940        Image
3941          *images;
3942
3943        struct stat
3944          properties;
3945
3946        /*
3947          Option is a file name: begin by reading image from specified file.
3948        */
3949        FireImageStack(MagickFalse,MagickFalse,pend);
3950        filename=argv[i];
3951        if ((LocaleCompare(filename,"--") == 0) && (i < (ssize_t) (argc-1)))
3952          filename=argv[++i];
3953        images=ReadImages(image_info,filename,exception);
3954        status&=(images != (Image *) NULL) &&
3955          (exception->severity < ErrorException);
3956        if (images == (Image *) NULL)
3957          continue;
3958        properties=(*GetBlobProperties(images));
3959        if (format != (char *) NULL)
3960          (void) CopyMagickString(images->filename,images->magick_filename,
3961            MagickPathExtent);
3962        if (path != (char *) NULL)
3963          {
3964            GetPathComponent(option,TailPath,filename);
3965            (void) FormatLocaleString(images->filename,MagickPathExtent,
3966              "%s%c%s",path,*DirectorySeparator,filename);
3967          }
3968        if (format != (char *) NULL)
3969          AppendImageFormat(format,images->filename);
3970        AppendImageStack(images);
3971        FinalizeImageSettings(image_info,image,MagickFalse);
3972        if (global_colormap != MagickFalse)
3973          {
3974            QuantizeInfo
3975              *quantize_info;
3976
3977            quantize_info=AcquireQuantizeInfo(image_info);
3978            (void) RemapImages(quantize_info,images,(Image *) NULL,exception);
3979            quantize_info=DestroyQuantizeInfo(quantize_info);
3980          }
3981        *backup_filename='\0';
3982        if ((LocaleCompare(image->filename,"-") != 0) &&
3983            (IsPathWritable(image->filename) != MagickFalse))
3984          {
3985            /*
3986              Rename image file as backup.
3987            */
3988            (void) CopyMagickString(backup_filename,image->filename,
3989              MagickPathExtent);
3990            for (j=0; j < 6; j++)
3991            {
3992              (void) ConcatenateMagickString(backup_filename,"~",
3993                MagickPathExtent);
3994              if (IsPathAccessible(backup_filename) == MagickFalse)
3995                break;
3996            }
3997            if ((IsPathAccessible(backup_filename) != MagickFalse) ||
3998                (rename_utf8(image->filename,backup_filename) != 0))
3999              *backup_filename='\0';
4000          }
4001        /*
4002          Write transmogrified image to disk.
4003        */
4004        image_info->synchronize=MagickTrue;
4005        status&=WriteImages(image_info,image,image->filename,exception);
4006        if (status != MagickFalse)
4007          {
4008#if defined(MAGICKCORE_HAVE_UTIME)
4009            {
4010              MagickBooleanType
4011                preserve_timestamp;
4012
4013              preserve_timestamp=IsStringTrue(GetImageOption(image_info,
4014                "preserve-timestamp"));
4015              if (preserve_timestamp != MagickFalse)
4016                {
4017                  struct utimbuf
4018                    timestamp;
4019
4020                  timestamp.actime=properties.st_atime;
4021                  timestamp.modtime=properties.st_mtime;
4022                  (void) utime(image->filename,&timestamp);
4023                }
4024            }
4025#endif
4026            if (*backup_filename != '\0')
4027              (void) remove_utf8(backup_filename);
4028          }
4029        RemoveAllImageStack();
4030        continue;
4031      }
4032    pend=image != (Image *) NULL ? MagickTrue : MagickFalse;
4033    switch (*(option+1))
4034    {
4035      case 'a':
4036      {
4037        if (LocaleCompare("adaptive-blur",option+1) == 0)
4038          {
4039            i++;
4040            if (i == (ssize_t) argc)
4041              ThrowMogrifyException(OptionError,"MissingArgument",option);
4042            if (IsGeometry(argv[i]) == MagickFalse)
4043              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4044            break;
4045          }
4046        if (LocaleCompare("adaptive-resize",option+1) == 0)
4047          {
4048            i++;
4049            if (i == (ssize_t) argc)
4050              ThrowMogrifyException(OptionError,"MissingArgument",option);
4051            if (IsGeometry(argv[i]) == MagickFalse)
4052              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4053            break;
4054          }
4055        if (LocaleCompare("adaptive-sharpen",option+1) == 0)
4056          {
4057            i++;
4058            if (i == (ssize_t) argc)
4059              ThrowMogrifyException(OptionError,"MissingArgument",option);
4060            if (IsGeometry(argv[i]) == MagickFalse)
4061              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4062            break;
4063          }
4064        if (LocaleCompare("affine",option+1) == 0)
4065          {
4066            if (*option == '+')
4067              break;
4068            i++;
4069            if (i == (ssize_t) argc)
4070              ThrowMogrifyException(OptionError,"MissingArgument",option);
4071            break;
4072          }
4073        if (LocaleCompare("alpha",option+1) == 0)
4074          {
4075            ssize_t
4076              type;
4077
4078            if (*option == '+')
4079              break;
4080            i++;
4081            if (i == (ssize_t) argc)
4082              ThrowMogrifyException(OptionError,"MissingArgument",option);
4083            type=ParseCommandOption(MagickAlphaChannelOptions,MagickFalse,
4084              argv[i]);
4085            if (type < 0)
4086              ThrowMogrifyException(OptionError,
4087                "UnrecognizedAlphaChannelOption",argv[i]);
4088            break;
4089          }
4090        if (LocaleCompare("alpha-color",option+1) == 0)
4091          {
4092            if (*option == '+')
4093              break;
4094            i++;
4095            if (i == (ssize_t) argc)
4096              ThrowMogrifyException(OptionError,"MissingArgument",option);
4097            break;
4098          }
4099        if (LocaleCompare("annotate",option+1) == 0)
4100          {
4101            if (*option == '+')
4102              break;
4103            i++;
4104            if (i == (ssize_t) argc)
4105              ThrowMogrifyException(OptionError,"MissingArgument",option);
4106            if (IsGeometry(argv[i]) == MagickFalse)
4107              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4108            if (i == (ssize_t) argc)
4109              ThrowMogrifyException(OptionError,"MissingArgument",option);
4110            i++;
4111            break;
4112          }
4113        if (LocaleCompare("antialias",option+1) == 0)
4114          break;
4115        if (LocaleCompare("append",option+1) == 0)
4116          break;
4117        if (LocaleCompare("attenuate",option+1) == 0)
4118          {
4119            if (*option == '+')
4120              break;
4121            i++;
4122            if (i == (ssize_t) argc)
4123              ThrowMogrifyException(OptionError,"MissingArgument",option);
4124            if (IsGeometry(argv[i]) == MagickFalse)
4125              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4126            break;
4127          }
4128        if (LocaleCompare("authenticate",option+1) == 0)
4129          {
4130            if (*option == '+')
4131              break;
4132            i++;
4133            if (i == (ssize_t) argc)
4134              ThrowMogrifyException(OptionError,"MissingArgument",option);
4135            break;
4136          }
4137        if (LocaleCompare("auto-gamma",option+1) == 0)
4138          break;
4139        if (LocaleCompare("auto-level",option+1) == 0)
4140          break;
4141        if (LocaleCompare("auto-orient",option+1) == 0)
4142          break;
4143        if (LocaleCompare("average",option+1) == 0)
4144          break;
4145        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
4146      }
4147      case 'b':
4148      {
4149        if (LocaleCompare("background",option+1) == 0)
4150          {
4151            if (*option == '+')
4152              break;
4153            i++;
4154            if (i == (ssize_t) argc)
4155              ThrowMogrifyException(OptionError,"MissingArgument",option);
4156            break;
4157          }
4158        if (LocaleCompare("bias",option+1) == 0)
4159          {
4160            if (*option == '+')
4161              break;
4162            i++;
4163            if (i == (ssize_t) argc)
4164              ThrowMogrifyException(OptionError,"MissingArgument",option);
4165            if (IsGeometry(argv[i]) == MagickFalse)
4166              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4167            break;
4168          }
4169        if (LocaleCompare("black-point-compensation",option+1) == 0)
4170          break;
4171        if (LocaleCompare("black-threshold",option+1) == 0)
4172          {
4173            if (*option == '+')
4174              break;
4175            i++;
4176            if (i == (ssize_t) argc)
4177              ThrowMogrifyException(OptionError,"MissingArgument",option);
4178            if (IsGeometry(argv[i]) == MagickFalse)
4179              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4180            break;
4181          }
4182        if (LocaleCompare("blue-primary",option+1) == 0)
4183          {
4184            if (*option == '+')
4185              break;
4186            i++;
4187            if (i == (ssize_t) argc)
4188              ThrowMogrifyException(OptionError,"MissingArgument",option);
4189            if (IsGeometry(argv[i]) == MagickFalse)
4190              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4191            break;
4192          }
4193        if (LocaleCompare("blue-shift",option+1) == 0)
4194          {
4195            i++;
4196            if (i == (ssize_t) argc)
4197              ThrowMogrifyException(OptionError,"MissingArgument",option);
4198            if (IsGeometry(argv[i]) == MagickFalse)
4199              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4200            break;
4201          }
4202        if (LocaleCompare("blur",option+1) == 0)
4203          {
4204            i++;
4205            if (i == (ssize_t) argc)
4206              ThrowMogrifyException(OptionError,"MissingArgument",option);
4207            if (IsGeometry(argv[i]) == MagickFalse)
4208              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4209            break;
4210          }
4211        if (LocaleCompare("border",option+1) == 0)
4212          {
4213            if (*option == '+')
4214              break;
4215            i++;
4216            if (i == (ssize_t) argc)
4217              ThrowMogrifyException(OptionError,"MissingArgument",option);
4218            if (IsGeometry(argv[i]) == MagickFalse)
4219              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4220            break;
4221          }
4222        if (LocaleCompare("bordercolor",option+1) == 0)
4223          {
4224            if (*option == '+')
4225              break;
4226            i++;
4227            if (i == (ssize_t) argc)
4228              ThrowMogrifyException(OptionError,"MissingArgument",option);
4229            break;
4230          }
4231        if (LocaleCompare("box",option+1) == 0)
4232          {
4233            if (*option == '+')
4234              break;
4235            i++;
4236            if (i == (ssize_t) argc)
4237              ThrowMogrifyException(OptionError,"MissingArgument",option);
4238            break;
4239          }
4240        if (LocaleCompare("brightness-contrast",option+1) == 0)
4241          {
4242            i++;
4243            if (i == (ssize_t) argc)
4244              ThrowMogrifyException(OptionError,"MissingArgument",option);
4245            if (IsGeometry(argv[i]) == MagickFalse)
4246              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4247            break;
4248          }
4249        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
4250      }
4251      case 'c':
4252      {
4253        if (LocaleCompare("cache",option+1) == 0)
4254          {
4255            if (*option == '+')
4256              break;
4257            i++;
4258            if (i == (ssize_t) argc)
4259              ThrowMogrifyException(OptionError,"MissingArgument",option);
4260            if (IsGeometry(argv[i]) == MagickFalse)
4261              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4262            break;
4263          }
4264        if (LocaleCompare("canny",option+1) == 0)
4265          {
4266            if (*option == '+')
4267              break;
4268            i++;
4269            if (i == (ssize_t) argc)
4270              ThrowMogrifyException(OptionError,"MissingArgument",option);
4271            if (IsGeometry(argv[i]) == MagickFalse)
4272              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4273            break;
4274          }
4275        if (LocaleCompare("caption",option+1) == 0)
4276          {
4277            if (*option == '+')
4278              break;
4279            i++;
4280            if (i == (ssize_t) argc)
4281              ThrowMogrifyException(OptionError,"MissingArgument",option);
4282            break;
4283          }
4284        if (LocaleCompare("channel",option+1) == 0)
4285          {
4286            ssize_t
4287              channel;
4288
4289            if (*option == '+')
4290              break;
4291            i++;
4292            if (i == (ssize_t) argc)
4293              ThrowMogrifyException(OptionError,"MissingArgument",option);
4294            channel=ParseChannelOption(argv[i]);
4295            if (channel < 0)
4296              ThrowMogrifyException(OptionError,"UnrecognizedChannelType",
4297                argv[i]);
4298            break;
4299          }
4300        if (LocaleCompare("channel-fx",option+1) == 0)
4301          {
4302            ssize_t
4303              channel;
4304
4305            if (*option == '+')
4306              break;
4307            i++;
4308            if (i == (ssize_t) argc)
4309              ThrowMogrifyException(OptionError,"MissingArgument",option);
4310            channel=ParsePixelChannelOption(argv[i]);
4311            if (channel < 0)
4312              ThrowMogrifyException(OptionError,"UnrecognizedChannelType",
4313                argv[i]);
4314            break;
4315          }
4316        if (LocaleCompare("cdl",option+1) == 0)
4317          {
4318            if (*option == '+')
4319              break;
4320            i++;
4321            if (i == (ssize_t) argc)
4322              ThrowMogrifyException(OptionError,"MissingArgument",option);
4323            break;
4324          }
4325        if (LocaleCompare("charcoal",option+1) == 0)
4326          {
4327            if (*option == '+')
4328              break;
4329            i++;
4330            if (i == (ssize_t) argc)
4331              ThrowMogrifyException(OptionError,"MissingArgument",option);
4332            if (IsGeometry(argv[i]) == MagickFalse)
4333              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4334            break;
4335          }
4336        if (LocaleCompare("chop",option+1) == 0)
4337          {
4338            if (*option == '+')
4339              break;
4340            i++;
4341            if (i == (ssize_t) argc)
4342              ThrowMogrifyException(OptionError,"MissingArgument",option);
4343            if (IsGeometry(argv[i]) == MagickFalse)
4344              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4345            break;
4346          }
4347        if (LocaleCompare("clamp",option+1) == 0)
4348          break;
4349        if (LocaleCompare("clip",option+1) == 0)
4350          break;
4351        if (LocaleCompare("clip-mask",option+1) == 0)
4352          {
4353            if (*option == '+')
4354              break;
4355            i++;
4356            if (i == (ssize_t) argc)
4357              ThrowMogrifyException(OptionError,"MissingArgument",option);
4358            break;
4359          }
4360        if (LocaleCompare("clut",option+1) == 0)
4361          break;
4362        if (LocaleCompare("coalesce",option+1) == 0)
4363          break;
4364        if (LocaleCompare("colorize",option+1) == 0)
4365          {
4366            if (*option == '+')
4367              break;
4368            i++;
4369            if (i == (ssize_t) argc)
4370              ThrowMogrifyException(OptionError,"MissingArgument",option);
4371            if (IsGeometry(argv[i]) == MagickFalse)
4372              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4373            break;
4374          }
4375        if (LocaleCompare("color-matrix",option+1) == 0)
4376          {
4377            KernelInfo
4378              *kernel_info;
4379
4380            if (*option == '+')
4381              break;
4382            i++;
4383            if (i == (ssize_t) argc)
4384              ThrowMogrifyException(OptionError,"MissingArgument",option);
4385            kernel_info=AcquireKernelInfo(argv[i],exception);
4386            if (kernel_info == (KernelInfo *) NULL)
4387              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4388            kernel_info=DestroyKernelInfo(kernel_info);
4389            break;
4390          }
4391        if (LocaleCompare("colors",option+1) == 0)
4392          {
4393            if (*option == '+')
4394              break;
4395            i++;
4396            if (i == (ssize_t) argc)
4397              ThrowMogrifyException(OptionError,"MissingArgument",option);
4398            if (IsGeometry(argv[i]) == MagickFalse)
4399              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4400            break;
4401          }
4402        if (LocaleCompare("colorspace",option+1) == 0)
4403          {
4404            ssize_t
4405              colorspace;
4406
4407            if (*option == '+')
4408              break;
4409            i++;
4410            if (i == (ssize_t) argc)
4411              ThrowMogrifyException(OptionError,"MissingArgument",option);
4412            colorspace=ParseCommandOption(MagickColorspaceOptions,MagickFalse,
4413              argv[i]);
4414            if (colorspace < 0)
4415              ThrowMogrifyException(OptionError,"UnrecognizedColorspace",
4416                argv[i]);
4417            break;
4418          }
4419        if (LocaleCompare("combine",option+1) == 0)
4420          {
4421            ssize_t
4422              colorspace;
4423
4424            if (*option == '+')
4425              break;
4426            i++;
4427            if (i == (ssize_t) argc)
4428              ThrowMogrifyException(OptionError,"MissingArgument",option);
4429            colorspace=ParseCommandOption(MagickColorspaceOptions,MagickFalse,
4430              argv[i]);
4431            if (colorspace < 0)
4432              ThrowMogrifyException(OptionError,"UnrecognizedColorspace",
4433                argv[i]);
4434            break;
4435          }
4436        if (LocaleCompare("compare",option+1) == 0)
4437          break;
4438        if (LocaleCompare("comment",option+1) == 0)
4439          {
4440            if (*option == '+')
4441              break;
4442            i++;
4443            if (i == (ssize_t) argc)
4444              ThrowMogrifyException(OptionError,"MissingArgument",option);
4445            break;
4446          }
4447        if (LocaleCompare("composite",option+1) == 0)
4448          break;
4449        if (LocaleCompare("compress",option+1) == 0)
4450          {
4451            ssize_t
4452              compress;
4453
4454            if (*option == '+')
4455              break;
4456            i++;
4457            if (i == (ssize_t) argc)
4458              ThrowMogrifyException(OptionError,"MissingArgument",option);
4459            compress=ParseCommandOption(MagickCompressOptions,MagickFalse,
4460              argv[i]);
4461            if (compress < 0)
4462              ThrowMogrifyException(OptionError,"UnrecognizedImageCompression",
4463                argv[i]);
4464            break;
4465          }
4466        if (LocaleCompare("concurrent",option+1) == 0)
4467          break;
4468        if (LocaleCompare("connected-components",option+1) == 0)
4469          {
4470            i++;
4471            if (i == (ssize_t) argc)
4472              ThrowMogrifyException(OptionError,"MissingArgument",option);
4473            if (IsGeometry(argv[i]) == MagickFalse)
4474              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4475            break;
4476          }
4477        if (LocaleCompare("contrast",option+1) == 0)
4478          break;
4479        if (LocaleCompare("contrast-stretch",option+1) == 0)
4480          {
4481            i++;
4482            if (i == (ssize_t) argc)
4483              ThrowMogrifyException(OptionError,"MissingArgument",option);
4484            if (IsGeometry(argv[i]) == MagickFalse)
4485              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4486            break;
4487          }
4488        if (LocaleCompare("convolve",option+1) == 0)
4489          {
4490            KernelInfo
4491              *kernel_info;
4492
4493            if (*option == '+')
4494              break;
4495            i++;
4496            if (i == (ssize_t) argc)
4497              ThrowMogrifyException(OptionError,"MissingArgument",option);
4498            kernel_info=AcquireKernelInfo(argv[i],exception);
4499            if (kernel_info == (KernelInfo *) NULL)
4500              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4501            kernel_info=DestroyKernelInfo(kernel_info);
4502            break;
4503          }
4504        if (LocaleCompare("copy",option+1) == 0)
4505          {
4506            if (*option == '+')
4507              break;
4508            i++;
4509            if (i == (ssize_t) argc)
4510              ThrowMogrifyException(OptionError,"MissingArgument",option);
4511            if (IsGeometry(argv[i]) == MagickFalse)
4512              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4513            i++;
4514            if (i == (ssize_t) argc)
4515              ThrowMogrifyException(OptionError,"MissingArgument",option);
4516            if (IsGeometry(argv[i]) == MagickFalse)
4517              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4518            break;
4519          }
4520        if (LocaleCompare("crop",option+1) == 0)
4521          {
4522            if (*option == '+')
4523              break;
4524            i++;
4525            if (i == (ssize_t) argc)
4526              ThrowMogrifyException(OptionError,"MissingArgument",option);
4527            if (IsGeometry(argv[i]) == MagickFalse)
4528              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4529            break;
4530          }
4531        if (LocaleCompare("cycle",option+1) == 0)
4532          {
4533            if (*option == '+')
4534              break;
4535            i++;
4536            if (i == (ssize_t) argc)
4537              ThrowMogrifyException(OptionError,"MissingArgument",option);
4538            if (IsGeometry(argv[i]) == MagickFalse)
4539              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4540            break;
4541          }
4542        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
4543      }
4544      case 'd':
4545      {
4546        if (LocaleCompare("decipher",option+1) == 0)
4547          {
4548            if (*option == '+')
4549              break;
4550            i++;
4551            if (i == (ssize_t) argc)
4552              ThrowMogrifyException(OptionError,"MissingArgument",option);
4553            break;
4554          }
4555        if (LocaleCompare("deconstruct",option+1) == 0)
4556          break;
4557        if (LocaleCompare("debug",option+1) == 0)
4558          {
4559            ssize_t
4560              event;
4561
4562            if (*option == '+')
4563              break;
4564            i++;
4565            if (i == (ssize_t) argc)
4566              ThrowMogrifyException(OptionError,"MissingArgument",option);
4567            event=ParseCommandOption(MagickLogEventOptions,MagickFalse,argv[i]);
4568            if (event < 0)
4569              ThrowMogrifyException(OptionError,"UnrecognizedEventType",
4570                argv[i]);
4571            (void) SetLogEventMask(argv[i]);
4572            break;
4573          }
4574        if (LocaleCompare("define",option+1) == 0)
4575          {
4576            i++;
4577            if (i == (ssize_t) argc)
4578              ThrowMogrifyException(OptionError,"MissingArgument",option);
4579            if (*option == '+')
4580              {
4581                const char
4582                  *define;
4583
4584                define=GetImageOption(image_info,argv[i]);
4585                if (define == (const char *) NULL)
4586                  ThrowMogrifyException(OptionError,"NoSuchOption",argv[i]);
4587                break;
4588              }
4589            break;
4590          }
4591        if (LocaleCompare("delay",option+1) == 0)
4592          {
4593            if (*option == '+')
4594              break;
4595            i++;
4596            if (i == (ssize_t) argc)
4597              ThrowMogrifyException(OptionError,"MissingArgument",option);
4598            if (IsGeometry(argv[i]) == MagickFalse)
4599              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4600            break;
4601          }
4602        if (LocaleCompare("delete",option+1) == 0)
4603          {
4604            if (*option == '+')
4605              break;
4606            i++;
4607            if (i == (ssize_t) argc)
4608              ThrowMogrifyException(OptionError,"MissingArgument",option);
4609            if (IsGeometry(argv[i]) == MagickFalse)
4610              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4611            break;
4612          }
4613        if (LocaleCompare("density",option+1) == 0)
4614          {
4615            if (*option == '+')
4616              break;
4617            i++;
4618            if (i == (ssize_t) argc)
4619              ThrowMogrifyException(OptionError,"MissingArgument",option);
4620            if (IsGeometry(argv[i]) == MagickFalse)
4621              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4622            break;
4623          }
4624        if (LocaleCompare("depth",option+1) == 0)
4625          {
4626            if (*option == '+')
4627              break;
4628            i++;
4629            if (i == (ssize_t) argc)
4630              ThrowMogrifyException(OptionError,"MissingArgument",option);
4631            if (IsGeometry(argv[i]) == MagickFalse)
4632              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4633            break;
4634          }
4635        if (LocaleCompare("deskew",option+1) == 0)
4636          {
4637            if (*option == '+')
4638              break;
4639            i++;
4640            if (i == (ssize_t) argc)
4641              ThrowMogrifyException(OptionError,"MissingArgument",option);
4642            if (IsGeometry(argv[i]) == MagickFalse)
4643              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4644            break;
4645          }
4646        if (LocaleCompare("despeckle",option+1) == 0)
4647          break;
4648        if (LocaleCompare("dft",option+1) == 0)
4649          break;
4650        if (LocaleCompare("direction",option+1) == 0)
4651          {
4652            ssize_t
4653              direction;
4654
4655            if (*option == '+')
4656              break;
4657            i++;
4658            if (i == (ssize_t) argc)
4659              ThrowMogrifyException(OptionError,"MissingArgument",option);
4660            direction=ParseCommandOption(MagickDirectionOptions,MagickFalse,
4661              argv[i]);
4662            if (direction < 0)
4663              ThrowMogrifyException(OptionError,"UnrecognizedDirectionType",
4664                argv[i]);
4665            break;
4666          }
4667        if (LocaleCompare("display",option+1) == 0)
4668          {
4669            if (*option == '+')
4670              break;
4671            i++;
4672            if (i == (ssize_t) argc)
4673              ThrowMogrifyException(OptionError,"MissingArgument",option);
4674            break;
4675          }
4676        if (LocaleCompare("dispose",option+1) == 0)
4677          {
4678            ssize_t
4679              dispose;
4680
4681            if (*option == '+')
4682              break;
4683            i++;
4684            if (i == (ssize_t) argc)
4685              ThrowMogrifyException(OptionError,"MissingArgument",option);
4686            dispose=ParseCommandOption(MagickDisposeOptions,MagickFalse,
4687              argv[i]);
4688            if (dispose < 0)
4689              ThrowMogrifyException(OptionError,"UnrecognizedDisposeMethod",
4690                argv[i]);
4691            break;
4692          }
4693        if (LocaleCompare("distort",option+1) == 0)
4694          {
4695            ssize_t
4696              op;
4697
4698            i++;
4699            if (i == (ssize_t) argc)
4700              ThrowMogrifyException(OptionError,"MissingArgument",option);
4701            op=ParseCommandOption(MagickDistortOptions,MagickFalse,argv[i]);
4702            if (op < 0)
4703              ThrowMogrifyException(OptionError,"UnrecognizedDistortMethod",
4704                argv[i]);
4705            i++;
4706            if (i == (ssize_t) argc)
4707              ThrowMogrifyException(OptionError,"MissingArgument",option);
4708            break;
4709          }
4710        if (LocaleCompare("dither",option+1) == 0)
4711          {
4712            ssize_t
4713              method;
4714
4715            if (*option == '+')
4716              break;
4717            i++;
4718            if (i == (ssize_t) argc)
4719              ThrowMogrifyException(OptionError,"MissingArgument",option);
4720            method=ParseCommandOption(MagickDitherOptions,MagickFalse,argv[i]);
4721            if (method < 0)
4722              ThrowMogrifyException(OptionError,"UnrecognizedDitherMethod",
4723                argv[i]);
4724            break;
4725          }
4726        if (LocaleCompare("draw",option+1) == 0)
4727          {
4728            if (*option == '+')
4729              break;
4730            i++;
4731            if (i == (ssize_t) argc)
4732              ThrowMogrifyException(OptionError,"MissingArgument",option);
4733            break;
4734          }
4735        if (LocaleCompare("duplicate",option+1) == 0)
4736          {
4737            if (*option == '+')
4738              break;
4739            i++;
4740            if (i == (ssize_t) argc)
4741              ThrowMogrifyException(OptionError,"MissingArgument",option);
4742            if (IsGeometry(argv[i]) == MagickFalse)
4743              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4744            break;
4745          }
4746        if (LocaleCompare("duration",option+1) == 0)
4747          {
4748            if (*option == '+')
4749              break;
4750            i++;
4751            if (i == (ssize_t) argc)
4752              ThrowMogrifyException(OptionError,"MissingArgument",option);
4753            if (IsGeometry(argv[i]) == MagickFalse)
4754              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4755            break;
4756          }
4757        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
4758      }
4759      case 'e':
4760      {
4761        if (LocaleCompare("edge",option+1) == 0)
4762          {
4763            if (*option == '+')
4764              break;
4765            i++;
4766            if (i == (ssize_t) argc)
4767              ThrowMogrifyException(OptionError,"MissingArgument",option);
4768            if (IsGeometry(argv[i]) == MagickFalse)
4769              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4770            break;
4771          }
4772        if (LocaleCompare("emboss",option+1) == 0)
4773          {
4774            if (*option == '+')
4775              break;
4776            i++;
4777            if (i == (ssize_t) argc)
4778              ThrowMogrifyException(OptionError,"MissingArgument",option);
4779            if (IsGeometry(argv[i]) == MagickFalse)
4780              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4781            break;
4782          }
4783        if (LocaleCompare("encipher",option+1) == 0)
4784          {
4785            if (*option == '+')
4786              break;
4787            i++;
4788            if (i == (ssize_t) argc)
4789              ThrowMogrifyException(OptionError,"MissingArgument",option);
4790            break;
4791          }
4792        if (LocaleCompare("encoding",option+1) == 0)
4793          {
4794            if (*option == '+')
4795              break;
4796            i++;
4797            if (i == (ssize_t) argc)
4798              ThrowMogrifyException(OptionError,"MissingArgument",option);
4799            break;
4800          }
4801        if (LocaleCompare("endian",option+1) == 0)
4802          {
4803            ssize_t
4804              endian;
4805
4806            if (*option == '+')
4807              break;
4808            i++;
4809            if (i == (ssize_t) argc)
4810              ThrowMogrifyException(OptionError,"MissingArgument",option);
4811            endian=ParseCommandOption(MagickEndianOptions,MagickFalse,argv[i]);
4812            if (endian < 0)
4813              ThrowMogrifyException(OptionError,"UnrecognizedEndianType",
4814                argv[i]);
4815            break;
4816          }
4817        if (LocaleCompare("enhance",option+1) == 0)
4818          break;
4819        if (LocaleCompare("equalize",option+1) == 0)
4820          break;
4821        if (LocaleCompare("evaluate",option+1) == 0)
4822          {
4823            ssize_t
4824              op;
4825
4826            if (*option == '+')
4827              break;
4828            i++;
4829            if (i == (ssize_t) argc)
4830              ThrowMogrifyException(OptionError,"MissingArgument",option);
4831            op=ParseCommandOption(MagickEvaluateOptions,MagickFalse,argv[i]);
4832            if (op < 0)
4833              ThrowMogrifyException(OptionError,"UnrecognizedEvaluateOperator",
4834                argv[i]);
4835            i++;
4836            if (i == (ssize_t) argc)
4837              ThrowMogrifyException(OptionError,"MissingArgument",option);
4838            if (IsGeometry(argv[i]) == MagickFalse)
4839              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4840            break;
4841          }
4842        if (LocaleCompare("evaluate-sequence",option+1) == 0)
4843          {
4844            ssize_t
4845              op;
4846
4847            if (*option == '+')
4848              break;
4849            i++;
4850            if (i == (ssize_t) argc)
4851              ThrowMogrifyException(OptionError,"MissingArgument",option);
4852            op=ParseCommandOption(MagickEvaluateOptions,MagickFalse,argv[i]);
4853            if (op < 0)
4854              ThrowMogrifyException(OptionError,"UnrecognizedEvaluateOperator",
4855                argv[i]);
4856            break;
4857          }
4858        if (LocaleCompare("extent",option+1) == 0)
4859          {
4860            if (*option == '+')
4861              break;
4862            i++;
4863            if (i == (ssize_t) argc)
4864              ThrowMogrifyException(OptionError,"MissingArgument",option);
4865            if (IsGeometry(argv[i]) == MagickFalse)
4866              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4867            break;
4868          }
4869        if (LocaleCompare("extract",option+1) == 0)
4870          {
4871            if (*option == '+')
4872              break;
4873            i++;
4874            if (i == (ssize_t) argc)
4875              ThrowMogrifyException(OptionError,"MissingArgument",option);
4876            if (IsGeometry(argv[i]) == MagickFalse)
4877              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4878            break;
4879          }
4880        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
4881      }
4882      case 'f':
4883      {
4884        if (LocaleCompare("family",option+1) == 0)
4885          {
4886            if (*option == '+')
4887              break;
4888            i++;
4889            if (i == (ssize_t) argc)
4890              ThrowMogrifyException(OptionError,"MissingArgument",option);
4891            break;
4892          }
4893        if (LocaleCompare("features",option+1) == 0)
4894          {
4895            if (*option == '+')
4896              break;
4897            i++;
4898            if (i == (ssize_t) argc)
4899              ThrowMogrifyException(OptionError,"MissingArgument",option);
4900            if (IsGeometry(argv[i]) == MagickFalse)
4901              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4902            break;
4903          }
4904        if (LocaleCompare("fill",option+1) == 0)
4905          {
4906            if (*option == '+')
4907              break;
4908            i++;
4909            if (i == (ssize_t) argc)
4910              ThrowMogrifyException(OptionError,"MissingArgument",option);
4911            break;
4912          }
4913        if (LocaleCompare("filter",option+1) == 0)
4914          {
4915            ssize_t
4916              filter;
4917
4918            if (*option == '+')
4919              break;
4920            i++;
4921            if (i == (ssize_t) argc)
4922              ThrowMogrifyException(OptionError,"MissingArgument",option);
4923            filter=ParseCommandOption(MagickFilterOptions,MagickFalse,argv[i]);
4924            if (filter < 0)
4925              ThrowMogrifyException(OptionError,"UnrecognizedImageFilter",
4926                argv[i]);
4927            break;
4928          }
4929        if (LocaleCompare("flatten",option+1) == 0)
4930          break;
4931        if (LocaleCompare("flip",option+1) == 0)
4932          break;
4933        if (LocaleCompare("flop",option+1) == 0)
4934          break;
4935        if (LocaleCompare("floodfill",option+1) == 0)
4936          {
4937            if (*option == '+')
4938              break;
4939            i++;
4940            if (i == (ssize_t) argc)
4941              ThrowMogrifyException(OptionError,"MissingArgument",option);
4942            if (IsGeometry(argv[i]) == MagickFalse)
4943              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4944            i++;
4945            if (i == (ssize_t) argc)
4946              ThrowMogrifyException(OptionError,"MissingArgument",option);
4947            break;
4948          }
4949        if (LocaleCompare("font",option+1) == 0)
4950          {
4951            if (*option == '+')
4952              break;
4953            i++;
4954            if (i == (ssize_t) argc)
4955              ThrowMogrifyException(OptionError,"MissingArgument",option);
4956            break;
4957          }
4958        if (LocaleCompare("format",option+1) == 0)
4959          {
4960            (void) CopyMagickString(argv[i]+1,"sans",MagickPathExtent);
4961            (void) CloneString(&format,(char *) NULL);
4962            if (*option == '+')
4963              break;
4964            i++;
4965            if (i == (ssize_t) argc)
4966              ThrowMogrifyException(OptionError,"MissingArgument",option);
4967            (void) CloneString(&format,argv[i]);
4968            (void) CopyMagickString(image_info->filename,format,
4969              MagickPathExtent);
4970            (void) ConcatenateMagickString(image_info->filename,":",
4971              MagickPathExtent);
4972            (void) SetImageInfo(image_info,0,exception);
4973            if (*image_info->magick == '\0')
4974              ThrowMogrifyException(OptionError,"UnrecognizedImageFormat",
4975                format);
4976            break;
4977          }
4978        if (LocaleCompare("frame",option+1) == 0)
4979          {
4980            if (*option == '+')
4981              break;
4982            i++;
4983            if (i == (ssize_t) argc)
4984              ThrowMogrifyException(OptionError,"MissingArgument",option);
4985            if (IsGeometry(argv[i]) == MagickFalse)
4986              ThrowMogrifyInvalidArgumentException(option,argv[i]);
4987            break;
4988          }
4989        if (LocaleCompare("function",option+1) == 0)
4990          {
4991            ssize_t
4992              op;
4993
4994            if (*option == '+')
4995              break;
4996            i++;
4997            if (i == (ssize_t) argc)
4998              ThrowMogrifyException(OptionError,"MissingArgument",option);
4999            op=ParseCommandOption(MagickFunctionOptions,MagickFalse,argv[i]);
5000            if (op < 0)
5001              ThrowMogrifyException(OptionError,"UnrecognizedFunction",argv[i]);
5002             i++;
5003             if (i == (ssize_t) argc)
5004               ThrowMogrifyException(OptionError,"MissingArgument",option);
5005            break;
5006          }
5007        if (LocaleCompare("fuzz",option+1) == 0)
5008          {
5009            if (*option == '+')
5010              break;
5011            i++;
5012            if (i == (ssize_t) argc)
5013              ThrowMogrifyException(OptionError,"MissingArgument",option);
5014            if (IsGeometry(argv[i]) == MagickFalse)
5015              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5016            break;
5017          }
5018        if (LocaleCompare("fx",option+1) == 0)
5019          {
5020            if (*option == '+')
5021              break;
5022            i++;
5023            if (i == (ssize_t) argc)
5024              ThrowMogrifyException(OptionError,"MissingArgument",option);
5025            break;
5026          }
5027        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5028      }
5029      case 'g':
5030      {
5031        if (LocaleCompare("gamma",option+1) == 0)
5032          {
5033            i++;
5034            if (i == (ssize_t) argc)
5035              ThrowMogrifyException(OptionError,"MissingArgument",option);
5036            if (IsGeometry(argv[i]) == MagickFalse)
5037              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5038            break;
5039          }
5040        if ((LocaleCompare("gaussian-blur",option+1) == 0) ||
5041            (LocaleCompare("gaussian",option+1) == 0))
5042          {
5043            i++;
5044            if (i == (ssize_t) argc)
5045              ThrowMogrifyException(OptionError,"MissingArgument",option);
5046            if (IsGeometry(argv[i]) == MagickFalse)
5047              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5048            break;
5049          }
5050        if (LocaleCompare("geometry",option+1) == 0)
5051          {
5052            if (*option == '+')
5053              break;
5054            i++;
5055            if (i == (ssize_t) argc)
5056              ThrowMogrifyException(OptionError,"MissingArgument",option);
5057            if (IsGeometry(argv[i]) == MagickFalse)
5058              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5059            break;
5060          }
5061        if (LocaleCompare("gravity",option+1) == 0)
5062          {
5063            ssize_t
5064              gravity;
5065
5066            if (*option == '+')
5067              break;
5068            i++;
5069            if (i == (ssize_t) argc)
5070              ThrowMogrifyException(OptionError,"MissingArgument",option);
5071            gravity=ParseCommandOption(MagickGravityOptions,MagickFalse,
5072              argv[i]);
5073            if (gravity < 0)
5074              ThrowMogrifyException(OptionError,"UnrecognizedGravityType",
5075                argv[i]);
5076            break;
5077          }
5078        if (LocaleCompare("grayscale",option+1) == 0)
5079          {
5080            ssize_t
5081              method;
5082
5083            if (*option == '+')
5084              break;
5085            i++;
5086            if (i == (ssize_t) argc)
5087              ThrowMogrifyException(OptionError,"MissingArgument",option);
5088            method=ParseCommandOption(MagickPixelIntensityOptions,MagickFalse,
5089              argv[i]);
5090            if (method < 0)
5091              ThrowMogrifyException(OptionError,"UnrecognizedIntensityMethod",
5092                argv[i]);
5093            break;
5094          }
5095        if (LocaleCompare("green-primary",option+1) == 0)
5096          {
5097            if (*option == '+')
5098              break;
5099            i++;
5100            if (i == (ssize_t) argc)
5101              ThrowMogrifyException(OptionError,"MissingArgument",option);
5102            if (IsGeometry(argv[i]) == MagickFalse)
5103              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5104            break;
5105          }
5106        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5107      }
5108      case 'h':
5109      {
5110        if (LocaleCompare("hald-clut",option+1) == 0)
5111          break;
5112        if ((LocaleCompare("help",option+1) == 0) ||
5113            (LocaleCompare("-help",option+1) == 0))
5114          return(MogrifyUsage());
5115        if (LocaleCompare("hough-lines",option+1) == 0)
5116          {
5117            if (*option == '+')
5118              break;
5119            i++;
5120            if (i == (ssize_t) argc)
5121              ThrowMogrifyException(OptionError,"MissingArgument",option);
5122            if (IsGeometry(argv[i]) == MagickFalse)
5123              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5124            break;
5125          }
5126        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5127      }
5128      case 'i':
5129      {
5130        if (LocaleCompare("identify",option+1) == 0)
5131          break;
5132        if (LocaleCompare("idft",option+1) == 0)
5133          break;
5134        if (LocaleCompare("implode",option+1) == 0)
5135          {
5136            if (*option == '+')
5137              break;
5138            i++;
5139            if (i == (ssize_t) argc)
5140              ThrowMogrifyException(OptionError,"MissingArgument",option);
5141            if (IsGeometry(argv[i]) == MagickFalse)
5142              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5143            break;
5144          }
5145        if (LocaleCompare("intensity",option+1) == 0)
5146          {
5147            ssize_t
5148              intensity;
5149
5150            if (*option == '+')
5151              break;
5152            i++;
5153            if (i == (ssize_t) argc)
5154              ThrowMogrifyException(OptionError,"MissingArgument",option);
5155            intensity=ParseCommandOption(MagickPixelIntensityOptions,
5156              MagickFalse,argv[i]);
5157            if (intensity < 0)
5158              ThrowMogrifyException(OptionError,
5159                "UnrecognizedPixelIntensityMethod",argv[i]);
5160            break;
5161          }
5162        if (LocaleCompare("intent",option+1) == 0)
5163          {
5164            ssize_t
5165              intent;
5166
5167            if (*option == '+')
5168              break;
5169            i++;
5170            if (i == (ssize_t) argc)
5171              ThrowMogrifyException(OptionError,"MissingArgument",option);
5172            intent=ParseCommandOption(MagickIntentOptions,MagickFalse,argv[i]);
5173            if (intent < 0)
5174              ThrowMogrifyException(OptionError,"UnrecognizedIntentType",
5175                argv[i]);
5176            break;
5177          }
5178        if (LocaleCompare("interlace",option+1) == 0)
5179          {
5180            ssize_t
5181              interlace;
5182
5183            if (*option == '+')
5184              break;
5185            i++;
5186            if (i == (ssize_t) argc)
5187              ThrowMogrifyException(OptionError,"MissingArgument",option);
5188            interlace=ParseCommandOption(MagickInterlaceOptions,MagickFalse,
5189              argv[i]);
5190            if (interlace < 0)
5191              ThrowMogrifyException(OptionError,"UnrecognizedInterlaceType",
5192                argv[i]);
5193            break;
5194          }
5195        if (LocaleCompare("interline-spacing",option+1) == 0)
5196          {
5197            if (*option == '+')
5198              break;
5199            i++;
5200            if (i == (ssize_t) argc)
5201              ThrowMogrifyException(OptionError,"MissingArgument",option);
5202            if (IsGeometry(argv[i]) == MagickFalse)
5203              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5204            break;
5205          }
5206        if (LocaleCompare("interpolate",option+1) == 0)
5207          {
5208            ssize_t
5209              interpolate;
5210
5211            if (*option == '+')
5212              break;
5213            i++;
5214            if (i == (ssize_t) argc)
5215              ThrowMogrifyException(OptionError,"MissingArgument",option);
5216            interpolate=ParseCommandOption(MagickInterpolateOptions,MagickFalse,
5217              argv[i]);
5218            if (interpolate < 0)
5219              ThrowMogrifyException(OptionError,"UnrecognizedInterpolateMethod",
5220                argv[i]);
5221            break;
5222          }
5223        if (LocaleCompare("interword-spacing",option+1) == 0)
5224          {
5225            if (*option == '+')
5226              break;
5227            i++;
5228            if (i == (ssize_t) argc)
5229              ThrowMogrifyException(OptionError,"MissingArgument",option);
5230            if (IsGeometry(argv[i]) == MagickFalse)
5231              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5232            break;
5233          }
5234        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5235      }
5236      case 'k':
5237      {
5238        if (LocaleCompare("kerning",option+1) == 0)
5239          {
5240            if (*option == '+')
5241              break;
5242            i++;
5243            if (i == (ssize_t) argc)
5244              ThrowMogrifyException(OptionError,"MissingArgument",option);
5245            if (IsGeometry(argv[i]) == MagickFalse)
5246              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5247            break;
5248          }
5249        if (LocaleCompare("kuwahara",option+1) == 0)
5250          {
5251            i++;
5252            if (i == (ssize_t) argc)
5253              ThrowMogrifyException(OptionError,"MissingArgument",option);
5254            if (IsGeometry(argv[i]) == MagickFalse)
5255              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5256            break;
5257          }
5258        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5259      }
5260      case 'l':
5261      {
5262        if (LocaleCompare("label",option+1) == 0)
5263          {
5264            if (*option == '+')
5265              break;
5266            i++;
5267            if (i == (ssize_t) argc)
5268              ThrowMogrifyException(OptionError,"MissingArgument",option);
5269            break;
5270          }
5271        if (LocaleCompare("lat",option+1) == 0)
5272          {
5273            if (*option == '+')
5274              break;
5275            i++;
5276            if (i == (ssize_t) argc)
5277              ThrowMogrifyException(OptionError,"MissingArgument",option);
5278            if (IsGeometry(argv[i]) == MagickFalse)
5279              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5280          }
5281        if (LocaleCompare("layers",option+1) == 0)
5282          {
5283            ssize_t
5284              type;
5285
5286            if (*option == '+')
5287              break;
5288            i++;
5289            if (i == (ssize_t) argc)
5290              ThrowMogrifyException(OptionError,"MissingArgument",option);
5291            type=ParseCommandOption(MagickLayerOptions,MagickFalse,argv[i]);
5292            if (type < 0)
5293              ThrowMogrifyException(OptionError,"UnrecognizedLayerMethod",
5294                argv[i]);
5295            break;
5296          }
5297        if (LocaleCompare("level",option+1) == 0)
5298          {
5299            i++;
5300            if (i == (ssize_t) argc)
5301              ThrowMogrifyException(OptionError,"MissingArgument",option);
5302            if (IsGeometry(argv[i]) == MagickFalse)
5303              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5304            break;
5305          }
5306        if (LocaleCompare("level-colors",option+1) == 0)
5307          {
5308            i++;
5309            if (i == (ssize_t) argc)
5310              ThrowMogrifyException(OptionError,"MissingArgument",option);
5311            break;
5312          }
5313        if (LocaleCompare("limit",option+1) == 0)
5314          {
5315            char
5316              *p;
5317
5318            double
5319              value;
5320
5321            ssize_t
5322              resource;
5323
5324            if (*option == '+')
5325              break;
5326            i++;
5327            if (i == (ssize_t) argc)
5328              ThrowMogrifyException(OptionError,"MissingArgument",option);
5329            resource=ParseCommandOption(MagickResourceOptions,MagickFalse,
5330              argv[i]);
5331            if (resource < 0)
5332              ThrowMogrifyException(OptionError,"UnrecognizedResourceType",
5333                argv[i]);
5334            i++;
5335            if (i == (ssize_t) argc)
5336              ThrowMogrifyException(OptionError,"MissingArgument",option);
5337            value=StringToDouble(argv[i],&p);
5338            (void) value;
5339            if ((p == argv[i]) && (LocaleCompare("unlimited",argv[i]) != 0))
5340              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5341            break;
5342          }
5343        if (LocaleCompare("liquid-rescale",option+1) == 0)
5344          {
5345            i++;
5346            if (i == (ssize_t) argc)
5347              ThrowMogrifyException(OptionError,"MissingArgument",option);
5348            if (IsGeometry(argv[i]) == MagickFalse)
5349              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5350            break;
5351          }
5352        if (LocaleCompare("list",option+1) == 0)
5353          {
5354            ssize_t
5355              list;
5356
5357            if (*option == '+')
5358              break;
5359            i++;
5360            if (i == (ssize_t) argc)
5361              ThrowMogrifyException(OptionError,"MissingArgument",option);
5362            list=ParseCommandOption(MagickListOptions,MagickFalse,argv[i]);
5363            if (list < 0)
5364              ThrowMogrifyException(OptionError,"UnrecognizedListType",argv[i]);
5365            status=MogrifyImageInfo(image_info,(int) (i-j+1),(const char **)
5366              argv+j,exception);
5367            return(status == 0 ? MagickTrue : MagickFalse);
5368          }
5369        if (LocaleCompare("log",option+1) == 0)
5370          {
5371            if (*option == '+')
5372              break;
5373            i++;
5374            if ((i == (ssize_t) argc) ||
5375                (strchr(argv[i],'%') == (char *) NULL))
5376              ThrowMogrifyException(OptionError,"MissingArgument",option);
5377            break;
5378          }
5379        if (LocaleCompare("loop",option+1) == 0)
5380          {
5381            if (*option == '+')
5382              break;
5383            i++;
5384            if (i == (ssize_t) argc)
5385              ThrowMogrifyException(OptionError,"MissingArgument",option);
5386            if (IsGeometry(argv[i]) == MagickFalse)
5387              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5388            break;
5389          }
5390        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5391      }
5392      case 'm':
5393      {
5394        if (LocaleCompare("map",option+1) == 0)
5395          {
5396            global_colormap=(*option == '+') ? MagickTrue : MagickFalse;
5397            if (*option == '+')
5398              break;
5399            i++;
5400            if (i == (ssize_t) argc)
5401              ThrowMogrifyException(OptionError,"MissingArgument",option);
5402            break;
5403          }
5404        if (LocaleCompare("mask",option+1) == 0)
5405          {
5406            if (*option == '+')
5407              break;
5408            i++;
5409            if (i == (ssize_t) argc)
5410              ThrowMogrifyException(OptionError,"MissingArgument",option);
5411            break;
5412          }
5413        if (LocaleCompare("matte",option+1) == 0)
5414          break;
5415        if (LocaleCompare("maximum",option+1) == 0)
5416          break;
5417        if (LocaleCompare("mean-shift",option+1) == 0)
5418          {
5419            if (*option == '+')
5420              break;
5421            i++;
5422            if (i == (ssize_t) argc)
5423              ThrowMogrifyException(OptionError,"MissingArgument",option);
5424            if (IsGeometry(argv[i]) == MagickFalse)
5425              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5426            break;
5427          }
5428        if (LocaleCompare("median",option+1) == 0)
5429          {
5430            if (*option == '+')
5431              break;
5432            i++;
5433            if (i == (ssize_t) argc)
5434              ThrowMogrifyException(OptionError,"MissingArgument",option);
5435            if (IsGeometry(argv[i]) == MagickFalse)
5436              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5437            break;
5438          }
5439        if (LocaleCompare("metric",option+1) == 0)
5440          {
5441            ssize_t
5442              type;
5443
5444            if (*option == '+')
5445              break;
5446            i++;
5447            if (i == (ssize_t) argc)
5448              ThrowMogrifyException(OptionError,"MissingArgument",option);
5449            type=ParseCommandOption(MagickMetricOptions,MagickTrue,argv[i]);
5450            if (type < 0)
5451              ThrowMogrifyException(OptionError,"UnrecognizedMetricType",
5452                argv[i]);
5453            break;
5454          }
5455        if (LocaleCompare("minimum",option+1) == 0)
5456          break;
5457        if (LocaleCompare("modulate",option+1) == 0)
5458          {
5459            if (*option == '+')
5460              break;
5461            i++;
5462            if (i == (ssize_t) argc)
5463              ThrowMogrifyException(OptionError,"MissingArgument",option);
5464            if (IsGeometry(argv[i]) == MagickFalse)
5465              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5466            break;
5467          }
5468        if (LocaleCompare("mode",option+1) == 0)
5469          {
5470            if (*option == '+')
5471              break;
5472            i++;
5473            if (i == (ssize_t) argc)
5474              ThrowMogrifyException(OptionError,"MissingArgument",option);
5475            if (IsGeometry(argv[i]) == MagickFalse)
5476              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5477            break;
5478          }
5479        if (LocaleCompare("monitor",option+1) == 0)
5480          break;
5481        if (LocaleCompare("monochrome",option+1) == 0)
5482          break;
5483        if (LocaleCompare("morph",option+1) == 0)
5484          {
5485            if (*option == '+')
5486              break;
5487            i++;
5488            if (i == (ssize_t) argc)
5489              ThrowMogrifyException(OptionError,"MissingArgument",option);
5490            if (IsGeometry(argv[i]) == MagickFalse)
5491              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5492            break;
5493          }
5494        if (LocaleCompare("morphology",option+1) == 0)
5495          {
5496            char
5497              token[MagickPathExtent];
5498
5499            KernelInfo
5500              *kernel_info;
5501
5502            ssize_t
5503              op;
5504
5505            i++;
5506            if (i == (ssize_t) argc)
5507              ThrowMogrifyException(OptionError,"MissingArgument",option);
5508            GetNextToken(argv[i],(const char **) NULL,MagickPathExtent,token);
5509            op=ParseCommandOption(MagickMorphologyOptions,MagickFalse,token);
5510            if (op < 0)
5511              ThrowMogrifyException(OptionError,"UnrecognizedMorphologyMethod",
5512                token);
5513            i++;
5514            if (i == (ssize_t) argc)
5515              ThrowMogrifyException(OptionError,"MissingArgument",option);
5516            kernel_info=AcquireKernelInfo(argv[i],exception);
5517            if (kernel_info == (KernelInfo *) NULL)
5518              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5519            kernel_info=DestroyKernelInfo(kernel_info);
5520            break;
5521          }
5522        if (LocaleCompare("mosaic",option+1) == 0)
5523          break;
5524        if (LocaleCompare("motion-blur",option+1) == 0)
5525          {
5526            if (*option == '+')
5527              break;
5528            i++;
5529            if (i == (ssize_t) argc)
5530              ThrowMogrifyException(OptionError,"MissingArgument",option);
5531            if (IsGeometry(argv[i]) == MagickFalse)
5532              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5533            break;
5534          }
5535        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5536      }
5537      case 'n':
5538      {
5539        if (LocaleCompare("negate",option+1) == 0)
5540          break;
5541        if (LocaleCompare("noise",option+1) == 0)
5542          {
5543            i++;
5544            if (i == (ssize_t) argc)
5545              ThrowMogrifyException(OptionError,"MissingArgument",option);
5546            if (*option == '+')
5547              {
5548                ssize_t
5549                  noise;
5550
5551                noise=ParseCommandOption(MagickNoiseOptions,MagickFalse,
5552                  argv[i]);
5553                if (noise < 0)
5554                  ThrowMogrifyException(OptionError,"UnrecognizedNoiseType",
5555                    argv[i]);
5556                break;
5557              }
5558            if (IsGeometry(argv[i]) == MagickFalse)
5559              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5560            break;
5561          }
5562        if (LocaleCompare("noop",option+1) == 0)
5563          break;
5564        if (LocaleCompare("normalize",option+1) == 0)
5565          break;
5566        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5567      }
5568      case 'o':
5569      {
5570        if (LocaleCompare("opaque",option+1) == 0)
5571          {
5572            i++;
5573            if (i == (ssize_t) argc)
5574              ThrowMogrifyException(OptionError,"MissingArgument",option);
5575            break;
5576          }
5577        if (LocaleCompare("ordered-dither",option+1) == 0)
5578          {
5579            if (*option == '+')
5580              break;
5581            i++;
5582            if (i == (ssize_t) argc)
5583              ThrowMogrifyException(OptionError,"MissingArgument",option);
5584            break;
5585          }
5586        if (LocaleCompare("orient",option+1) == 0)
5587          {
5588            ssize_t
5589              orientation;
5590
5591            orientation=UndefinedOrientation;
5592            if (*option == '+')
5593              break;
5594            i++;
5595            if (i == (ssize_t) argc)
5596              ThrowMogrifyException(OptionError,"MissingArgument",option);
5597            orientation=ParseCommandOption(MagickOrientationOptions,MagickFalse,
5598              argv[i]);
5599            if (orientation < 0)
5600              ThrowMogrifyException(OptionError,"UnrecognizedImageOrientation",
5601                argv[i]);
5602            break;
5603          }
5604        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5605      }
5606      case 'p':
5607      {
5608        if (LocaleCompare("page",option+1) == 0)
5609          {
5610            if (*option == '+')
5611              break;
5612            i++;
5613            if (i == (ssize_t) argc)
5614              ThrowMogrifyException(OptionError,"MissingArgument",option);
5615            break;
5616          }
5617        if (LocaleCompare("paint",option+1) == 0)
5618          {
5619            if (*option == '+')
5620              break;
5621            i++;
5622            if (i == (ssize_t) argc)
5623              ThrowMogrifyException(OptionError,"MissingArgument",option);
5624            if (IsGeometry(argv[i]) == MagickFalse)
5625              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5626            break;
5627          }
5628        if (LocaleCompare("path",option+1) == 0)
5629          {
5630            (void) CloneString(&path,(char *) NULL);
5631            if (*option == '+')
5632              break;
5633            i++;
5634            if (i == (ssize_t) argc)
5635              ThrowMogrifyException(OptionError,"MissingArgument",option);
5636            (void) CloneString(&path,argv[i]);
5637            break;
5638          }
5639        if (LocaleCompare("perceptible",option+1) == 0)
5640          {
5641            if (*option == '+')
5642              break;
5643            i++;
5644            if (i == (ssize_t) argc)
5645              ThrowMogrifyException(OptionError,"MissingArgument",option);
5646            if (IsGeometry(argv[i]) == MagickFalse)
5647              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5648            break;
5649          }
5650        if (LocaleCompare("pointsize",option+1) == 0)
5651          {
5652            if (*option == '+')
5653              break;
5654            i++;
5655            if (i == (ssize_t) argc)
5656              ThrowMogrifyException(OptionError,"MissingArgument",option);
5657            if (IsGeometry(argv[i]) == MagickFalse)
5658              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5659            break;
5660          }
5661        if (LocaleCompare("polaroid",option+1) == 0)
5662          {
5663            if (*option == '+')
5664              break;
5665            i++;
5666            if (i == (ssize_t) argc)
5667              ThrowMogrifyException(OptionError,"MissingArgument",option);
5668            if (IsGeometry(argv[i]) == MagickFalse)
5669              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5670            break;
5671          }
5672        if (LocaleCompare("poly",option+1) == 0)
5673          {
5674            if (*option == '+')
5675              break;
5676            i++;
5677            if (i == (ssize_t) argc)
5678              ThrowMogrifyException(OptionError,"MissingArgument",option);
5679            if (IsGeometry(argv[i]) == MagickFalse)
5680              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5681            break;
5682          }
5683        if (LocaleCompare("posterize",option+1) == 0)
5684          {
5685            if (*option == '+')
5686              break;
5687            i++;
5688            if (i == (ssize_t) argc)
5689              ThrowMogrifyException(OptionError,"MissingArgument",option);
5690            if (IsGeometry(argv[i]) == MagickFalse)
5691              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5692            break;
5693          }
5694        if (LocaleCompare("precision",option+1) == 0)
5695          {
5696            if (*option == '+')
5697              break;
5698            i++;
5699            if (i == (ssize_t) argc)
5700              ThrowMogrifyException(OptionError,"MissingArgument",option);
5701            if (IsGeometry(argv[i]) == MagickFalse)
5702              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5703            break;
5704          }
5705        if (LocaleCompare("print",option+1) == 0)
5706          {
5707            if (*option == '+')
5708              break;
5709            i++;
5710            if (i == (ssize_t) argc)
5711              ThrowMogrifyException(OptionError,"MissingArgument",option);
5712            break;
5713          }
5714        if (LocaleCompare("process",option+1) == 0)
5715          {
5716            if (*option == '+')
5717              break;
5718            i++;
5719            if (i == (ssize_t) argc)
5720              ThrowMogrifyException(OptionError,"MissingArgument",option);
5721            break;
5722          }
5723        if (LocaleCompare("profile",option+1) == 0)
5724          {
5725            i++;
5726            if (i == (ssize_t) argc)
5727              ThrowMogrifyException(OptionError,"MissingArgument",option);
5728            break;
5729          }
5730        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5731      }
5732      case 'q':
5733      {
5734        if (LocaleCompare("quality",option+1) == 0)
5735          {
5736            if (*option == '+')
5737              break;
5738            i++;
5739            if (i == (ssize_t) argc)
5740              ThrowMogrifyException(OptionError,"MissingArgument",option);
5741            if (IsGeometry(argv[i]) == MagickFalse)
5742              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5743            break;
5744          }
5745        if (LocaleCompare("quantize",option+1) == 0)
5746          {
5747            ssize_t
5748              colorspace;
5749
5750            if (*option == '+')
5751              break;
5752            i++;
5753            if (i == (ssize_t) argc)
5754              ThrowMogrifyException(OptionError,"MissingArgument",option);
5755            colorspace=ParseCommandOption(MagickColorspaceOptions,MagickFalse,
5756              argv[i]);
5757            if (colorspace < 0)
5758              ThrowMogrifyException(OptionError,"UnrecognizedColorspace",
5759                argv[i]);
5760            break;
5761          }
5762        if (LocaleCompare("quiet",option+1) == 0)
5763          break;
5764        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5765      }
5766      case 'r':
5767      {
5768        if (LocaleCompare("rotational-blur",option+1) == 0)
5769          {
5770            i++;
5771            if (i == (ssize_t) argc)
5772              ThrowMogrifyException(OptionError,"MissingArgument",option);
5773            if (IsGeometry(argv[i]) == MagickFalse)
5774              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5775            break;
5776          }
5777        if (LocaleCompare("raise",option+1) == 0)
5778          {
5779            i++;
5780            if (i == (ssize_t) argc)
5781              ThrowMogrifyException(OptionError,"MissingArgument",option);
5782            if (IsGeometry(argv[i]) == MagickFalse)
5783              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5784            break;
5785          }
5786        if (LocaleCompare("random-threshold",option+1) == 0)
5787          {
5788            if (*option == '+')
5789              break;
5790            i++;
5791            if (i == (ssize_t) argc)
5792              ThrowMogrifyException(OptionError,"MissingArgument",option);
5793            if (IsGeometry(argv[i]) == MagickFalse)
5794              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5795            break;
5796          }
5797        if (LocaleCompare("read-mask",option+1) == 0)
5798          {
5799            if (*option == '+')
5800              break;
5801            i++;
5802            if (i == (ssize_t) argc)
5803              ThrowMogrifyException(OptionError,"MissingArgument",option);
5804            break;
5805          }
5806        if (LocaleCompare("red-primary",option+1) == 0)
5807          {
5808            if (*option == '+')
5809              break;
5810            i++;
5811            if (i == (ssize_t) argc)
5812              ThrowMogrifyException(OptionError,"MissingArgument",option);
5813            if (IsGeometry(argv[i]) == MagickFalse)
5814              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5815          }
5816        if (LocaleCompare("regard-warnings",option+1) == 0)
5817          break;
5818        if (LocaleCompare("region",option+1) == 0)
5819          {
5820            if (*option == '+')
5821              break;
5822            i++;
5823            if (i == (ssize_t) argc)
5824              ThrowMogrifyException(OptionError,"MissingArgument",option);
5825            if (IsGeometry(argv[i]) == MagickFalse)
5826              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5827            break;
5828          }
5829        if (LocaleCompare("remap",option+1) == 0)
5830          {
5831            if (*option == '+')
5832              break;
5833            i++;
5834            if (i == (ssize_t) argc)
5835              ThrowMogrifyException(OptionError,"MissingArgument",option);
5836            break;
5837          }
5838        if (LocaleCompare("render",option+1) == 0)
5839          break;
5840        if (LocaleCompare("repage",option+1) == 0)
5841          {
5842            if (*option == '+')
5843              break;
5844            i++;
5845            if (i == (ssize_t) argc)
5846              ThrowMogrifyException(OptionError,"MissingArgument",option);
5847            if (IsGeometry(argv[i]) == MagickFalse)
5848              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5849            break;
5850          }
5851        if (LocaleCompare("resample",option+1) == 0)
5852          {
5853            if (*option == '+')
5854              break;
5855            i++;
5856            if (i == (ssize_t) argc)
5857              ThrowMogrifyException(OptionError,"MissingArgument",option);
5858            if (IsGeometry(argv[i]) == MagickFalse)
5859              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5860            break;
5861          }
5862        if (LocaleCompare("resize",option+1) == 0)
5863          {
5864            if (*option == '+')
5865              break;
5866            i++;
5867            if (i == (ssize_t) argc)
5868              ThrowMogrifyException(OptionError,"MissingArgument",option);
5869            if (IsGeometry(argv[i]) == MagickFalse)
5870              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5871            break;
5872          }
5873        if (LocaleNCompare("respect-parentheses",option+1,17) == 0)
5874          {
5875            respect_parenthesis=(*option == '-') ? MagickTrue : MagickFalse;
5876            break;
5877          }
5878        if (LocaleCompare("reverse",option+1) == 0)
5879          break;
5880        if (LocaleCompare("roll",option+1) == 0)
5881          {
5882            if (*option == '+')
5883              break;
5884            i++;
5885            if (i == (ssize_t) argc)
5886              ThrowMogrifyException(OptionError,"MissingArgument",option);
5887            if (IsGeometry(argv[i]) == MagickFalse)
5888              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5889            break;
5890          }
5891        if (LocaleCompare("rotate",option+1) == 0)
5892          {
5893            i++;
5894            if (i == (ssize_t) argc)
5895              ThrowMogrifyException(OptionError,"MissingArgument",option);
5896            if (IsGeometry(argv[i]) == MagickFalse)
5897              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5898            break;
5899          }
5900        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
5901      }
5902      case 's':
5903      {
5904        if (LocaleCompare("sample",option+1) == 0)
5905          {
5906            if (*option == '+')
5907              break;
5908            i++;
5909            if (i == (ssize_t) argc)
5910              ThrowMogrifyException(OptionError,"MissingArgument",option);
5911            if (IsGeometry(argv[i]) == MagickFalse)
5912              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5913            break;
5914          }
5915        if (LocaleCompare("sampling-factor",option+1) == 0)
5916          {
5917            if (*option == '+')
5918              break;
5919            i++;
5920            if (i == (ssize_t) argc)
5921              ThrowMogrifyException(OptionError,"MissingArgument",option);
5922            if (IsGeometry(argv[i]) == MagickFalse)
5923              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5924            break;
5925          }
5926        if (LocaleCompare("scale",option+1) == 0)
5927          {
5928            if (*option == '+')
5929              break;
5930            i++;
5931            if (i == (ssize_t) argc)
5932              ThrowMogrifyException(OptionError,"MissingArgument",option);
5933            if (IsGeometry(argv[i]) == MagickFalse)
5934              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5935            break;
5936          }
5937        if (LocaleCompare("scene",option+1) == 0)
5938          {
5939            if (*option == '+')
5940              break;
5941            i++;
5942            if (i == (ssize_t) argc)
5943              ThrowMogrifyException(OptionError,"MissingArgument",option);
5944            if (IsGeometry(argv[i]) == MagickFalse)
5945              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5946            break;
5947          }
5948        if (LocaleCompare("seed",option+1) == 0)
5949          {
5950            if (*option == '+')
5951              break;
5952            i++;
5953            if (i == (ssize_t) argc)
5954              ThrowMogrifyException(OptionError,"MissingArgument",option);
5955            if (IsGeometry(argv[i]) == MagickFalse)
5956              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5957            break;
5958          }
5959        if (LocaleCompare("segment",option+1) == 0)
5960          {
5961            if (*option == '+')
5962              break;
5963            i++;
5964            if (i == (ssize_t) argc)
5965              ThrowMogrifyException(OptionError,"MissingArgument",option);
5966            if (IsGeometry(argv[i]) == MagickFalse)
5967              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5968            break;
5969          }
5970        if (LocaleCompare("selective-blur",option+1) == 0)
5971          {
5972            i++;
5973            if (i == (ssize_t) argc)
5974              ThrowMogrifyException(OptionError,"MissingArgument",option);
5975            if (IsGeometry(argv[i]) == MagickFalse)
5976              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5977            break;
5978          }
5979        if (LocaleCompare("separate",option+1) == 0)
5980          break;
5981        if (LocaleCompare("sepia-tone",option+1) == 0)
5982          {
5983            if (*option == '+')
5984              break;
5985            i++;
5986            if (i == (ssize_t) argc)
5987              ThrowMogrifyException(OptionError,"MissingArgument",option);
5988            if (IsGeometry(argv[i]) == MagickFalse)
5989              ThrowMogrifyInvalidArgumentException(option,argv[i]);
5990            break;
5991          }
5992        if (LocaleCompare("set",option+1) == 0)
5993          {
5994            i++;
5995            if (i == (ssize_t) argc)
5996              ThrowMogrifyException(OptionError,"MissingArgument",option);
5997            if (*option == '+')
5998              break;
5999            i++;
6000            if (i == (ssize_t) argc)
6001              ThrowMogrifyException(OptionError,"MissingArgument",option);
6002            break;
6003          }
6004        if (LocaleCompare("shade",option+1) == 0)
6005          {
6006            i++;
6007            if (i == (ssize_t) argc)
6008              ThrowMogrifyException(OptionError,"MissingArgument",option);
6009            if (IsGeometry(argv[i]) == MagickFalse)
6010              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6011            break;
6012          }
6013        if (LocaleCompare("shadow",option+1) == 0)
6014          {
6015            if (*option == '+')
6016              break;
6017            i++;
6018            if (i == (ssize_t) argc)
6019              ThrowMogrifyException(OptionError,"MissingArgument",option);
6020            if (IsGeometry(argv[i]) == MagickFalse)
6021              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6022            break;
6023          }
6024        if (LocaleCompare("sharpen",option+1) == 0)
6025          {
6026            i++;
6027            if (i == (ssize_t) argc)
6028              ThrowMogrifyException(OptionError,"MissingArgument",option);
6029            if (IsGeometry(argv[i]) == MagickFalse)
6030              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6031            break;
6032          }
6033        if (LocaleCompare("shave",option+1) == 0)
6034          {
6035            if (*option == '+')
6036              break;
6037            i++;
6038            if (i == (ssize_t) argc)
6039              ThrowMogrifyException(OptionError,"MissingArgument",option);
6040            if (IsGeometry(argv[i]) == MagickFalse)
6041              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6042            break;
6043          }
6044        if (LocaleCompare("shear",option+1) == 0)
6045          {
6046            i++;
6047            if (i == (ssize_t) argc)
6048              ThrowMogrifyException(OptionError,"MissingArgument",option);
6049            if (IsGeometry(argv[i]) == MagickFalse)
6050              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6051            break;
6052          }
6053        if (LocaleCompare("sigmoidal-contrast",option+1) == 0)
6054          {
6055            i++;
6056            if (i == (ssize_t) argc)
6057              ThrowMogrifyException(OptionError,"MissingArgument",option);
6058            if (IsGeometry(argv[i]) == MagickFalse)
6059              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6060            break;
6061          }
6062        if (LocaleCompare("size",option+1) == 0)
6063          {
6064            if (*option == '+')
6065              break;
6066            i++;
6067            if (i == (ssize_t) argc)
6068              ThrowMogrifyException(OptionError,"MissingArgument",option);
6069            if (IsGeometry(argv[i]) == MagickFalse)
6070              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6071            break;
6072          }
6073        if (LocaleCompare("sketch",option+1) == 0)
6074          {
6075            if (*option == '+')
6076              break;
6077            i++;
6078            if (i == (ssize_t) argc)
6079              ThrowMogrifyException(OptionError,"MissingArgument",option);
6080            if (IsGeometry(argv[i]) == MagickFalse)
6081              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6082            break;
6083          }
6084        if (LocaleCompare("smush",option+1) == 0)
6085          {
6086            i++;
6087            if (i == (ssize_t) argc)
6088              ThrowMogrifyException(OptionError,"MissingArgument",option);
6089            if (IsGeometry(argv[i]) == MagickFalse)
6090              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6091            i++;
6092            break;
6093          }
6094        if (LocaleCompare("solarize",option+1) == 0)
6095          {
6096            if (*option == '+')
6097              break;
6098            i++;
6099            if (i == (ssize_t) argc)
6100              ThrowMogrifyException(OptionError,"MissingArgument",option);
6101            if (IsGeometry(argv[i]) == MagickFalse)
6102              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6103            break;
6104          }
6105        if (LocaleCompare("sparse-color",option+1) == 0)
6106          {
6107            ssize_t
6108              op;
6109
6110            i++;
6111            if (i == (ssize_t) argc)
6112              ThrowMogrifyException(OptionError,"MissingArgument",option);
6113            op=ParseCommandOption(MagickSparseColorOptions,MagickFalse,argv[i]);
6114            if (op < 0)
6115              ThrowMogrifyException(OptionError,"UnrecognizedSparseColorMethod",
6116                argv[i]);
6117            i++;
6118            if (i == (ssize_t) argc)
6119              ThrowMogrifyException(OptionError,"MissingArgument",option);
6120            break;
6121          }
6122        if (LocaleCompare("splice",option+1) == 0)
6123          {
6124            if (*option == '+')
6125              break;
6126            i++;
6127            if (i == (ssize_t) argc)
6128              ThrowMogrifyException(OptionError,"MissingArgument",option);
6129            if (IsGeometry(argv[i]) == MagickFalse)
6130              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6131            break;
6132          }
6133        if (LocaleCompare("spread",option+1) == 0)
6134          {
6135            if (*option == '+')
6136              break;
6137            i++;
6138            if (i == (ssize_t) argc)
6139              ThrowMogrifyException(OptionError,"MissingArgument",option);
6140            if (IsGeometry(argv[i]) == MagickFalse)
6141              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6142            break;
6143          }
6144        if (LocaleCompare("statistic",option+1) == 0)
6145          {
6146            ssize_t
6147              op;
6148
6149            if (*option == '+')
6150              break;
6151            i++;
6152            if (i == (ssize_t) argc)
6153              ThrowMogrifyException(OptionError,"MissingArgument",option);
6154            op=ParseCommandOption(MagickStatisticOptions,MagickFalse,argv[i]);
6155            if (op < 0)
6156              ThrowMogrifyException(OptionError,"UnrecognizedStatisticType",
6157                argv[i]);
6158            i++;
6159            if (i == (ssize_t) argc)
6160              ThrowMogrifyException(OptionError,"MissingArgument",option);
6161            if (IsGeometry(argv[i]) == MagickFalse)
6162              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6163            break;
6164          }
6165        if (LocaleCompare("stretch",option+1) == 0)
6166          {
6167            ssize_t
6168              stretch;
6169
6170            if (*option == '+')
6171              break;
6172            i++;
6173            if (i == (ssize_t) argc)
6174              ThrowMogrifyException(OptionError,"MissingArgument",option);
6175            stretch=ParseCommandOption(MagickStretchOptions,MagickFalse,
6176              argv[i]);
6177            if (stretch < 0)
6178              ThrowMogrifyException(OptionError,"UnrecognizedStyleType",
6179                argv[i]);
6180            break;
6181          }
6182        if (LocaleCompare("strip",option+1) == 0)
6183          break;
6184        if (LocaleCompare("stroke",option+1) == 0)
6185          {
6186            if (*option == '+')
6187              break;
6188            i++;
6189            if (i == (ssize_t) argc)
6190              ThrowMogrifyException(OptionError,"MissingArgument",option);
6191            break;
6192          }
6193        if (LocaleCompare("strokewidth",option+1) == 0)
6194          {
6195            if (*option == '+')
6196              break;
6197            i++;
6198            if (i == (ssize_t) argc)
6199              ThrowMogrifyException(OptionError,"MissingArgument",option);
6200            if (IsGeometry(argv[i]) == MagickFalse)
6201              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6202            break;
6203          }
6204        if (LocaleCompare("style",option+1) == 0)
6205          {
6206            ssize_t
6207              style;
6208
6209            if (*option == '+')
6210              break;
6211            i++;
6212            if (i == (ssize_t) argc)
6213              ThrowMogrifyException(OptionError,"MissingArgument",option);
6214            style=ParseCommandOption(MagickStyleOptions,MagickFalse,argv[i]);
6215            if (style < 0)
6216              ThrowMogrifyException(OptionError,"UnrecognizedStyleType",
6217                argv[i]);
6218            break;
6219          }
6220        if (LocaleCompare("swap",option+1) == 0)
6221          {
6222            if (*option == '+')
6223              break;
6224            i++;
6225            if (i == (ssize_t) argc)
6226              ThrowMogrifyException(OptionError,"MissingArgument",option);
6227            if (IsGeometry(argv[i]) == MagickFalse)
6228              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6229            break;
6230          }
6231        if (LocaleCompare("swirl",option+1) == 0)
6232          {
6233            if (*option == '+')
6234              break;
6235            i++;
6236            if (i == (ssize_t) argc)
6237              ThrowMogrifyException(OptionError,"MissingArgument",option);
6238            if (IsGeometry(argv[i]) == MagickFalse)
6239              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6240            break;
6241          }
6242        if (LocaleCompare("synchronize",option+1) == 0)
6243          break;
6244        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
6245      }
6246      case 't':
6247      {
6248        if (LocaleCompare("taint",option+1) == 0)
6249          break;
6250        if (LocaleCompare("texture",option+1) == 0)
6251          {
6252            if (*option == '+')
6253              break;
6254            i++;
6255            if (i == (ssize_t) argc)
6256              ThrowMogrifyException(OptionError,"MissingArgument",option);
6257            break;
6258          }
6259        if (LocaleCompare("tile",option+1) == 0)
6260          {
6261            if (*option == '+')
6262              break;
6263            i++;
6264            if (i == (ssize_t) argc)
6265              ThrowMogrifyException(OptionError,"MissingArgument",option);
6266            break;
6267          }
6268        if (LocaleCompare("tile-offset",option+1) == 0)
6269          {
6270            if (*option == '+')
6271              break;
6272            i++;
6273            if (i == (ssize_t) argc)
6274              ThrowMogrifyException(OptionError,"MissingArgument",option);
6275            if (IsGeometry(argv[i]) == MagickFalse)
6276              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6277            break;
6278          }
6279        if (LocaleCompare("tint",option+1) == 0)
6280          {
6281            if (*option == '+')
6282              break;
6283            i++;
6284            if (i == (ssize_t) argc)
6285              ThrowMogrifyException(OptionError,"MissingArgument",option);
6286            if (IsGeometry(argv[i]) == MagickFalse)
6287              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6288            break;
6289          }
6290        if (LocaleCompare("transform",option+1) == 0)
6291          break;
6292        if (LocaleCompare("transpose",option+1) == 0)
6293          break;
6294        if (LocaleCompare("transverse",option+1) == 0)
6295          break;
6296        if (LocaleCompare("threshold",option+1) == 0)
6297          {
6298            if (*option == '+')
6299              break;
6300            i++;
6301            if (i == (ssize_t) argc)
6302              ThrowMogrifyException(OptionError,"MissingArgument",option);
6303            if (IsGeometry(argv[i]) == MagickFalse)
6304              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6305            break;
6306          }
6307        if (LocaleCompare("thumbnail",option+1) == 0)
6308          {
6309            if (*option == '+')
6310              break;
6311            i++;
6312            if (i == (ssize_t) argc)
6313              ThrowMogrifyException(OptionError,"MissingArgument",option);
6314            if (IsGeometry(argv[i]) == MagickFalse)
6315              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6316            break;
6317          }
6318        if (LocaleCompare("transparent",option+1) == 0)
6319          {
6320            i++;
6321            if (i == (ssize_t) argc)
6322              ThrowMogrifyException(OptionError,"MissingArgument",option);
6323            break;
6324          }
6325        if (LocaleCompare("transparent-color",option+1) == 0)
6326          {
6327            if (*option == '+')
6328              break;
6329            i++;
6330            if (i == (ssize_t) argc)
6331              ThrowMogrifyException(OptionError,"MissingArgument",option);
6332            break;
6333          }
6334        if (LocaleCompare("treedepth",option+1) == 0)
6335          {
6336            if (*option == '+')
6337              break;
6338            i++;
6339            if (i == (ssize_t) argc)
6340              ThrowMogrifyException(OptionError,"MissingArgument",option);
6341            if (IsGeometry(argv[i]) == MagickFalse)
6342              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6343            break;
6344          }
6345        if (LocaleCompare("trim",option+1) == 0)
6346          break;
6347        if (LocaleCompare("type",option+1) == 0)
6348          {
6349            ssize_t
6350              type;
6351
6352            if (*option == '+')
6353              break;
6354            i++;
6355            if (i == (ssize_t) argc)
6356              ThrowMogrifyException(OptionError,"MissingArgument",option);
6357            type=ParseCommandOption(MagickTypeOptions,MagickFalse,argv[i]);
6358            if (type < 0)
6359              ThrowMogrifyException(OptionError,"UnrecognizedImageType",
6360                argv[i]);
6361            break;
6362          }
6363        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
6364      }
6365      case 'u':
6366      {
6367        if (LocaleCompare("undercolor",option+1) == 0)
6368          {
6369            if (*option == '+')
6370              break;
6371            i++;
6372            if (i == (ssize_t) argc)
6373              ThrowMogrifyException(OptionError,"MissingArgument",option);
6374            break;
6375          }
6376        if (LocaleCompare("unique-colors",option+1) == 0)
6377          break;
6378        if (LocaleCompare("units",option+1) == 0)
6379          {
6380            ssize_t
6381              units;
6382
6383            if (*option == '+')
6384              break;
6385            i++;
6386            if (i == (ssize_t) argc)
6387              ThrowMogrifyException(OptionError,"MissingArgument",option);
6388            units=ParseCommandOption(MagickResolutionOptions,MagickFalse,
6389              argv[i]);
6390            if (units < 0)
6391              ThrowMogrifyException(OptionError,"UnrecognizedUnitsType",
6392                argv[i]);
6393            break;
6394          }
6395        if (LocaleCompare("unsharp",option+1) == 0)
6396          {
6397            i++;
6398            if (i == (ssize_t) argc)
6399              ThrowMogrifyException(OptionError,"MissingArgument",option);
6400            if (IsGeometry(argv[i]) == MagickFalse)
6401              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6402            break;
6403          }
6404        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
6405      }
6406      case 'v':
6407      {
6408        if (LocaleCompare("verbose",option+1) == 0)
6409          {
6410            image_info->verbose=(*option == '-') ? MagickTrue : MagickFalse;
6411            break;
6412          }
6413        if ((LocaleCompare("version",option+1) == 0) ||
6414            (LocaleCompare("-version",option+1) == 0))
6415          {
6416            ListMagickVersion(stdout);
6417            break;
6418          }
6419        if (LocaleCompare("vignette",option+1) == 0)
6420          {
6421            if (*option == '+')
6422              break;
6423            i++;
6424            if (i == (ssize_t) argc)
6425              ThrowMogrifyException(OptionError,"MissingArgument",option);
6426            if (IsGeometry(argv[i]) == MagickFalse)
6427              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6428            break;
6429          }
6430        if (LocaleCompare("virtual-pixel",option+1) == 0)
6431          {
6432            ssize_t
6433              method;
6434
6435            if (*option == '+')
6436              break;
6437            i++;
6438            if (i == (ssize_t) argc)
6439              ThrowMogrifyException(OptionError,"MissingArgument",option);
6440            method=ParseCommandOption(MagickVirtualPixelOptions,MagickFalse,
6441              argv[i]);
6442            if (method < 0)
6443              ThrowMogrifyException(OptionError,
6444                "UnrecognizedVirtualPixelMethod",argv[i]);
6445            break;
6446          }
6447        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
6448      }
6449      case 'w':
6450      {
6451        if (LocaleCompare("wave",option+1) == 0)
6452          {
6453            i++;
6454            if (i == (ssize_t) argc)
6455              ThrowMogrifyException(OptionError,"MissingArgument",option);
6456            if (IsGeometry(argv[i]) == MagickFalse)
6457              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6458            break;
6459          }
6460        if (LocaleCompare("wavelet-denoise",option+1) == 0)
6461          {
6462            i++;
6463            if (i == (ssize_t) argc)
6464              ThrowMogrifyException(OptionError,"MissingArgument",option);
6465            if (IsGeometry(argv[i]) == MagickFalse)
6466              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6467            break;
6468          }
6469        if (LocaleCompare("weight",option+1) == 0)
6470          {
6471            if (*option == '+')
6472              break;
6473            i++;
6474            if (i == (ssize_t) argc)
6475              ThrowMogrifyException(OptionError,"MissingArgument",option);
6476            break;
6477          }
6478        if (LocaleCompare("white-point",option+1) == 0)
6479          {
6480            if (*option == '+')
6481              break;
6482            i++;
6483            if (i == (ssize_t) argc)
6484              ThrowMogrifyException(OptionError,"MissingArgument",option);
6485            if (IsGeometry(argv[i]) == MagickFalse)
6486              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6487            break;
6488          }
6489        if (LocaleCompare("white-threshold",option+1) == 0)
6490          {
6491            if (*option == '+')
6492              break;
6493            i++;
6494            if (i == (ssize_t) argc)
6495              ThrowMogrifyException(OptionError,"MissingArgument",option);
6496            if (IsGeometry(argv[i]) == MagickFalse)
6497              ThrowMogrifyInvalidArgumentException(option,argv[i]);
6498            break;
6499          }
6500        if (LocaleCompare("write",option+1) == 0)
6501          {
6502            i++;
6503            if (i == (ssize_t) argc)
6504              ThrowMogrifyException(OptionError,"MissingArgument",option);
6505            break;
6506          }
6507        if (LocaleCompare("write-mask",option+1) == 0)
6508          {
6509            if (*option == '+')
6510              break;
6511            i++;
6512            if (i == (ssize_t) argc)
6513              ThrowMogrifyException(OptionError,"MissingArgument",option);
6514            break;
6515          }
6516        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
6517      }
6518      case '?':
6519        break;
6520      default:
6521        ThrowMogrifyException(OptionError,"UnrecognizedOption",option)
6522    }
6523    fire=(GetCommandOptionFlags(MagickCommandOptions,MagickFalse,option) &
6524      FireOptionFlag) == 0 ?  MagickFalse : MagickTrue;
6525    if (fire != MagickFalse)
6526      FireImageStack(MagickFalse,MagickTrue,MagickTrue);
6527  }
6528  if (k != 0)
6529    ThrowMogrifyException(OptionError,"UnbalancedParenthesis",argv[i]);
6530  if (i != (ssize_t) argc)
6531    ThrowMogrifyException(OptionError,"MissingAnImageFilename",argv[i]);
6532  DestroyMogrify();
6533  return(status != 0 ? MagickTrue : MagickFalse);
6534}
6535
6536/*
6537%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6538%                                                                             %
6539%                                                                             %
6540%                                                                             %
6541+     M o g r i f y I m a g e I n f o                                         %
6542%                                                                             %
6543%                                                                             %
6544%                                                                             %
6545%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6546%
6547%  MogrifyImageInfo() applies image processing settings to the image as
6548%  prescribed by command line options.
6549%
6550%  The format of the MogrifyImageInfo method is:
6551%
6552%      MagickBooleanType MogrifyImageInfo(ImageInfo *image_info,const int argc,
6553%        const char **argv,ExceptionInfo *exception)
6554%
6555%  A description of each parameter follows:
6556%
6557%    o image_info: the image info..
6558%
6559%    o argc: Specifies a pointer to an integer describing the number of
6560%      elements in the argument vector.
6561%
6562%    o argv: Specifies a pointer to a text array containing the command line
6563%      arguments.
6564%
6565%    o exception: return any errors or warnings in this structure.
6566%
6567*/
6568WandExport MagickBooleanType MogrifyImageInfo(ImageInfo *image_info,
6569  const int argc,const char **argv,ExceptionInfo *exception)
6570{
6571  const char
6572    *option;
6573
6574  GeometryInfo
6575    geometry_info;
6576
6577  ssize_t
6578    count;
6579
6580  register ssize_t
6581    i;
6582
6583  /*
6584    Initialize method variables.
6585  */
6586  assert(image_info != (ImageInfo *) NULL);
6587  assert(image_info->signature == MagickCoreSignature);
6588  if (image_info->debug != MagickFalse)
6589    (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
6590      image_info->filename);
6591  if (argc < 0)
6592    return(MagickTrue);
6593  /*
6594    Set the image settings.
6595  */
6596  for (i=0; i < (ssize_t) argc; i++)
6597  {
6598    option=argv[i];
6599    if (IsCommandOption(option) == MagickFalse)
6600      continue;
6601    count=ParseCommandOption(MagickCommandOptions,MagickFalse,option);
6602    count=MagickMax(count,0L);
6603    if ((i+count) >= (ssize_t) argc)
6604      break;
6605    switch (*(option+1))
6606    {
6607      case 'a':
6608      {
6609        if (LocaleCompare("adjoin",option+1) == 0)
6610          {
6611            image_info->adjoin=(*option == '-') ? MagickTrue : MagickFalse;
6612            break;
6613          }
6614        if (LocaleCompare("alpha-color",option+1) == 0)
6615          {
6616            if (*option == '+')
6617              {
6618                (void) SetImageOption(image_info,option+1,argv[i+1]);
6619                (void) QueryColorCompliance(MogrifyAlphaColor,AllCompliance,
6620                  &image_info->alpha_color,exception);
6621                break;
6622              }
6623            (void) SetImageOption(image_info,option+1,argv[i+1]);
6624            (void) QueryColorCompliance(argv[i+1],AllCompliance,
6625              &image_info->alpha_color,exception);
6626            break;
6627          }
6628        if (LocaleCompare("antialias",option+1) == 0)
6629          {
6630            image_info->antialias=(*option == '-') ? MagickTrue : MagickFalse;
6631            break;
6632          }
6633        if (LocaleCompare("authenticate",option+1) == 0)
6634          {
6635            if (*option == '+')
6636              (void) DeleteImageOption(image_info,option+1);
6637            else
6638              (void) SetImageOption(image_info,option+1,argv[i+1]);
6639            break;
6640          }
6641        break;
6642      }
6643      case 'b':
6644      {
6645        if (LocaleCompare("background",option+1) == 0)
6646          {
6647            if (*option == '+')
6648              {
6649                (void) DeleteImageOption(image_info,option+1);
6650                (void) QueryColorCompliance(MogrifyBackgroundColor,
6651                  AllCompliance,&image_info->background_color,exception);
6652                break;
6653              }
6654            (void) SetImageOption(image_info,option+1,argv[i+1]);
6655            (void) QueryColorCompliance(argv[i+1],AllCompliance,
6656              &image_info->background_color,exception);
6657            break;
6658          }
6659        if (LocaleCompare("bias",option+1) == 0)
6660          {
6661            if (*option == '+')
6662              {
6663                (void) SetImageOption(image_info,option+1,"0.0");
6664                break;
6665              }
6666            (void) SetImageOption(image_info,option+1,argv[i+1]);
6667            break;
6668          }
6669        if (LocaleCompare("black-point-compensation",option+1) == 0)
6670          {
6671            if (*option == '+')
6672              {
6673                (void) SetImageOption(image_info,option+1,"false");
6674                break;
6675              }
6676            (void) SetImageOption(image_info,option+1,"true");
6677            break;
6678          }
6679        if (LocaleCompare("blue-primary",option+1) == 0)
6680          {
6681            if (*option == '+')
6682              {
6683                (void) SetImageOption(image_info,option+1,"0.0");
6684                break;
6685              }
6686            (void) SetImageOption(image_info,option+1,argv[i+1]);
6687            break;
6688          }
6689        if (LocaleCompare("bordercolor",option+1) == 0)
6690          {
6691            if (*option == '+')
6692              {
6693                (void) DeleteImageOption(image_info,option+1);
6694                (void) QueryColorCompliance(MogrifyBorderColor,AllCompliance,
6695                  &image_info->border_color,exception);
6696                break;
6697              }
6698            (void) QueryColorCompliance(argv[i+1],AllCompliance,
6699              &image_info->border_color,exception);
6700            (void) SetImageOption(image_info,option+1,argv[i+1]);
6701            break;
6702          }
6703        if (LocaleCompare("box",option+1) == 0)
6704          {
6705            if (*option == '+')
6706              {
6707                (void) SetImageOption(image_info,"undercolor","none");
6708                break;
6709              }
6710            (void) SetImageOption(image_info,"undercolor",argv[i+1]);
6711            break;
6712          }
6713        break;
6714      }
6715      case 'c':
6716      {
6717        if (LocaleCompare("cache",option+1) == 0)
6718          {
6719            MagickSizeType
6720              limit;
6721
6722            limit=MagickResourceInfinity;
6723            if (LocaleCompare("unlimited",argv[i+1]) != 0)
6724              limit=(MagickSizeType) SiPrefixToDoubleInterval(argv[i+1],
6725                100.0);
6726            (void) SetMagickResourceLimit(MemoryResource,limit);
6727            (void) SetMagickResourceLimit(MapResource,2*limit);
6728            break;
6729          }
6730        if (LocaleCompare("caption",option+1) == 0)
6731          {
6732            if (*option == '+')
6733              {
6734                (void) DeleteImageOption(image_info,option+1);
6735                break;
6736              }
6737            (void) SetImageOption(image_info,option+1,argv[i+1]);
6738            break;
6739          }
6740        if (LocaleCompare("colorspace",option+1) == 0)
6741          {
6742            if (*option == '+')
6743              {
6744                image_info->colorspace=UndefinedColorspace;
6745                (void) SetImageOption(image_info,option+1,"undefined");
6746                break;
6747              }
6748            image_info->colorspace=(ColorspaceType) ParseCommandOption(
6749              MagickColorspaceOptions,MagickFalse,argv[i+1]);
6750            (void) SetImageOption(image_info,option+1,argv[i+1]);
6751            break;
6752          }
6753        if (LocaleCompare("comment",option+1) == 0)
6754          {
6755            if (*option == '+')
6756              {
6757                (void) DeleteImageOption(image_info,option+1);
6758                break;
6759              }
6760            (void) SetImageOption(image_info,option+1,argv[i+1]);
6761            break;
6762          }
6763        if (LocaleCompare("compose",option+1) == 0)
6764          {
6765            if (*option == '+')
6766              {
6767                (void) SetImageOption(image_info,option+1,"undefined");
6768                break;
6769              }
6770            (void) SetImageOption(image_info,option+1,argv[i+1]);
6771            break;
6772          }
6773        if (LocaleCompare("compress",option+1) == 0)
6774          {
6775            if (*option == '+')
6776              {
6777                image_info->compression=UndefinedCompression;
6778                (void) SetImageOption(image_info,option+1,"undefined");
6779                break;
6780              }
6781            image_info->compression=(CompressionType) ParseCommandOption(
6782              MagickCompressOptions,MagickFalse,argv[i+1]);
6783            (void) SetImageOption(image_info,option+1,argv[i+1]);
6784            break;
6785          }
6786        break;
6787      }
6788      case 'd':
6789      {
6790        if (LocaleCompare("debug",option+1) == 0)
6791          {
6792            if (*option == '+')
6793              (void) SetLogEventMask("none");
6794            else
6795              (void) SetLogEventMask(argv[i+1]);
6796            image_info->debug=IsEventLogging();
6797            break;
6798          }
6799        if (LocaleCompare("define",option+1) == 0)
6800          {
6801            if (*option == '+')
6802              {
6803                if (LocaleNCompare(argv[i+1],"registry:",9) == 0)
6804                  (void) DeleteImageRegistry(argv[i+1]+9);
6805                else
6806                  (void) DeleteImageOption(image_info,argv[i+1]);
6807                break;
6808              }
6809            if (LocaleNCompare(argv[i+1],"registry:",9) == 0)
6810              {
6811                (void) DefineImageRegistry(StringRegistryType,argv[i+1]+9,
6812                  exception);
6813                break;
6814              }
6815            (void) DefineImageOption(image_info,argv[i+1]);
6816            break;
6817          }
6818        if (LocaleCompare("delay",option+1) == 0)
6819          {
6820            if (*option == '+')
6821              {
6822                (void) SetImageOption(image_info,option+1,"0");
6823                break;
6824              }
6825            (void) SetImageOption(image_info,option+1,argv[i+1]);
6826            break;
6827          }
6828        if (LocaleCompare("density",option+1) == 0)
6829          {
6830            /*
6831              Set image density.
6832            */
6833            if (*option == '+')
6834              {
6835                if (image_info->density != (char *) NULL)
6836                  image_info->density=DestroyString(image_info->density);
6837                (void) SetImageOption(image_info,option+1,"72");
6838                break;
6839              }
6840            (void) CloneString(&image_info->density,argv[i+1]);
6841            (void) SetImageOption(image_info,option+1,argv[i+1]);
6842            break;
6843          }
6844        if (LocaleCompare("depth",option+1) == 0)
6845          {
6846            if (*option == '+')
6847              {
6848                image_info->depth=MAGICKCORE_QUANTUM_DEPTH;
6849                break;
6850              }
6851            image_info->depth=StringToUnsignedLong(argv[i+1]);
6852            break;
6853          }
6854        if (LocaleCompare("direction",option+1) == 0)
6855          {
6856            if (*option == '+')
6857              {
6858                (void) SetImageOption(image_info,option+1,"undefined");
6859                break;
6860              }
6861            (void) SetImageOption(image_info,option+1,argv[i+1]);
6862            break;
6863          }
6864        if (LocaleCompare("display",option+1) == 0)
6865          {
6866            if (*option == '+')
6867              {
6868                if (image_info->server_name != (char *) NULL)
6869                  image_info->server_name=DestroyString(
6870                    image_info->server_name);
6871                break;
6872              }
6873            (void) CloneString(&image_info->server_name,argv[i+1]);
6874            break;
6875          }
6876        if (LocaleCompare("dispose",option+1) == 0)
6877          {
6878            if (*option == '+')
6879              {
6880                (void) SetImageOption(image_info,option+1,"undefined");
6881                break;
6882              }
6883            (void) SetImageOption(image_info,option+1,argv[i+1]);
6884            break;
6885          }
6886        if (LocaleCompare("dither",option+1) == 0)
6887          {
6888            if (*option == '+')
6889              {
6890                image_info->dither=MagickFalse;
6891                (void) SetImageOption(image_info,option+1,"none");
6892                break;
6893              }
6894            (void) SetImageOption(image_info,option+1,argv[i+1]);
6895            image_info->dither=MagickTrue;
6896            break;
6897          }
6898        break;
6899      }
6900      case 'e':
6901      {
6902        if (LocaleCompare("encoding",option+1) == 0)
6903          {
6904            if (*option == '+')
6905              {
6906                (void) SetImageOption(image_info,option+1,"undefined");
6907                break;
6908              }
6909            (void) SetImageOption(image_info,option+1,argv[i+1]);
6910            break;
6911          }
6912        if (LocaleCompare("endian",option+1) == 0)
6913          {
6914            if (*option == '+')
6915              {
6916                image_info->endian=UndefinedEndian;
6917                (void) SetImageOption(image_info,option+1,"undefined");
6918                break;
6919              }
6920            image_info->endian=(EndianType) ParseCommandOption(
6921              MagickEndianOptions,MagickFalse,argv[i+1]);
6922            (void) SetImageOption(image_info,option+1,argv[i+1]);
6923            break;
6924          }
6925        if (LocaleCompare("extract",option+1) == 0)
6926          {
6927            /*
6928              Set image extract geometry.
6929            */
6930            if (*option == '+')
6931              {
6932                if (image_info->extract != (char *) NULL)
6933                  image_info->extract=DestroyString(image_info->extract);
6934                break;
6935              }
6936            (void) CloneString(&image_info->extract,argv[i+1]);
6937            break;
6938          }
6939        break;
6940      }
6941      case 'f':
6942      {
6943        if (LocaleCompare("family",option+1) == 0)
6944          {
6945            if (*option != '+')
6946              (void) SetImageOption(image_info,option+1,argv[i+1]);
6947            break;
6948          }
6949        if (LocaleCompare("fill",option+1) == 0)
6950          {
6951            if (*option == '+')
6952              {
6953                (void) SetImageOption(image_info,option+1,"none");
6954                break;
6955              }
6956            (void) SetImageOption(image_info,option+1,argv[i+1]);
6957            break;
6958          }
6959        if (LocaleCompare("filter",option+1) == 0)
6960          {
6961            if (*option == '+')
6962              {
6963                (void) SetImageOption(image_info,option+1,"undefined");
6964                break;
6965              }
6966            (void) SetImageOption(image_info,option+1,argv[i+1]);
6967            break;
6968          }
6969        if (LocaleCompare("font",option+1) == 0)
6970          {
6971            if (*option == '+')
6972              {
6973                if (image_info->font != (char *) NULL)
6974                  image_info->font=DestroyString(image_info->font);
6975                break;
6976              }
6977            (void) CloneString(&image_info->font,argv[i+1]);
6978            break;
6979          }
6980        if (LocaleCompare("format",option+1) == 0)
6981          {
6982            register const char
6983              *q;
6984
6985            for (q=strchr(argv[i+1],'%'); q != (char *) NULL; q=strchr(q+1,'%'))
6986              if (strchr("Agkrz@[#",*(q+1)) != (char *) NULL)
6987                image_info->ping=MagickFalse;
6988            (void) SetImageOption(image_info,option+1,argv[i+1]);
6989            break;
6990          }
6991        if (LocaleCompare("fuzz",option+1) == 0)
6992          {
6993            if (*option == '+')
6994              {
6995                image_info->fuzz=0.0;
6996                (void) SetImageOption(image_info,option+1,"0");
6997                break;
6998              }
6999            image_info->fuzz=StringToDoubleInterval(argv[i+1],(double)
7000              QuantumRange+1.0);
7001            (void) SetImageOption(image_info,option+1,argv[i+1]);
7002            break;
7003          }
7004        break;
7005      }
7006      case 'g':
7007      {
7008        if (LocaleCompare("gravity",option+1) == 0)
7009          {
7010            if (*option == '+')
7011              {
7012                (void) SetImageOption(image_info,option+1,"undefined");
7013                break;
7014              }
7015            (void) SetImageOption(image_info,option+1,argv[i+1]);
7016            break;
7017          }
7018        if (LocaleCompare("green-primary",option+1) == 0)
7019          {
7020            if (*option == '+')
7021              {
7022                (void) SetImageOption(image_info,option+1,"0.0");
7023                break;
7024              }
7025            (void) SetImageOption(image_info,option+1,argv[i+1]);
7026            break;
7027          }
7028        break;
7029      }
7030      case 'i':
7031      {
7032        if (LocaleCompare("intensity",option+1) == 0)
7033          {
7034            if (*option == '+')
7035              {
7036                (void) SetImageOption(image_info,option+1,"undefined");
7037                break;
7038              }
7039            (void) SetImageOption(image_info,option+1,argv[i+1]);
7040            break;
7041          }
7042        if (LocaleCompare("intent",option+1) == 0)
7043          {
7044            if (*option == '+')
7045              {
7046                (void) SetImageOption(image_info,option+1,"undefined");
7047                break;
7048              }
7049            (void) SetImageOption(image_info,option+1,argv[i+1]);
7050            break;
7051          }
7052        if (LocaleCompare("interlace",option+1) == 0)
7053          {
7054            if (*option == '+')
7055              {
7056                image_info->interlace=UndefinedInterlace;
7057                (void) SetImageOption(image_info,option+1,"undefined");
7058                break;
7059              }
7060            image_info->interlace=(InterlaceType) ParseCommandOption(
7061              MagickInterlaceOptions,MagickFalse,argv[i+1]);
7062            (void) SetImageOption(image_info,option+1,argv[i+1]);
7063            break;
7064          }
7065        if (LocaleCompare("interline-spacing",option+1) == 0)
7066          {
7067            if (*option == '+')
7068              {
7069                (void) SetImageOption(image_info,option+1,"undefined");
7070                break;
7071              }
7072            (void) SetImageOption(image_info,option+1,argv[i+1]);
7073            break;
7074          }
7075        if (LocaleCompare("interpolate",option+1) == 0)
7076          {
7077            if (*option == '+')
7078              {
7079                (void) SetImageOption(image_info,option+1,"undefined");
7080                break;
7081              }
7082            (void) SetImageOption(image_info,option+1,argv[i+1]);
7083            break;
7084          }
7085        if (LocaleCompare("interword-spacing",option+1) == 0)
7086          {
7087            if (*option == '+')
7088              {
7089                (void) SetImageOption(image_info,option+1,"undefined");
7090                break;
7091              }
7092            (void) SetImageOption(image_info,option+1,argv[i+1]);
7093            break;
7094          }
7095        break;
7096      }
7097      case 'k':
7098      {
7099        if (LocaleCompare("kerning",option+1) == 0)
7100          {
7101            if (*option == '+')
7102              {
7103                (void) SetImageOption(image_info,option+1,"undefined");
7104                break;
7105              }
7106            (void) SetImageOption(image_info,option+1,argv[i+1]);
7107            break;
7108          }
7109        break;
7110      }
7111      case 'l':
7112      {
7113        if (LocaleCompare("label",option+1) == 0)
7114          {
7115            if (*option == '+')
7116              {
7117                (void) DeleteImageOption(image_info,option+1);
7118                break;
7119              }
7120            (void) SetImageOption(image_info,option+1,argv[i+1]);
7121            break;
7122          }
7123        if (LocaleCompare("limit",option+1) == 0)
7124          {
7125            MagickSizeType
7126              limit;
7127
7128            ResourceType
7129              type;
7130
7131            if (*option == '+')
7132              break;
7133            type=(ResourceType) ParseCommandOption(MagickResourceOptions,
7134              MagickFalse,argv[i+1]);
7135            limit=MagickResourceInfinity;
7136            if (LocaleCompare("unlimited",argv[i+2]) != 0)
7137              limit=(MagickSizeType) SiPrefixToDoubleInterval(argv[i+2],100.0);
7138            (void) SetMagickResourceLimit(type,limit);
7139            break;
7140          }
7141        if (LocaleCompare("list",option+1) == 0)
7142          {
7143            ssize_t
7144              list;
7145
7146            /*
7147              Display configuration list.
7148            */
7149            list=ParseCommandOption(MagickListOptions,MagickFalse,argv[i+1]);
7150            switch (list)
7151            {
7152              case MagickCoderOptions:
7153              {
7154                (void) ListCoderInfo((FILE *) NULL,exception);
7155                break;
7156              }
7157              case MagickColorOptions:
7158              {
7159                (void) ListColorInfo((FILE *) NULL,exception);
7160                break;
7161              }
7162              case MagickConfigureOptions:
7163              {
7164                (void) ListConfigureInfo((FILE *) NULL,exception);
7165                break;
7166              }
7167              case MagickDelegateOptions:
7168              {
7169                (void) ListDelegateInfo((FILE *) NULL,exception);
7170                break;
7171              }
7172              case MagickFontOptions:
7173              {
7174                (void) ListTypeInfo((FILE *) NULL,exception);
7175                break;
7176              }
7177              case MagickFormatOptions:
7178              {
7179                (void) ListMagickInfo((FILE *) NULL,exception);
7180                break;
7181              }
7182              case MagickLocaleOptions:
7183              {
7184                (void) ListLocaleInfo((FILE *) NULL,exception);
7185                break;
7186              }
7187              case MagickLogOptions:
7188              {
7189                (void) ListLogInfo((FILE *) NULL,exception);
7190                break;
7191              }
7192              case MagickMagicOptions:
7193              {
7194                (void) ListMagicInfo((FILE *) NULL,exception);
7195                break;
7196              }
7197              case MagickMimeOptions:
7198              {
7199                (void) ListMimeInfo((FILE *) NULL,exception);
7200                break;
7201              }
7202              case MagickModuleOptions:
7203              {
7204                (void) ListModuleInfo((FILE *) NULL,exception);
7205                break;
7206              }
7207              case MagickPolicyOptions:
7208              {
7209                (void) ListPolicyInfo((FILE *) NULL,exception);
7210                break;
7211              }
7212              case MagickResourceOptions:
7213              {
7214                (void) ListMagickResourceInfo((FILE *) NULL,exception);
7215                break;
7216              }
7217              case MagickThresholdOptions:
7218              {
7219                (void) ListThresholdMaps((FILE *) NULL,exception);
7220                break;
7221              }
7222              default:
7223              {
7224                (void) ListCommandOptions((FILE *) NULL,(CommandOption) list,
7225                  exception);
7226                break;
7227              }
7228            }
7229            break;
7230          }
7231        if (LocaleCompare("log",option+1) == 0)
7232          {
7233            if (*option == '+')
7234              break;
7235            (void) SetLogFormat(argv[i+1]);
7236            break;
7237          }
7238        if (LocaleCompare("loop",option+1) == 0)
7239          {
7240            if (*option == '+')
7241              {
7242                (void) SetImageOption(image_info,option+1,"0");
7243                break;
7244              }
7245            (void) SetImageOption(image_info,option+1,argv[i+1]);
7246            break;
7247          }
7248        break;
7249      }
7250      case 'm':
7251      {
7252        if (LocaleCompare("matte",option+1) == 0)
7253          {
7254            if (*option == '+')
7255              {
7256                (void) SetImageOption(image_info,option+1,"false");
7257                break;
7258              }
7259            (void) SetImageOption(image_info,option+1,"true");
7260            break;
7261          }
7262        if (LocaleCompare("metric",option+1) == 0)
7263          {
7264            if (*option == '+')
7265              (void) DeleteImageOption(image_info,option+1);
7266            else
7267              (void) SetImageOption(image_info,option+1,argv[i+1]);
7268            break;
7269          }
7270        if (LocaleCompare("monitor",option+1) == 0)
7271          {
7272            (void) SetImageInfoProgressMonitor(image_info,MonitorProgress,
7273              (void *) NULL);
7274            break;
7275          }
7276        if (LocaleCompare("monochrome",option+1) == 0)
7277          {
7278            image_info->monochrome=(*option == '-') ? MagickTrue : MagickFalse;
7279            break;
7280          }
7281        break;
7282      }
7283      case 'o':
7284      {
7285        if (LocaleCompare("orient",option+1) == 0)
7286          {
7287            if (*option == '+')
7288              {
7289                image_info->orientation=UndefinedOrientation;
7290                (void) SetImageOption(image_info,option+1,"undefined");
7291                break;
7292              }
7293            image_info->orientation=(OrientationType) ParseCommandOption(
7294              MagickOrientationOptions,MagickFalse,argv[i+1]);
7295            (void) SetImageOption(image_info,option+1,argv[i+1]);
7296            break;
7297          }
7298      }
7299      case 'p':
7300      {
7301        if (LocaleCompare("page",option+1) == 0)
7302          {
7303            char
7304              *canonical_page,
7305              page[MagickPathExtent];
7306
7307            const char
7308              *image_option;
7309
7310            MagickStatusType
7311              flags;
7312
7313            RectangleInfo
7314              geometry;
7315
7316            if (*option == '+')
7317              {
7318                (void) DeleteImageOption(image_info,option+1);
7319                (void) CloneString(&image_info->page,(char *) NULL);
7320                break;
7321              }
7322            (void) ResetMagickMemory(&geometry,0,sizeof(geometry));
7323            image_option=GetImageOption(image_info,"page");
7324            if (image_option != (const char *) NULL)
7325              flags=ParseAbsoluteGeometry(image_option,&geometry);
7326            canonical_page=GetPageGeometry(argv[i+1]);
7327            flags=ParseAbsoluteGeometry(canonical_page,&geometry);
7328            canonical_page=DestroyString(canonical_page);
7329            (void) FormatLocaleString(page,MagickPathExtent,"%lux%lu",
7330              (unsigned long) geometry.width,(unsigned long) geometry.height);
7331            if (((flags & XValue) != 0) || ((flags & YValue) != 0))
7332              (void) FormatLocaleString(page,MagickPathExtent,"%lux%lu%+ld%+ld",
7333                (unsigned long) geometry.width,(unsigned long) geometry.height,
7334                (long) geometry.x,(long) geometry.y);
7335            (void) SetImageOption(image_info,option+1,page);
7336            (void) CloneString(&image_info->page,page);
7337            break;
7338          }
7339        if (LocaleCompare("ping",option+1) == 0)
7340          {
7341            image_info->ping=(*option == '-') ? MagickTrue : MagickFalse;
7342            break;
7343          }
7344        if (LocaleCompare("pointsize",option+1) == 0)
7345          {
7346            if (*option == '+')
7347              geometry_info.rho=0.0;
7348            else
7349              (void) ParseGeometry(argv[i+1],&geometry_info);
7350            image_info->pointsize=geometry_info.rho;
7351            break;
7352          }
7353        if (LocaleCompare("precision",option+1) == 0)
7354          {
7355            (void) SetMagickPrecision(StringToInteger(argv[i+1]));
7356            break;
7357          }
7358        break;
7359      }
7360      case 'q':
7361      {
7362        if (LocaleCompare("quality",option+1) == 0)
7363          {
7364            /*
7365              Set image compression quality.
7366            */
7367            if (*option == '+')
7368              {
7369                image_info->quality=UndefinedCompressionQuality;
7370                (void) SetImageOption(image_info,option+1,"0");
7371                break;
7372              }
7373            image_info->quality=StringToUnsignedLong(argv[i+1]);
7374            (void) SetImageOption(image_info,option+1,argv[i+1]);
7375            break;
7376          }
7377        if (LocaleCompare("quiet",option+1) == 0)
7378          {
7379            static WarningHandler
7380              warning_handler = (WarningHandler) NULL;
7381
7382            if (*option == '+')
7383              {
7384                /*
7385                  Restore error or warning messages.
7386                */
7387                warning_handler=SetWarningHandler(warning_handler);
7388                break;
7389              }
7390            /*
7391              Suppress error or warning messages.
7392            */
7393            warning_handler=SetWarningHandler((WarningHandler) NULL);
7394            break;
7395          }
7396        break;
7397      }
7398      case 'r':
7399      {
7400        if (LocaleCompare("red-primary",option+1) == 0)
7401          {
7402            if (*option == '+')
7403              {
7404                (void) SetImageOption(image_info,option+1,"0.0");
7405                break;
7406              }
7407            (void) SetImageOption(image_info,option+1,argv[i+1]);
7408            break;
7409          }
7410        break;
7411      }
7412      case 's':
7413      {
7414        if (LocaleCompare("sampling-factor",option+1) == 0)
7415          {
7416            /*
7417              Set image sampling factor.
7418            */
7419            if (*option == '+')
7420              {
7421                if (image_info->sampling_factor != (char *) NULL)
7422                  image_info->sampling_factor=DestroyString(
7423                    image_info->sampling_factor);
7424                break;
7425              }
7426            (void) CloneString(&image_info->sampling_factor,argv[i+1]);
7427            break;
7428          }
7429        if (LocaleCompare("scene",option+1) == 0)
7430          {
7431            /*
7432              Set image scene.
7433            */
7434            if (*option == '+')
7435              {
7436                image_info->scene=0;
7437                (void) SetImageOption(image_info,option+1,"0");
7438                break;
7439              }
7440            image_info->scene=StringToUnsignedLong(argv[i+1]);
7441            (void) SetImageOption(image_info,option+1,argv[i+1]);
7442            break;
7443          }
7444        if (LocaleCompare("seed",option+1) == 0)
7445          {
7446            unsigned long
7447              seed;
7448
7449            if (*option == '+')
7450              {
7451                seed=(unsigned long) time((time_t *) NULL);
7452                SetRandomSecretKey(seed);
7453                break;
7454              }
7455            seed=StringToUnsignedLong(argv[i+1]);
7456            SetRandomSecretKey(seed);
7457            break;
7458          }
7459        if (LocaleCompare("size",option+1) == 0)
7460          {
7461            if (*option == '+')
7462              {
7463                if (image_info->size != (char *) NULL)
7464                  image_info->size=DestroyString(image_info->size);
7465                break;
7466              }
7467            (void) CloneString(&image_info->size,argv[i+1]);
7468            break;
7469          }
7470        if (LocaleCompare("stroke",option+1) == 0)
7471          {
7472            if (*option == '+')
7473              {
7474                (void) SetImageOption(image_info,option+1,"none");
7475                break;
7476              }
7477            (void) SetImageOption(image_info,option+1,argv[i+1]);
7478            break;
7479          }
7480        if (LocaleCompare("strokewidth",option+1) == 0)
7481          {
7482            if (*option == '+')
7483              (void) SetImageOption(image_info,option+1,"0");
7484            else
7485              (void) SetImageOption(image_info,option+1,argv[i+1]);
7486            break;
7487          }
7488        if (LocaleCompare("style",option+1) == 0)
7489          {
7490            if (*option == '+')
7491              {
7492                (void) SetImageOption(image_info,option+1,"none");
7493                break;
7494              }
7495            (void) SetImageOption(image_info,option+1,argv[i+1]);
7496            break;
7497          }
7498        if (LocaleCompare("synchronize",option+1) == 0)
7499          {
7500            if (*option == '+')
7501              {
7502                image_info->synchronize=MagickFalse;
7503                break;
7504              }
7505            image_info->synchronize=MagickTrue;
7506            break;
7507          }
7508        break;
7509      }
7510      case 't':
7511      {
7512        if (LocaleCompare("taint",option+1) == 0)
7513          {
7514            if (*option == '+')
7515              {
7516                (void) SetImageOption(image_info,option+1,"false");
7517                break;
7518              }
7519            (void) SetImageOption(image_info,option+1,"true");
7520            break;
7521          }
7522        if (LocaleCompare("texture",option+1) == 0)
7523          {
7524            if (*option == '+')
7525              {
7526                if (image_info->texture != (char *) NULL)
7527                  image_info->texture=DestroyString(image_info->texture);
7528                break;
7529              }
7530            (void) CloneString(&image_info->texture,argv[i+1]);
7531            break;
7532          }
7533        if (LocaleCompare("tile-offset",option+1) == 0)
7534          {
7535            if (*option == '+')
7536              (void) SetImageOption(image_info,option+1,"0");
7537            else
7538              (void) SetImageOption(image_info,option+1,argv[i+1]);
7539            break;
7540          }
7541        if (LocaleCompare("transparent-color",option+1) == 0)
7542          {
7543            if (*option == '+')
7544              {
7545                (void) QueryColorCompliance("none",AllCompliance,
7546                  &image_info->transparent_color,exception);
7547                (void) SetImageOption(image_info,option+1,"none");
7548                break;
7549              }
7550            (void) QueryColorCompliance(argv[i+1],AllCompliance,
7551              &image_info->transparent_color,exception);
7552            (void) SetImageOption(image_info,option+1,argv[i+1]);
7553            break;
7554          }
7555        if (LocaleCompare("type",option+1) == 0)
7556          {
7557            if (*option == '+')
7558              {
7559                image_info->type=UndefinedType;
7560                (void) SetImageOption(image_info,option+1,"undefined");
7561                break;
7562              }
7563            image_info->type=(ImageType) ParseCommandOption(MagickTypeOptions,
7564              MagickFalse,argv[i+1]);
7565            (void) SetImageOption(image_info,option+1,argv[i+1]);
7566            break;
7567          }
7568        break;
7569      }
7570      case 'u':
7571      {
7572        if (LocaleCompare("undercolor",option+1) == 0)
7573          {
7574            if (*option == '+')
7575              (void) DeleteImageOption(image_info,option+1);
7576            else
7577              (void) SetImageOption(image_info,option+1,argv[i+1]);
7578            break;
7579          }
7580        if (LocaleCompare("units",option+1) == 0)
7581          {
7582            if (*option == '+')
7583              {
7584                image_info->units=UndefinedResolution;
7585                (void) SetImageOption(image_info,option+1,"undefined");
7586                break;
7587              }
7588            image_info->units=(ResolutionType) ParseCommandOption(
7589              MagickResolutionOptions,MagickFalse,argv[i+1]);
7590            (void) SetImageOption(image_info,option+1,argv[i+1]);
7591            break;
7592          }
7593        break;
7594      }
7595      case 'v':
7596      {
7597        if (LocaleCompare("verbose",option+1) == 0)
7598          {
7599            if (*option == '+')
7600              {
7601                image_info->verbose=MagickFalse;
7602                break;
7603              }
7604            image_info->verbose=MagickTrue;
7605            image_info->ping=MagickFalse;
7606            break;
7607          }
7608        if (LocaleCompare("virtual-pixel",option+1) == 0)
7609          {
7610            if (*option == '+')
7611              (void) SetImageOption(image_info,option+1,"undefined");
7612            else
7613              (void) SetImageOption(image_info,option+1,argv[i+1]);
7614            break;
7615          }
7616        break;
7617      }
7618      case 'w':
7619      {
7620        if (LocaleCompare("weight",option+1) == 0)
7621          {
7622            if (*option == '+')
7623              (void) SetImageOption(image_info,option+1,"0");
7624            else
7625              (void) SetImageOption(image_info,option+1,argv[i+1]);
7626            break;
7627          }
7628        if (LocaleCompare("white-point",option+1) == 0)
7629          {
7630            if (*option == '+')
7631              (void) SetImageOption(image_info,option+1,"0.0");
7632            else
7633              (void) SetImageOption(image_info,option+1,argv[i+1]);
7634            break;
7635          }
7636        break;
7637      }
7638      default:
7639        break;
7640    }
7641    i+=count;
7642  }
7643  return(MagickTrue);
7644}
7645
7646/*
7647%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7648%                                                                             %
7649%                                                                             %
7650%                                                                             %
7651+     M o g r i f y I m a g e L i s t                                         %
7652%                                                                             %
7653%                                                                             %
7654%                                                                             %
7655%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
7656%
7657%  MogrifyImageList() applies any command line options that might affect the
7658%  entire image list (e.g. -append, -coalesce, etc.).
7659%
7660%  The format of the MogrifyImage method is:
7661%
7662%      MagickBooleanType MogrifyImageList(ImageInfo *image_info,const int argc,
7663%        const char **argv,Image **images,ExceptionInfo *exception)
7664%
7665%  A description of each parameter follows:
7666%
7667%    o image_info: the image info..
7668%
7669%    o argc: Specifies a pointer to an integer describing the number of
7670%      elements in the argument vector.
7671%
7672%    o argv: Specifies a pointer to a text array containing the command line
7673%      arguments.
7674%
7675%    o images: pointer to pointer of the first image in image list.
7676%
7677%    o exception: return any errors or warnings in this structure.
7678%
7679*/
7680WandExport MagickBooleanType MogrifyImageList(ImageInfo *image_info,
7681  const int argc,const char **argv,Image **images,ExceptionInfo *exception)
7682{
7683  const char
7684    *option;
7685
7686  ImageInfo
7687    *mogrify_info;
7688
7689  MagickStatusType
7690    status;
7691
7692  PixelInterpolateMethod
7693   interpolate_method;
7694
7695  QuantizeInfo
7696    *quantize_info;
7697
7698  register ssize_t
7699    i;
7700
7701  ssize_t
7702    count,
7703    index;
7704
7705  /*
7706    Apply options to the image list.
7707  */
7708  assert(image_info != (ImageInfo *) NULL);
7709  assert(image_info->signature == MagickCoreSignature);
7710  assert(images != (Image **) NULL);
7711  assert((*images)->previous == (Image *) NULL);
7712  assert((*images)->signature == MagickCoreSignature);
7713  if ((*images)->debug != MagickFalse)
7714    (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
7715      (*images)->filename);
7716  if ((argc <= 0) || (*argv == (char *) NULL))
7717    return(MagickTrue);
7718  interpolate_method=UndefinedInterpolatePixel;
7719  mogrify_info=CloneImageInfo(image_info);
7720  quantize_info=AcquireQuantizeInfo(mogrify_info);
7721  status=MagickTrue;
7722  for (i=0; i < (ssize_t) argc; i++)
7723  {
7724    if (*images == (Image *) NULL)
7725      break;
7726    option=argv[i];
7727    if (IsCommandOption(option) == MagickFalse)
7728      continue;
7729    count=ParseCommandOption(MagickCommandOptions,MagickFalse,option);
7730    count=MagickMax(count,0L);
7731    if ((i+count) >= (ssize_t) argc)
7732      break;
7733    status=MogrifyImageInfo(mogrify_info,(int) count+1,argv+i,exception);
7734    switch (*(option+1))
7735    {
7736      case 'a':
7737      {
7738        if (LocaleCompare("affinity",option+1) == 0)
7739          {
7740            (void) SyncImagesSettings(mogrify_info,*images,exception);
7741            if (*option == '+')
7742              {
7743                (void) RemapImages(quantize_info,*images,(Image *) NULL,
7744                  exception);
7745                break;
7746              }
7747            i++;
7748            break;
7749          }
7750        if (LocaleCompare("append",option+1) == 0)
7751          {
7752            Image
7753              *append_image;
7754
7755            (void) SyncImagesSettings(mogrify_info,*images,exception);
7756            append_image=AppendImages(*images,*option == '-' ? MagickTrue :
7757              MagickFalse,exception);
7758            if (append_image == (Image *) NULL)
7759              {
7760                status=MagickFalse;
7761                break;
7762              }
7763            *images=DestroyImageList(*images);
7764            *images=append_image;
7765            break;
7766          }
7767        if (LocaleCompare("average",option+1) == 0)
7768          {
7769            Image
7770              *average_image;
7771
7772            /*
7773              Average an image sequence (deprecated).
7774            */
7775            (void) SyncImagesSettings(mogrify_info,*images,exception);
7776            average_image=EvaluateImages(*images,MeanEvaluateOperator,
7777              exception);
7778            if (average_image == (Image *) NULL)
7779              {
7780                status=MagickFalse;
7781                break;
7782              }
7783            *images=DestroyImageList(*images);
7784            *images=average_image;
7785            break;
7786          }
7787        break;
7788      }
7789      case 'c':
7790      {
7791        if (LocaleCompare("channel-fx",option+1) == 0)
7792          {
7793            Image
7794              *channel_image;
7795
7796            (void) SyncImagesSettings(mogrify_info,*images,exception);
7797            channel_image=ChannelFxImage(*images,argv[i+1],exception);
7798            if (channel_image == (Image *) NULL)
7799              {
7800                status=MagickFalse;
7801                break;
7802              }
7803            *images=DestroyImageList(*images);
7804            *images=channel_image;
7805            break;
7806          }
7807        if (LocaleCompare("clut",option+1) == 0)
7808          {
7809            Image
7810              *clut_image,
7811              *image;
7812
7813            (void) SyncImagesSettings(mogrify_info,*images,exception);
7814            image=RemoveFirstImageFromList(images);
7815            clut_image=RemoveFirstImageFromList(images);
7816            if (clut_image == (Image *) NULL)
7817              {
7818                status=MagickFalse;
7819                break;
7820              }
7821            (void) ClutImage(image,clut_image,interpolate_method,exception);
7822            clut_image=DestroyImage(clut_image);
7823            *images=DestroyImageList(*images);
7824            *images=image;
7825            break;
7826          }
7827        if (LocaleCompare("coalesce",option+1) == 0)
7828          {
7829            Image
7830              *coalesce_image;
7831
7832            (void) SyncImagesSettings(mogrify_info,*images,exception);
7833            coalesce_image=CoalesceImages(*images,exception);
7834            if (coalesce_image == (Image *) NULL)
7835              {
7836                status=MagickFalse;
7837                break;
7838              }
7839            *images=DestroyImageList(*images);
7840            *images=coalesce_image;
7841            break;
7842          }
7843        if (LocaleCompare("combine",option+1) == 0)
7844          {
7845            ColorspaceType
7846              colorspace;
7847
7848            Image
7849              *combine_image;
7850
7851            (void) SyncImagesSettings(mogrify_info,*images,exception);
7852            colorspace=(*images)->colorspace;
7853            if (*option == '+')
7854              colorspace=(ColorspaceType) ParseCommandOption(
7855                MagickColorspaceOptions,MagickFalse,argv[i+1]);
7856            combine_image=CombineImages(*images,colorspace,exception);
7857            if (combine_image == (Image *) NULL)
7858              {
7859                status=MagickFalse;
7860                break;
7861              }
7862            *images=DestroyImageList(*images);
7863            *images=combine_image;
7864            break;
7865          }
7866        if (LocaleCompare("compare",option+1) == 0)
7867          {
7868            double
7869              distortion;
7870
7871            Image
7872              *difference_image,
7873              *image,
7874              *reconstruct_image;
7875
7876            MetricType
7877              metric;
7878
7879            /*
7880              Mathematically and visually annotate the difference between an
7881              image and its reconstruction.
7882            */
7883            (void) SyncImagesSettings(mogrify_info,*images,exception);
7884            image=RemoveFirstImageFromList(images);
7885            reconstruct_image=RemoveFirstImageFromList(images);
7886            if (reconstruct_image == (Image *) NULL)
7887              {
7888                status=MagickFalse;
7889                break;
7890              }
7891            metric=UndefinedErrorMetric;
7892            option=GetImageOption(image_info,"metric");
7893            if (option != (const char *) NULL)
7894              metric=(MetricType) ParseCommandOption(MagickMetricOptions,
7895                MagickFalse,option);
7896            difference_image=CompareImages(image,reconstruct_image,metric,
7897              &distortion,exception);
7898            if (difference_image == (Image *) NULL)
7899              break;
7900            if (*images != (Image *) NULL)
7901              *images=DestroyImage(*images);
7902            *images=difference_image;
7903            break;
7904          }
7905        if (LocaleCompare("complex",option+1) == 0)
7906          {
7907            ComplexOperator
7908              op;
7909
7910            Image
7911              *complex_images;
7912
7913            (void) SyncImageSettings(mogrify_info,*images,exception);
7914            op=(ComplexOperator) ParseCommandOption(MagickComplexOptions,
7915              MagickFalse,argv[i+1]);
7916            complex_images=ComplexImages(*images,op,exception);
7917            if (complex_images == (Image *) NULL)
7918              {
7919                status=MagickFalse;
7920                break;
7921              }
7922            *images=DestroyImageList(*images);
7923            *images=complex_images;
7924            break;
7925          }
7926        if (LocaleCompare("composite",option+1) == 0)
7927          {
7928            const char
7929              *value;
7930
7931            Image
7932              *mask_image,
7933              *composite_image,
7934              *image;
7935
7936            MagickBooleanType
7937              clip_to_self;
7938
7939            RectangleInfo
7940              geometry;
7941
7942            (void) SyncImagesSettings(mogrify_info,*images,exception);
7943            value=GetImageOption(mogrify_info,"compose:clip-to-self");
7944            if (value == (const char *) NULL)
7945              clip_to_self=MagickTrue;
7946            else
7947              clip_to_self=IsStringTrue(GetImageOption(mogrify_info,
7948                "compose:clip-to-self")); /* if this is true */
7949            if (clip_to_self == MagickFalse) /* or */
7950              clip_to_self=IsStringFalse(GetImageOption(mogrify_info,
7951                "compose:outside-overlay"));
7952            image=RemoveFirstImageFromList(images);
7953            composite_image=RemoveFirstImageFromList(images);
7954            if (composite_image == (Image *) NULL)
7955              {
7956                status=MagickFalse;
7957                break;
7958              }
7959            if (composite_image->geometry != (char *) NULL)
7960              {
7961                RectangleInfo
7962                  resize_geometry;
7963
7964                (void) ParseRegionGeometry(composite_image,
7965                  composite_image->geometry,&resize_geometry,exception);
7966                if ((composite_image->columns != resize_geometry.width) ||
7967                    (composite_image->rows != resize_geometry.height))
7968                  {
7969                    Image
7970                      *resize_image;
7971
7972                    resize_image=ResizeImage(composite_image,
7973                      resize_geometry.width,resize_geometry.height,
7974                      composite_image->filter,exception);
7975                    if (resize_image != (Image *) NULL)
7976                      {
7977                        composite_image=DestroyImage(composite_image);
7978                        composite_image=resize_image;
7979                      }
7980                  }
7981              }
7982            SetGeometry(composite_image,&geometry);
7983            (void) ParseAbsoluteGeometry(composite_image->geometry,&geometry);
7984            GravityAdjustGeometry(image->columns,image->rows,image->gravity,
7985              &geometry);
7986            mask_image=RemoveFirstImageFromList(images);
7987            if (mask_image == (Image *) NULL)
7988              (void) CompositeImage(image,composite_image,image->compose,
7989                clip_to_self,geometry.x,geometry.y,exception);
7990            else
7991              {
7992                if ((image->compose != DisplaceCompositeOp) &&
7993                    (image->compose != DistortCompositeOp))
7994                  {
7995                    status&=CompositeImage(composite_image,mask_image,
7996                      CopyGreenCompositeOp,MagickTrue,0,0,exception);
7997                    (void) CompositeImage(image,composite_image,image->compose,
7998                      clip_to_self,geometry.x,geometry.y,exception);
7999                  }
8000                 else
8001                  {
8002                    Image
8003                      *clone_image;
8004
8005                    clone_image=CloneImage(image,0,0,MagickTrue,exception);
8006                    if (clone_image == (Image *) NULL)
8007                      break;
8008                    (void) CompositeImage(image,composite_image,image->compose,
8009                      clip_to_self,geometry.x,geometry.y,exception);
8010                    status&=CompositeImage(image,mask_image,
8011                      CopyAlphaCompositeOp,MagickTrue,0,0,exception);
8012                    status&=CompositeImage(clone_image,image,OverCompositeOp,
8013                      clip_to_self,0,0,exception);
8014                    image=DestroyImage(image);
8015                    image=clone_image;
8016                  }
8017                mask_image=DestroyImage(mask_image);
8018              }
8019            composite_image=DestroyImage(composite_image);
8020            *images=DestroyImageList(*images);
8021            *images=image;
8022            break;
8023          }
8024        if (LocaleCompare("copy",option+1) == 0)
8025          {
8026            Image
8027              *source_image;
8028
8029            OffsetInfo
8030              offset;
8031
8032            RectangleInfo
8033              geometry;
8034
8035            /*
8036              Copy image pixels.
8037            */
8038            (void) SyncImageSettings(mogrify_info,*images,exception);
8039            (void) ParsePageGeometry(*images,argv[i+2],&geometry,exception);
8040            offset.x=geometry.x;
8041            offset.y=geometry.y;
8042            source_image=(*images);
8043            if (source_image->next != (Image *) NULL)
8044              source_image=source_image->next;
8045            (void) ParsePageGeometry(source_image,argv[i+1],&geometry,
8046              exception);
8047            status=CopyImagePixels(*images,source_image,&geometry,&offset,
8048              exception);
8049            break;
8050          }
8051        break;
8052      }
8053      case 'd':
8054      {
8055        if (LocaleCompare("deconstruct",option+1) == 0)
8056          {
8057            Image
8058              *deconstruct_image;
8059
8060            (void) SyncImagesSettings(mogrify_info,*images,exception);
8061            deconstruct_image=CompareImagesLayers(*images,CompareAnyLayer,
8062              exception);
8063            if (deconstruct_image == (Image *) NULL)
8064              {
8065                status=MagickFalse;
8066                break;
8067              }
8068            *images=DestroyImageList(*images);
8069            *images=deconstruct_image;
8070            break;
8071          }
8072        if (LocaleCompare("delete",option+1) == 0)
8073          {
8074            if (*option == '+')
8075              DeleteImages(images,"-1",exception);
8076            else
8077              DeleteImages(images,argv[i+1],exception);
8078            break;
8079          }
8080        if (LocaleCompare("dither",option+1) == 0)
8081          {
8082            if (*option == '+')
8083              {
8084                quantize_info->dither_method=NoDitherMethod;
8085                break;
8086              }
8087            quantize_info->dither_method=(DitherMethod) ParseCommandOption(
8088              MagickDitherOptions,MagickFalse,argv[i+1]);
8089            break;
8090          }
8091        if (LocaleCompare("duplicate",option+1) == 0)
8092          {
8093            Image
8094              *duplicate_images;
8095
8096            if (*option == '+')
8097              duplicate_images=DuplicateImages(*images,1,"-1",exception);
8098            else
8099              {
8100                const char
8101                  *p;
8102
8103                size_t
8104                  number_duplicates;
8105
8106                number_duplicates=(size_t) StringToLong(argv[i+1]);
8107                p=strchr(argv[i+1],',');
8108                if (p == (const char *) NULL)
8109                  duplicate_images=DuplicateImages(*images,number_duplicates,
8110                    "-1",exception);
8111                else
8112                  duplicate_images=DuplicateImages(*images,number_duplicates,p,
8113                    exception);
8114              }
8115            AppendImageToList(images, duplicate_images);
8116            (void) SyncImagesSettings(mogrify_info,*images,exception);
8117            break;
8118          }
8119        break;
8120      }
8121      case 'e':
8122      {
8123        if (LocaleCompare("evaluate-sequence",option+1) == 0)
8124          {
8125            Image
8126              *evaluate_image;
8127
8128            MagickEvaluateOperator
8129              op;
8130
8131            (void) SyncImageSettings(mogrify_info,*images,exception);
8132            op=(MagickEvaluateOperator) ParseCommandOption(
8133              MagickEvaluateOptions,MagickFalse,argv[i+1]);
8134            evaluate_image=EvaluateImages(*images,op,exception);
8135            if (evaluate_image == (Image *) NULL)
8136              {
8137                status=MagickFalse;
8138                break;
8139              }
8140            *images=DestroyImageList(*images);
8141            *images=evaluate_image;
8142            break;
8143          }
8144        break;
8145      }
8146      case 'f':
8147      {
8148        if (LocaleCompare("fft",option+1) == 0)
8149          {
8150            Image
8151              *fourier_image;
8152
8153            /*
8154              Implements the discrete Fourier transform (DFT).
8155            */
8156            (void) SyncImageSettings(mogrify_info,*images,exception);
8157            fourier_image=ForwardFourierTransformImage(*images,*option == '-' ?
8158              MagickTrue : MagickFalse,exception);
8159            if (fourier_image == (Image *) NULL)
8160              break;
8161            *images=DestroyImage(*images);
8162            *images=fourier_image;
8163            break;
8164          }
8165        if (LocaleCompare("flatten",option+1) == 0)
8166          {
8167            Image
8168              *flatten_image;
8169
8170            (void) SyncImagesSettings(mogrify_info,*images,exception);
8171            flatten_image=MergeImageLayers(*images,FlattenLayer,exception);
8172            if (flatten_image == (Image *) NULL)
8173              break;
8174            *images=DestroyImageList(*images);
8175            *images=flatten_image;
8176            break;
8177          }
8178        if (LocaleCompare("fx",option+1) == 0)
8179          {
8180            Image
8181              *fx_image;
8182
8183            (void) SyncImagesSettings(mogrify_info,*images,exception);
8184            fx_image=FxImage(*images,argv[i+1],exception);
8185            if (fx_image == (Image *) NULL)
8186              {
8187                status=MagickFalse;
8188                break;
8189              }
8190            *images=DestroyImageList(*images);
8191            *images=fx_image;
8192            break;
8193          }
8194        break;
8195      }
8196      case 'h':
8197      {
8198        if (LocaleCompare("hald-clut",option+1) == 0)
8199          {
8200            Image
8201              *hald_image,
8202              *image;
8203
8204            (void) SyncImagesSettings(mogrify_info,*images,exception);
8205            image=RemoveFirstImageFromList(images);
8206            hald_image=RemoveFirstImageFromList(images);
8207            if (hald_image == (Image *) NULL)
8208              {
8209                status=MagickFalse;
8210                break;
8211              }
8212            (void) HaldClutImage(image,hald_image,exception);
8213            hald_image=DestroyImage(hald_image);
8214            if (*images != (Image *) NULL)
8215              *images=DestroyImageList(*images);
8216            *images=image;
8217            break;
8218          }
8219        break;
8220      }
8221      case 'i':
8222      {
8223        if (LocaleCompare("ift",option+1) == 0)
8224          {
8225            Image
8226              *fourier_image,
8227              *magnitude_image,
8228              *phase_image;
8229
8230            /*
8231              Implements the inverse fourier discrete Fourier transform (DFT).
8232            */
8233            (void) SyncImagesSettings(mogrify_info,*images,exception);
8234            magnitude_image=RemoveFirstImageFromList(images);
8235            phase_image=RemoveFirstImageFromList(images);
8236            if (phase_image == (Image *) NULL)
8237              {
8238                status=MagickFalse;
8239                break;
8240              }
8241            fourier_image=InverseFourierTransformImage(magnitude_image,
8242              phase_image,*option == '-' ? MagickTrue : MagickFalse,exception);
8243            if (fourier_image == (Image *) NULL)
8244              break;
8245            if (*images != (Image *) NULL)
8246              *images=DestroyImage(*images);
8247            *images=fourier_image;
8248            break;
8249          }
8250        if (LocaleCompare("insert",option+1) == 0)
8251          {
8252            Image
8253              *p,
8254              *q;
8255
8256            index=0;
8257            if (*option != '+')
8258              index=(ssize_t) StringToLong(argv[i+1]);
8259            p=RemoveLastImageFromList(images);
8260            if (p == (Image *) NULL)
8261              {
8262                (void) ThrowMagickException(exception,GetMagickModule(),
8263                  OptionError,"NoSuchImage","`%s'",argv[i+1]);
8264                status=MagickFalse;
8265                break;
8266              }
8267            q=p;
8268            if (index == 0)
8269              PrependImageToList(images,q);
8270            else
8271              if (index == (ssize_t) GetImageListLength(*images))
8272                AppendImageToList(images,q);
8273              else
8274                {
8275                   q=GetImageFromList(*images,index-1);
8276                   if (q == (Image *) NULL)
8277                     {
8278                       (void) ThrowMagickException(exception,GetMagickModule(),
8279                         OptionError,"NoSuchImage","`%s'",argv[i+1]);
8280                       status=MagickFalse;
8281                       break;
8282                     }
8283                  InsertImageInList(&q,p);
8284                }
8285            *images=GetFirstImageInList(q);
8286            break;
8287          }
8288        if (LocaleCompare("interpolate",option+1) == 0)
8289          {
8290            interpolate_method=(PixelInterpolateMethod) ParseCommandOption(
8291              MagickInterpolateOptions,MagickFalse,argv[i+1]);
8292            break;
8293          }
8294        break;
8295      }
8296      case 'l':
8297      {
8298        if (LocaleCompare("layers",option+1) == 0)
8299          {
8300            Image
8301              *layers;
8302
8303            LayerMethod
8304              method;
8305
8306            (void) SyncImagesSettings(mogrify_info,*images,exception);
8307            layers=(Image *) NULL;
8308            method=(LayerMethod) ParseCommandOption(MagickLayerOptions,
8309              MagickFalse,argv[i+1]);
8310            switch (method)
8311            {
8312              case CoalesceLayer:
8313              {
8314                layers=CoalesceImages(*images,exception);
8315                break;
8316              }
8317              case CompareAnyLayer:
8318              case CompareClearLayer:
8319              case CompareOverlayLayer:
8320              default:
8321              {
8322                layers=CompareImagesLayers(*images,method,exception);
8323                break;
8324              }
8325              case MergeLayer:
8326              case FlattenLayer:
8327              case MosaicLayer:
8328              case TrimBoundsLayer:
8329              {
8330                layers=MergeImageLayers(*images,method,exception);
8331                break;
8332              }
8333              case DisposeLayer:
8334              {
8335                layers=DisposeImages(*images,exception);
8336                break;
8337              }
8338              case OptimizeImageLayer:
8339              {
8340                layers=OptimizeImageLayers(*images,exception);
8341                break;
8342              }
8343              case OptimizePlusLayer:
8344              {
8345                layers=OptimizePlusImageLayers(*images,exception);
8346                break;
8347              }
8348              case OptimizeTransLayer:
8349              {
8350                OptimizeImageTransparency(*images,exception);
8351                break;
8352              }
8353              case RemoveDupsLayer:
8354              {
8355                RemoveDuplicateLayers(images,exception);
8356                break;
8357              }
8358              case RemoveZeroLayer:
8359              {
8360                RemoveZeroDelayLayers(images,exception);
8361                break;
8362              }
8363              case OptimizeLayer:
8364              {
8365                /*
8366                  General Purpose, GIF Animation Optimizer.
8367                */
8368                layers=CoalesceImages(*images,exception);
8369                if (layers == (Image *) NULL)
8370                  {
8371                    status=MagickFalse;
8372                    break;
8373                  }
8374                *images=DestroyImageList(*images);
8375                *images=layers;
8376                layers=OptimizeImageLayers(*images,exception);
8377                if (layers == (Image *) NULL)
8378                  {
8379                    status=MagickFalse;
8380                    break;
8381                  }
8382                *images=DestroyImageList(*images);
8383                *images=layers;
8384                layers=(Image *) NULL;
8385                OptimizeImageTransparency(*images,exception);
8386                (void) RemapImages(quantize_info,*images,(Image *) NULL,
8387                  exception);
8388                break;
8389              }
8390              case CompositeLayer:
8391              {
8392                CompositeOperator
8393                  compose;
8394
8395                Image
8396                  *source;
8397
8398                RectangleInfo
8399                  geometry;
8400
8401                /*
8402                  Split image sequence at the first 'NULL:' image.
8403                */
8404                source=(*images);
8405                while (source != (Image *) NULL)
8406                {
8407                  source=GetNextImageInList(source);
8408                  if ((source != (Image *) NULL) &&
8409                      (LocaleCompare(source->magick,"NULL") == 0))
8410                    break;
8411                }
8412                if (source != (Image *) NULL)
8413                  {
8414                    if ((GetPreviousImageInList(source) == (Image *) NULL) ||
8415                        (GetNextImageInList(source) == (Image *) NULL))
8416                      source=(Image *) NULL;
8417                    else
8418                      {
8419                        /*
8420                          Separate the two lists, junk the null: image.
8421                        */
8422                        source=SplitImageList(source->previous);
8423                        DeleteImageFromList(&source);
8424                      }
8425                  }
8426                if (source == (Image *) NULL)
8427                  {
8428                    (void) ThrowMagickException(exception,GetMagickModule(),
8429                      OptionError,"MissingNullSeparator","layers Composite");
8430                    status=MagickFalse;
8431                    break;
8432                  }
8433                /*
8434                  Adjust offset with gravity and virtual canvas.
8435                */
8436                SetGeometry(*images,&geometry);
8437                (void) ParseAbsoluteGeometry((*images)->geometry,&geometry);
8438                geometry.width=source->page.width != 0 ?
8439                  source->page.width : source->columns;
8440                geometry.height=source->page.height != 0 ?
8441                 source->page.height : source->rows;
8442                GravityAdjustGeometry((*images)->page.width != 0 ?
8443                  (*images)->page.width : (*images)->columns,
8444                  (*images)->page.height != 0 ? (*images)->page.height :
8445                  (*images)->rows,(*images)->gravity,&geometry);
8446                compose=OverCompositeOp;
8447                option=GetImageOption(mogrify_info,"compose");
8448                if (option != (const char *) NULL)
8449                  compose=(CompositeOperator) ParseCommandOption(
8450                    MagickComposeOptions,MagickFalse,option);
8451                CompositeLayers(*images,compose,source,geometry.x,geometry.y,
8452                  exception);
8453                source=DestroyImageList(source);
8454                break;
8455              }
8456            }
8457            if (layers == (Image *) NULL)
8458              break;
8459            *images=DestroyImageList(*images);
8460            *images=layers;
8461            break;
8462          }
8463        break;
8464      }
8465      case 'm':
8466      {
8467        if (LocaleCompare("map",option+1) == 0)
8468          {
8469            (void) SyncImagesSettings(mogrify_info,*images,exception);
8470            if (*option == '+')
8471              {
8472                (void) RemapImages(quantize_info,*images,(Image *) NULL,
8473                  exception);
8474                break;
8475              }
8476            i++;
8477            break;
8478          }
8479        if (LocaleCompare("maximum",option+1) == 0)
8480          {
8481            Image
8482              *maximum_image;
8483
8484            /*
8485              Maximum image sequence (deprecated).
8486            */
8487            (void) SyncImagesSettings(mogrify_info,*images,exception);
8488            maximum_image=EvaluateImages(*images,MaxEvaluateOperator,exception);
8489            if (maximum_image == (Image *) NULL)
8490              {
8491                status=MagickFalse;
8492                break;
8493              }
8494            *images=DestroyImageList(*images);
8495            *images=maximum_image;
8496            break;
8497          }
8498        if (LocaleCompare("minimum",option+1) == 0)
8499          {
8500            Image
8501              *minimum_image;
8502
8503            /*
8504              Minimum image sequence (deprecated).
8505            */
8506            (void) SyncImagesSettings(mogrify_info,*images,exception);
8507            minimum_image=EvaluateImages(*images,MinEvaluateOperator,exception);
8508            if (minimum_image == (Image *) NULL)
8509              {
8510                status=MagickFalse;
8511                break;
8512              }
8513            *images=DestroyImageList(*images);
8514            *images=minimum_image;
8515            break;
8516          }
8517        if (LocaleCompare("morph",option+1) == 0)
8518          {
8519            Image
8520              *morph_image;
8521
8522            (void) SyncImagesSettings(mogrify_info,*images,exception);
8523            morph_image=MorphImages(*images,StringToUnsignedLong(argv[i+1]),
8524              exception);
8525            if (morph_image == (Image *) NULL)
8526              {
8527                status=MagickFalse;
8528                break;
8529              }
8530            *images=DestroyImageList(*images);
8531            *images=morph_image;
8532            break;
8533          }
8534        if (LocaleCompare("mosaic",option+1) == 0)
8535          {
8536            Image
8537              *mosaic_image;
8538
8539            (void) SyncImagesSettings(mogrify_info,*images,exception);
8540            mosaic_image=MergeImageLayers(*images,MosaicLayer,exception);
8541            if (mosaic_image == (Image *) NULL)
8542              {
8543                status=MagickFalse;
8544                break;
8545              }
8546            *images=DestroyImageList(*images);
8547            *images=mosaic_image;
8548            break;
8549          }
8550        break;
8551      }
8552      case 'p':
8553      {
8554        if (LocaleCompare("poly",option+1) == 0)
8555          {
8556            char
8557              *args,
8558              token[MagickPathExtent];
8559
8560            const char
8561              *p;
8562
8563            double
8564              *arguments;
8565
8566            Image
8567              *polynomial_image;
8568
8569            register ssize_t
8570              x;
8571
8572            size_t
8573              number_arguments;
8574
8575            /*
8576              Polynomial image.
8577            */
8578            (void) SyncImageSettings(mogrify_info,*images,exception);
8579            args=InterpretImageProperties(mogrify_info,*images,argv[i+1],
8580              exception);
8581            if (args == (char *) NULL)
8582              break;
8583            p=(char *) args;
8584            for (x=0; *p != '\0'; x++)
8585            {
8586              GetNextToken(p,&p,MagickPathExtent,token);
8587              if (*token == ',')
8588                GetNextToken(p,&p,MagickPathExtent,token);
8589            }
8590            number_arguments=(size_t) x;
8591            arguments=(double *) AcquireQuantumMemory(number_arguments,
8592              sizeof(*arguments));
8593            if (arguments == (double *) NULL)
8594              ThrowWandFatalException(ResourceLimitFatalError,
8595                "MemoryAllocationFailed",(*images)->filename);
8596            (void) ResetMagickMemory(arguments,0,number_arguments*
8597              sizeof(*arguments));
8598            p=(char *) args;
8599            for (x=0; (x < (ssize_t) number_arguments) && (*p != '\0'); x++)
8600            {
8601              GetNextToken(p,&p,MagickPathExtent,token);
8602              if (*token == ',')
8603                GetNextToken(p,&p,MagickPathExtent,token);
8604              arguments[x]=StringToDouble(token,(char **) NULL);
8605            }
8606            args=DestroyString(args);
8607            polynomial_image=PolynomialImage(*images,number_arguments >> 1,
8608              arguments,exception);
8609            arguments=(double *) RelinquishMagickMemory(arguments);
8610            if (polynomial_image == (Image *) NULL)
8611              {
8612                status=MagickFalse;
8613                break;
8614              }
8615            *images=DestroyImageList(*images);
8616            *images=polynomial_image;
8617          }
8618        if (LocaleCompare("print",option+1) == 0)
8619          {
8620            char
8621              *string;
8622
8623            (void) SyncImagesSettings(mogrify_info,*images,exception);
8624            string=InterpretImageProperties(mogrify_info,*images,argv[i+1],
8625              exception);
8626            if (string == (char *) NULL)
8627              break;
8628            (void) FormatLocaleFile(stdout,"%s",string);
8629            string=DestroyString(string);
8630          }
8631        if (LocaleCompare("process",option+1) == 0)
8632          {
8633            char
8634              **arguments;
8635
8636            int
8637              j,
8638              number_arguments;
8639
8640            (void) SyncImagesSettings(mogrify_info,*images,exception);
8641            arguments=StringToArgv(argv[i+1],&number_arguments);
8642            if (arguments == (char **) NULL)
8643              break;
8644            if ((argc > 1) && (strchr(arguments[1],'=') != (char *) NULL))
8645              {
8646                char
8647                  breaker,
8648                  quote,
8649                  *token;
8650
8651                const char
8652                  *argument;
8653
8654                int
8655                  next,
8656                  token_status;
8657
8658                size_t
8659                  length;
8660
8661                TokenInfo
8662                  *token_info;
8663
8664                /*
8665                  Support old style syntax, filter="-option arg".
8666                */
8667                length=strlen(argv[i+1]);
8668                token=(char *) NULL;
8669                if (~length >= (MagickPathExtent-1))
8670                  token=(char *) AcquireQuantumMemory(length+MagickPathExtent,
8671                    sizeof(*token));
8672                if (token == (char *) NULL)
8673                  break;
8674                next=0;
8675                argument=argv[i+1];
8676                token_info=AcquireTokenInfo();
8677                token_status=Tokenizer(token_info,0,token,length,argument,"",
8678                  "=","\"",'\0',&breaker,&next,&quote);
8679                token_info=DestroyTokenInfo(token_info);
8680                if (token_status == 0)
8681                  {
8682                    const char
8683                      *arg;
8684
8685                    arg=(&(argument[next]));
8686                    (void) InvokeDynamicImageFilter(token,&(*images),1,&arg,
8687                      exception);
8688                  }
8689                token=DestroyString(token);
8690                break;
8691              }
8692            (void) SubstituteString(&arguments[1],"-","");
8693            (void) InvokeDynamicImageFilter(arguments[1],&(*images),
8694              number_arguments-2,(const char **) arguments+2,exception);
8695            for (j=0; j < number_arguments; j++)
8696              arguments[j]=DestroyString(arguments[j]);
8697            arguments=(char **) RelinquishMagickMemory(arguments);
8698            break;
8699          }
8700        break;
8701      }
8702      case 'r':
8703      {
8704        if (LocaleCompare("reverse",option+1) == 0)
8705          {
8706            ReverseImageList(images);
8707            break;
8708          }
8709        break;
8710      }
8711      case 's':
8712      {
8713        if (LocaleCompare("smush",option+1) == 0)
8714          {
8715            Image
8716              *smush_image;
8717
8718            ssize_t
8719              offset;
8720
8721            (void) SyncImagesSettings(mogrify_info,*images,exception);
8722            offset=(ssize_t) StringToLong(argv[i+1]);
8723            smush_image=SmushImages(*images,*option == '-' ? MagickTrue :
8724              MagickFalse,offset,exception);
8725            if (smush_image == (Image *) NULL)
8726              {
8727                status=MagickFalse;
8728                break;
8729              }
8730            *images=DestroyImageList(*images);
8731            *images=smush_image;
8732            break;
8733          }
8734        if (LocaleCompare("swap",option+1) == 0)
8735          {
8736            Image
8737              *p,
8738              *q,
8739              *swap;
8740
8741            ssize_t
8742              swap_index;
8743
8744            index=(-1);
8745            swap_index=(-2);
8746            if (*option != '+')
8747              {
8748                GeometryInfo
8749                  geometry_info;
8750
8751                MagickStatusType
8752                  flags;
8753
8754                swap_index=(-1);
8755                flags=ParseGeometry(argv[i+1],&geometry_info);
8756                index=(ssize_t) geometry_info.rho;
8757                if ((flags & SigmaValue) != 0)
8758                  swap_index=(ssize_t) geometry_info.sigma;
8759              }
8760            p=GetImageFromList(*images,index);
8761            q=GetImageFromList(*images,swap_index);
8762            if ((p == (Image *) NULL) || (q == (Image *) NULL))
8763              {
8764                (void) ThrowMagickException(exception,GetMagickModule(),
8765                  OptionError,"NoSuchImage","`%s'",(*images)->filename);
8766                status=MagickFalse;
8767                break;
8768              }
8769            if (p == q)
8770              break;
8771            swap=CloneImage(p,0,0,MagickTrue,exception);
8772            ReplaceImageInList(&p,CloneImage(q,0,0,MagickTrue,exception));
8773            ReplaceImageInList(&q,swap);
8774            *images=GetFirstImageInList(q);
8775            break;
8776          }
8777        break;
8778      }
8779      case 'w':
8780      {
8781        if (LocaleCompare("write",option+1) == 0)
8782          {
8783            char
8784              key[MagickPathExtent];
8785
8786            Image
8787              *write_images;
8788
8789            ImageInfo
8790              *write_info;
8791
8792            (void) SyncImagesSettings(mogrify_info,*images,exception);
8793            (void) FormatLocaleString(key,MagickPathExtent,"cache:%s",
8794              argv[i+1]);
8795            (void) DeleteImageRegistry(key);
8796            write_images=(*images);
8797            if (*option == '+')
8798              write_images=CloneImageList(*images,exception);
8799            write_info=CloneImageInfo(mogrify_info);
8800            status&=WriteImages(write_info,write_images,argv[i+1],exception);
8801            write_info=DestroyImageInfo(write_info);
8802            if (*option == '+')
8803              write_images=DestroyImageList(write_images);
8804            break;
8805          }
8806        break;
8807      }
8808      default:
8809        break;
8810    }
8811    i+=count;
8812  }
8813  quantize_info=DestroyQuantizeInfo(quantize_info);
8814  mogrify_info=DestroyImageInfo(mogrify_info);
8815  status&=MogrifyImageInfo(image_info,argc,argv,exception);
8816  return(status != 0 ? MagickTrue : MagickFalse);
8817}
8818
8819/*
8820%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8821%                                                                             %
8822%                                                                             %
8823%                                                                             %
8824+     M o g r i f y I m a g e s                                               %
8825%                                                                             %
8826%                                                                             %
8827%                                                                             %
8828%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
8829%
8830%  MogrifyImages() applies image processing options to a sequence of images as
8831%  prescribed by command line options.
8832%
8833%  The format of the MogrifyImage method is:
8834%
8835%      MagickBooleanType MogrifyImages(ImageInfo *image_info,
8836%        const MagickBooleanType post,const int argc,const char **argv,
8837%        Image **images,Exceptioninfo *exception)
8838%
8839%  A description of each parameter follows:
8840%
8841%    o image_info: the image info..
8842%
8843%    o post: If true, post process image list operators otherwise pre-process.
8844%
8845%    o argc: Specifies a pointer to an integer describing the number of
8846%      elements in the argument vector.
8847%
8848%    o argv: Specifies a pointer to a text array containing the command line
8849%      arguments.
8850%
8851%    o images: pointer to a pointer of the first image in image list.
8852%
8853%    o exception: return any errors or warnings in this structure.
8854%
8855*/
8856WandExport MagickBooleanType MogrifyImages(ImageInfo *image_info,
8857  const MagickBooleanType post,const int argc,const char **argv,
8858  Image **images,ExceptionInfo *exception)
8859{
8860#define MogrifyImageTag  "Mogrify/Image"
8861
8862  MagickStatusType
8863    status;
8864
8865  MagickBooleanType
8866    proceed;
8867
8868  size_t
8869    n;
8870
8871  register ssize_t
8872    i;
8873
8874  assert(image_info != (ImageInfo *) NULL);
8875  assert(image_info->signature == MagickCoreSignature);
8876  if (images == (Image **) NULL)
8877    return(MogrifyImage(image_info,argc,argv,images,exception));
8878  assert((*images)->previous == (Image *) NULL);
8879  assert((*images)->signature == MagickCoreSignature);
8880  if ((*images)->debug != MagickFalse)
8881    (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
8882      (*images)->filename);
8883  if ((argc <= 0) || (*argv == (char *) NULL))
8884    return(MagickTrue);
8885  (void) SetImageInfoProgressMonitor(image_info,(MagickProgressMonitor) NULL,
8886    (void *) NULL);
8887  status=MagickTrue;
8888#if 0
8889  (void) FormatLocaleFile(stderr, "mogrify start %s %d (%s)\n",argv[0],argc,
8890    post?"post":"pre");
8891#endif
8892  /*
8893    Pre-process multi-image sequence operators
8894  */
8895  if (post == MagickFalse)
8896    status&=MogrifyImageList(image_info,argc,argv,images,exception);
8897  /*
8898    For each image, process simple single image operators
8899  */
8900  i=0;
8901  n=GetImageListLength(*images);
8902  for ( ; ; )
8903  {
8904#if 0
8905  (void) FormatLocaleFile(stderr,"mogrify %ld of %ld\n",(long)
8906    GetImageIndexInList(*images),(long)GetImageListLength(*images));
8907#endif
8908    status&=MogrifyImage(image_info,argc,argv,images,exception);
8909    proceed=SetImageProgress(*images,MogrifyImageTag,(MagickOffsetType) i, n);
8910    if (proceed == MagickFalse)
8911      break;
8912    if ( (*images)->next == (Image *) NULL )
8913      break;
8914    *images=(*images)->next;
8915    i++;
8916  }
8917  assert( *images != (Image *) NULL );
8918#if 0
8919  (void) FormatLocaleFile(stderr,"mogrify end %ld of %ld\n",(long)
8920    GetImageIndexInList(*images),(long)GetImageListLength(*images));
8921#endif
8922  /*
8923    Post-process, multi-image sequence operators
8924  */
8925  *images=GetFirstImageInList(*images);
8926  if (post != MagickFalse)
8927    status&=MogrifyImageList(image_info,argc,argv,images,exception);
8928  return(status != 0 ? MagickTrue : MagickFalse);
8929}
8930