]> granicus.if.org Git - imagemagick/blob - wand/import.c
(no commit message)
[imagemagick] / wand / import.c
1 /*
2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3 %                                                                             %
4 %                                                                             %
5 %                                                                             %
6 %                 IIIII  M   M  PPPP    OOO   RRRR   TTTTT                    %
7 %                   I    MM MM  P   P  O   O  R   R    T                      %
8 %                   I    M M M  PPPP   O   O  RRRR     T                      %
9 %                   I    M   M  P      O   O  R R      T                      %
10 %                 IIIII  M   M  P       OOO   R  R     T                      %
11 %                                                                             %
12 %                                                                             %
13 %                       Import Image from X11 Screen                          %
14 %                                                                             %
15 %                           Software Design                                   %
16 %                             John Cristy                                     %
17 %                              July 1992                                      %
18 %                                                                             %
19 %                                                                             %
20 %  Copyright 1999-2009 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 import program to capture some or all of an X server screen and
37 %  save the image to a file.
38 %
39 */
40 \f
41 /*
42   Include declarations.
43 */
44 #include "wand/studio.h"
45 #include "wand/MagickWand.h"
46 #include "wand/mogrify-private.h"
47 #include "magick/xwindow-private.h"
48 \f
49 /*
50 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
51 %                                                                             %
52 %                                                                             %
53 %                                                                             %
54 +   I m p o r t I m a g e C o m m a n d                                       %
55 %                                                                             %
56 %                                                                             %
57 %                                                                             %
58 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
59 %
60 %  ImportImageCommand() reads an image from any visible window on an X server
61 %  and outputs it as an image file. You can capture a single window, the
62 %  entire screen, or any rectangular portion of the screen.  You can use the
63 %  display utility for redisplay, printing, editing, formatting, archiving,
64 %  image processing, etc. of the captured image.</dd>
65 %
66 %  The target window can be specified by id, name, or may be selected by
67 %  clicking the mouse in the desired window. If you press a button and then
68 %  drag, a rectangle will form which expands and contracts as the mouse moves.
69 %  To save the portion of the screen defined by the rectangle, just release
70 %  the button. The keyboard bell is rung once at the beginning of the screen
71 %  capture and twice when it completes.
72 %
73 %  The format of the ImportImageCommand method is:
74 %
75 %      MagickBooleanType ImportImageCommand(ImageInfo *image_info,int argc,
76 %        char **argv,char **metadata,ExceptionInfo *exception)
77 %
78 %  A description of each parameter follows:
79 %
80 %    o image_info: the image info.
81 %
82 %    o argc: the number of elements in the argument vector.
83 %
84 %    o argv: A text array containing the command line arguments.
85 %
86 %    o metadata: any metadata is returned here.
87 %
88 %    o exception: return any errors or warnings in this structure.
89 %
90 */
91
92 static MagickBooleanType ImportUsage(void)
93 {
94   const char
95     **p;
96
97   static const char
98     *miscellaneous[]=
99     {
100       "-debug events        display copious debugging information",
101       "-help                print program options",
102       "-list type           print a list of supported option arguments",
103       "-log format          format of debugging information",
104       "-version             print version information",
105       (char *) NULL
106     },
107     *operators[]=
108     {
109       "-annotate geometry text",
110       "                     annotate the image with text",
111       "-border              include image borders in the output image",
112       "-colors value        preferred number of colors in the image",
113       "-crop geometry       preferred size and location of the cropped image",
114       "-encipher filename   convert plain pixels to cipher pixels",
115       "-geometry geometry   preferred size or location of the image",
116       "-help                print program options",
117       "-monochrome          transform image to black and white",
118       "-negate              replace every pixel with its complementary color ",
119       "-repage geometry     size and location of an image canvas",
120       "-quantize colorspace reduce colors in this colorspace",
121       "-resize geometry     resize the image",
122       "-rotate degrees      apply Paeth rotation to the image",
123       "-strip               strip image of all profiles and comments",
124       "-thumbnail geometry  create a thumbnail of the image",
125       "-transparent color   make this color transparent within the image",
126       "-trim                trim image edges",
127       "-type type           image type",
128       (char *) NULL
129     },
130     *settings[]=
131     {
132       "-adjoin              join images into a single multi-image file",
133       "-channel type        apply option to select image channels",
134       "-colorspace type     alternate image colorspace",
135       "-comment string      annotate image with comment",
136       "-compress type       type of pixel compression when writing the image",
137       "-define format:option",
138       "                     define one or more image format options",
139       "-density geometry    horizontal and vertical density of the image",
140       "-depth value         image depth",
141       "-descend             obtain image by descending window hierarchy",
142       "-display server      X server to contact",
143       "-dispose method      layer disposal method",
144       "-dither method       apply error diffusion to image",
145       "-delay value         display the next image after pausing",
146       "-encipher filename   convert plain pixels to cipher pixels",
147       "-endian type         endianness (MSB or LSB) of the image",
148       "-encoding type       text encoding type",
149       "-filter type         use this filter when resizing an image",
150       "-format \"string\"     output formatted image characteristics",
151       "-frame               include window manager frame",
152       "-gravity direction   which direction to gravitate towards",
153       "-identify            identify the format and characteristics of the image",
154       "-interlace type      None, Line, Plane, or Partition",
155       "-interpolate method  pixel color interpolation method",
156       "-label string        assign a label to an image",
157       "-limit type value    Area, Disk, Map, or Memory resource limit",
158       "-monitor             monitor progress",
159       "-page geometry       size and location of an image canvas",
160       "-pause value         seconds delay between snapshots",
161       "-pointsize value     font point size",
162       "-quality value       JPEG/MIFF/PNG compression level",
163       "-quiet               suppress all warning messages",
164       "-regard-warnings     pay attention to warning messages",
165       "-respect-parentheses settings remain in effect until parenthesis boundary",
166       "-sampling-factor geometry",
167       "                     horizontal and vertical sampling factor",
168       "-scene value         image scene number",
169       "-screen              select image from root window",
170       "-seed value          seed a new sequence of pseudo-random numbers",
171       "-set property value  set an image property",
172       "-silent              operate silently, i.e. don't ring any bells ",
173       "-snaps value         number of screen snapshots",
174       "-transparent-color color",
175       "                     transparent color",
176       "-treedepth value     color tree depth",
177       "-verbose             print detailed information about the image",
178       "-virtual-pixel method",
179       "                     Constant, Edge, Mirror, or Tile",
180       "-window id           select window with this id or name",
181       (char *) NULL
182     };
183
184   (void) printf("Version: %s\n",GetMagickVersion((unsigned long *) NULL));
185   (void) printf("Copyright: %s\n",GetMagickCopyright());
186   (void) printf("Features: %s\n\n",GetMagickFeatures());
187   (void) printf("Usage: %s [options ...] [ file ]\n",
188     GetClientName());
189   (void) printf("\nImage Settings:\n");
190   for (p=settings; *p != (char *) NULL; p++)
191     (void) printf("  %s\n",*p);
192   (void) printf("\nImage Operators:\n");
193   for (p=operators; *p != (char *) NULL; p++)
194     (void) printf("  %s\n",*p);
195   (void) printf("\nMiscellaneous Options:\n");
196   for (p=miscellaneous; *p != (char *) NULL; p++)
197     (void) printf("  %s\n",*p);
198   (void) printf(
199   "\nBy default, 'file' is written in the MIFF image format.  To\n");
200   (void) printf(
201     "specify a particular image format, precede the filename with an image\n");
202   (void) printf(
203     "format name and a colon (i.e. ps:image) or specify the image type as\n");
204   (void) printf(
205     "the filename suffix (i.e. image.ps).  Specify 'file' as '-' for\n");
206   (void) printf("standard input or output.\n");
207   return(MagickFalse);
208 }
209
210 static inline long MagickMax(const long x,const long y)
211 {
212   if (x > y)
213     return(x);
214   return(y);
215 }
216
217 WandExport MagickBooleanType ImportImageCommand(ImageInfo *image_info,
218   int argc,char **argv,char **wand_unused(metadata),ExceptionInfo *exception)
219 {
220 #if defined(MAGICKCORE_X11_DELEGATE)
221 #define DestroyImport() \
222 { \
223   XDestroyResourceInfo(&resource_info); \
224   if (display != (Display *) NULL) \
225     { \
226       XCloseDisplay(display); \
227       display=(Display *) NULL; \
228     } \
229   DestroyImageStack(); \
230   if (target_window != (char *) NULL) \
231     target_window=DestroyString(target_window); \
232   for (i=0; i < (long) argc; i++) \
233     argv[i]=DestroyString(argv[i]); \
234   argv=(char **) RelinquishMagickMemory(argv); \
235 }
236 #define ThrowImportException(asperity,tag,option) \
237 { \
238   (void) ThrowMagickException(exception,GetMagickModule(),asperity,tag,"`%s'", \
239      option); \
240   DestroyImport(); \
241   return(MagickFalse); \
242 }
243 #define ThrowImportInvalidArgumentException(option,argument) \
244 { \
245   (void) ThrowMagickException(exception,GetMagickModule(),OptionError, \
246     "InvalidArgument","`%s': %s",option,argument); \
247   DestroyImport(); \
248   return(MagickFalse); \
249 }
250
251   char
252     *filename,
253     *option,
254     *resource_value,
255     *server_name,
256     *target_window;
257
258   Display
259     *display;
260
261   Image
262     *image;
263
264   ImageStack
265     image_stack[MaxImageStackDepth+1];
266
267   long
268     j,
269     k,
270     snapshots;
271
272   MagickBooleanType
273     fire,
274     pend;
275
276   MagickStatusType
277     status;
278
279   QuantizeInfo
280     *quantize_info;
281
282   register long
283     i;
284
285   XImportInfo
286     ximage_info;
287
288   XResourceInfo
289     resource_info;
290
291   XrmDatabase
292     resource_database;
293
294   /*
295     Set defaults.
296   */
297   assert(image_info != (ImageInfo *) NULL);
298   assert(image_info->signature == MagickSignature);
299   if (image_info->debug != MagickFalse)
300     (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
301   assert(exception != (ExceptionInfo *) NULL);
302   if (argc == 2)
303     {
304       option=argv[1];
305       if ((LocaleCompare("version",option+1) == 0) ||
306           (LocaleCompare("-version",option+1) == 0))
307         {
308           (void) fprintf(stdout,"Version: %s\n",
309             GetMagickVersion((unsigned long *) NULL));
310           (void) fprintf(stdout,"Copyright: %s\n\n",GetMagickCopyright());
311           return(MagickFalse);
312         }
313     }
314   display=(Display *) NULL;
315   j=1;
316   k=0;
317   NewImageStack();
318   option=(char *) NULL;
319   pend=MagickFalse;
320   resource_database=(XrmDatabase) NULL;
321   (void) ResetMagickMemory(&resource_info,0,sizeof(resource_info));
322   server_name=(char *) NULL;
323   status=MagickTrue;
324   SetNotifyHandlers;
325   target_window=(char *) NULL;
326   /*
327     Check for server name specified on the command line.
328   */
329   ReadCommandlLine(argc,&argv);
330   status=ExpandFilenames(&argc,&argv);
331   if (status == MagickFalse)
332     ThrowImportException(ResourceLimitError,"MemoryAllocationFailed",
333       GetExceptionMessage(errno));
334   for (i=1; i < (long) argc; i++)
335   {
336     /*
337       Check command line for server name.
338     */
339     option=argv[i];
340     if (LocaleCompare("display",option+1) == 0)
341       {
342         /*
343           User specified server name.
344         */
345         i++;
346         if (i == (long) argc)
347           ThrowImportException(OptionError,"MissingArgument",option);
348         server_name=argv[i];
349       }
350     if ((LocaleCompare("help",option+1) == 0) ||
351         (LocaleCompare("-help",option+1) == 0))
352       return(ImportUsage());
353   }
354   /*
355     Get user defaults from X resource database.
356   */
357   display=XOpenDisplay(server_name);
358   if (display == (Display *) NULL)
359     ThrowImportException(XServerError,"UnableToOpenXServer",
360       XDisplayName(server_name));
361   (void) XSetErrorHandler(XError);
362   resource_database=XGetResourceDatabase(display,GetClientName());
363   XGetImportInfo(&ximage_info);
364   XGetResourceInfo(image_info,resource_database,GetClientName(),
365     &resource_info);
366   quantize_info=resource_info.quantize_info;
367   resource_value=XGetResourceInstance(resource_database,GetClientName(),
368     "border","False");
369   ximage_info.borders=IsMagickTrue(resource_value);
370   resource_value=XGetResourceInstance(resource_database,GetClientName(),
371     "delay","0");
372   resource_info.delay=(unsigned int) atoi(resource_value);
373   image_info->density=XGetResourceInstance(resource_database,GetClientName(),
374     "density",(char *) NULL);
375   resource_value=XGetResourceInstance(resource_database,GetClientName(),
376     "descend","True");
377   ximage_info.descend=IsMagickTrue(resource_value);
378   resource_value=XGetResourceInstance(resource_database,GetClientName(),
379     "frame","False");
380   ximage_info.frame=IsMagickTrue(resource_value);
381   resource_value=XGetResourceInstance(resource_database,GetClientName(),
382     "interlace","none");
383   image_info->interlace=UndefinedInterlace;
384   if (LocaleCompare("None",resource_value) == 0)
385     image_info->interlace=NoInterlace;
386   if (LocaleCompare("Line",resource_value) == 0)
387     image_info->interlace=LineInterlace;
388   if (LocaleCompare("Plane",resource_value) == 0)
389     image_info->interlace=PlaneInterlace;
390   if (LocaleCompare("Partition",resource_value) == 0)
391     image_info->interlace=PartitionInterlace;
392   if (image_info->interlace == UndefinedInterlace)
393     ThrowImportException(OptionError,"Unrecognized interlace type",
394       resource_value);
395   image_info->page=XGetResourceInstance(resource_database,GetClientName(),
396     "pageGeometry",(char *) NULL);
397   resource_value=XGetResourceInstance(resource_database,GetClientName(),
398     "pause","0");
399   resource_info.pause=(unsigned int) atol(resource_value);
400   resource_value=XGetResourceInstance(resource_database,GetClientName(),
401     "quality","85");
402   image_info->quality=(unsigned long) atol(resource_value);
403   resource_value=XGetResourceInstance(resource_database,GetClientName(),
404     "screen","False");
405   ximage_info.screen=IsMagickTrue(resource_value);
406   resource_value=XGetResourceInstance(resource_database,GetClientName(),
407     "silent","False");
408   ximage_info.silent=IsMagickTrue(resource_value);
409   resource_value=XGetResourceInstance(resource_database,GetClientName(),
410     "verbose","False");
411   image_info->verbose=IsMagickTrue(resource_value);
412   resource_value=XGetResourceInstance(resource_database,GetClientName(),
413     "dither","True");
414   quantize_info->dither=IsMagickTrue(resource_value);
415   snapshots=1;
416   status=MagickTrue;
417   filename=(char *) NULL;
418   /*
419     Check command syntax.
420   */
421   for (i=1; i < (long) argc; i++)
422   {
423     option=argv[i];
424     if (LocaleCompare(option,"(") == 0)
425       {
426         FireImageStack(MagickFalse,MagickTrue,pend);
427         if (k == MaxImageStackDepth)
428           ThrowImportException(OptionError,"ParenthesisNestedTooDeeply",
429             option);
430         PushImageStack();
431         continue;
432       }
433     if (LocaleCompare(option,")") == 0)
434       {
435         FireImageStack(MagickFalse,MagickTrue,MagickTrue);
436         if (k == 0)
437           ThrowImportException(OptionError,"UnableToParseExpression",option);
438         PopImageStack();
439         continue;
440       }
441     if (IsMagickOption(option) == MagickFalse)
442       {
443         Image
444           *images;
445
446         unsigned long
447           scene;
448
449         /*
450           Read image from X server.
451         */
452         FireImageStack(MagickFalse,MagickFalse,pend);
453         filename=argv[i];
454         if (target_window != (char *) NULL)
455           (void) CopyMagickString(image_info->filename,target_window,
456             MaxTextExtent);
457         for (scene=0; scene < (unsigned long) MagickMax(snapshots,1); scene++)
458         {
459           (void) sleep(resource_info.pause);
460           images=XImportImage(image_info,&ximage_info);
461           status&=(images != (Image *) NULL) &&
462             (exception->severity < ErrorException);
463           if (images == (Image *) NULL)
464             continue;
465           (void) CopyMagickString(images->filename,filename,MaxTextExtent);
466           (void) CopyMagickString(images->magick,"PS",MaxTextExtent);
467           images->scene=scene;
468           AppendImageStack(images);
469         }
470         continue;
471       }
472     pend=image != (Image *) NULL ? MagickTrue : MagickFalse;
473     switch(*(option+1))
474     {
475       case 'a':
476       {
477         if (LocaleCompare("adjoin",option+1) == 0)
478           break;
479         if (LocaleCompare("annotate",option+1) == 0)
480           {
481             if (*option == '+')
482               break;
483             i++;
484             if (i == (long) (argc-1))
485               ThrowImportException(OptionError,"MissingArgument",option);
486             if (IsGeometry(argv[i]) == MagickFalse)
487               ThrowImportInvalidArgumentException(option,argv[i]);
488             if (i == (long) (argc-1))
489               ThrowImportException(OptionError,"MissingArgument",option);
490             i++;
491             break;
492           }
493         ThrowImportException(OptionError,"UnrecognizedOption",option);
494       }
495       case 'b':
496       {
497         if (LocaleCompare("border",option+1) == 0)
498           {
499             (void) CopyMagickString(argv[i]+1,"sans",MaxTextExtent);
500             ximage_info.borders=(*option == '-') ? MagickTrue : MagickFalse;
501             break;
502           }
503         if (LocaleCompare("bordercolor",option+1) == 0)
504           {
505             if (*option == '+')
506               break;
507             i++;
508             if (i == (long) argc)
509               ThrowImportException(OptionError,"MissingArgument",option);
510             break;
511           }
512         ThrowImportException(OptionError,"UnrecognizedOption",option);
513       }
514       case 'c':
515       {
516         if (LocaleCompare("cache",option+1) == 0)
517           {
518             if (*option == '+')
519               break;
520             i++;
521             if (i == (long) argc)
522               ThrowImportException(OptionError,"MissingArgument",option);
523             if (IsGeometry(argv[i]) == MagickFalse)
524               ThrowImportInvalidArgumentException(option,argv[i]);
525             break;
526           }
527         if (LocaleCompare("channel",option+1) == 0)
528           {
529             long
530               channel;
531
532             if (*option == '+')
533               break;
534             i++;
535             if (i == (long) (argc-1))
536               ThrowImportException(OptionError,"MissingArgument",option);
537             channel=ParseChannelOption(argv[i]);
538             if (channel < 0)
539               ThrowImportException(OptionError,"UnrecognizedChannelType",
540                 argv[i]);
541             break;
542           }
543         if (LocaleCompare("colors",option+1) == 0)
544           {
545             quantize_info->number_colors=0;
546             if (*option == '+')
547               break;
548             i++;
549             if (i == (long) argc)
550               ThrowImportException(OptionError,"MissingArgument",option);
551             if (IsGeometry(argv[i]) == MagickFalse)
552               ThrowImportInvalidArgumentException(option,argv[i]);
553             quantize_info->number_colors=(unsigned long) atol(argv[i]);
554             break;
555           }
556         if (LocaleCompare("colorspace",option+1) == 0)
557           {
558             long
559               colorspace;
560
561             if (*option == '+')
562               break;
563             i++;
564             if (i == (long) argc)
565               ThrowImportException(OptionError,"MissingArgument",option);
566             colorspace=ParseMagickOption(MagickColorspaceOptions,MagickFalse,
567               argv[i]);
568             if (colorspace < 0)
569               ThrowImportException(OptionError,"UnrecognizedColorspace",
570                 argv[i]);
571             break;
572           }
573         if (LocaleCompare("comment",option+1) == 0)
574           {
575             if (*option == '+')
576               break;
577             i++;
578             if (i == (long) argc)
579               ThrowImportException(OptionError,"MissingArgument",option);
580             status=SetImageOption(image_info,"comment",argv[i]);
581             if (status == MagickFalse)
582               ThrowImportException(OptionError,"UnrecognizedOption",argv[i]);
583             break;
584           }
585         if (LocaleCompare("compress",option+1) == 0)
586           {
587             long
588               compress;
589
590             if (*option == '+')
591               break;
592             i++;
593             if (i == (long) argc)
594               ThrowImportException(OptionError,"MissingArgument",option);
595             compress=ParseMagickOption(MagickCompressOptions,MagickFalse,
596               argv[i]);
597             if (compress < 0)
598               ThrowImportException(OptionError,"UnrecognizedImageCompression",
599                 argv[i]);
600             break;
601           }
602         if (LocaleCompare("crop",option+1) == 0)
603           {
604             if (*option == '+')
605               break;
606             i++;
607             if (i == (long) argc)
608               ThrowImportException(OptionError,"MissingArgument",option);
609             if (IsGeometry(argv[i]) == MagickFalse)
610               ThrowImportInvalidArgumentException(option,argv[i]);
611             break;
612           }
613         ThrowImportException(OptionError,"UnrecognizedOption",option);
614       }
615       case 'd':
616       {
617         if (LocaleCompare("debug",option+1) == 0)
618           {
619             long
620               event;
621
622             if (*option == '+')
623               break;
624             i++;
625             if (i == (long) argc)
626               ThrowImportException(OptionError,"MissingArgument",option);
627             event=ParseMagickOption(MagickLogEventOptions,MagickFalse,argv[i]);
628             if (event < 0)
629               ThrowImportException(OptionError,"UnrecognizedEventType",argv[i]);
630             (void) SetLogEventMask(argv[i]);
631             break;
632           }
633         if (LocaleCompare("define",option+1) == 0)
634           {
635             i++;
636             if (i == (long) argc)
637               ThrowImportException(OptionError,"MissingArgument",option);
638             if (*option == '+')
639               {
640                 const char
641                   *define;
642
643                 define=GetImageOption(image_info,argv[i]);
644                 if (define == (char *) NULL)
645                   ThrowImportException(OptionError,"NoSuchOption",argv[i]);
646                 break;
647               }
648             break;
649           }
650         if (LocaleCompare("delay",option+1) == 0)
651           {
652             if (*option == '+')
653               break;
654             i++;
655             if (i == (long) argc)
656               ThrowImportException(OptionError,"MissingArgument",option);
657             if (IsGeometry(argv[i]) == MagickFalse)
658               ThrowImportInvalidArgumentException(option,argv[i]);
659             status=SetImageOption(image_info,"delay",argv[i]);
660             if (status == MagickFalse)
661               ThrowImportException(OptionError,"UnrecognizedOption",argv[i]);
662             break;
663           }
664         if (LocaleCompare("density",option+1) == 0)
665           {
666             if (*option == '+')
667               break;
668             i++;
669             if (i == (long) argc)
670               ThrowImportException(OptionError,"MissingArgument",option);
671             if (IsGeometry(argv[i]) == MagickFalse)
672               ThrowImportInvalidArgumentException(option,argv[i]);
673             break;
674           }
675         if (LocaleCompare("depth",option+1) == 0)
676           {
677             if (*option == '+')
678               break;
679             i++;
680             if (i == (long) argc)
681               ThrowImportException(OptionError,"MissingArgument",option);
682             if (IsGeometry(argv[i]) == MagickFalse)
683               ThrowImportInvalidArgumentException(option,argv[i]);
684             break;
685           }
686         if (LocaleCompare("descend",option+1) == 0)
687           {
688             ximage_info.descend=(*option == '-') ? MagickTrue : MagickFalse;
689             break;
690           }
691         if (LocaleCompare("display",option+1) == 0)
692           {
693             if (*option == '+')
694               break;
695             i++;
696             if (i == (long) argc)
697               ThrowImportException(OptionError,"MissingArgument",option);
698             break;
699           }
700         if (LocaleCompare("dispose",option+1) == 0)
701           {
702             long
703               dispose;
704
705             if (*option == '+')
706               break;
707             i++;
708             if (i == (long) argc)
709               ThrowImportException(OptionError,"MissingArgument",option);
710             dispose=ParseMagickOption(MagickDisposeOptions,MagickFalse,argv[i]);
711             if (dispose < 0)
712               ThrowImportException(OptionError,"UnrecognizedDisposeMethod",
713                 argv[i]);
714             break;
715           }
716         if (LocaleCompare("dither",option+1) == 0)
717           {
718             long
719               method;
720
721             quantize_info->dither=MagickFalse;
722             if (*option == '+')
723               break;
724             i++;
725             if (i == (long) argc)
726               ThrowImportException(OptionError,"MissingArgument",option);
727             method=ParseMagickOption(MagickDitherOptions,MagickFalse,argv[i]);
728             if (method < 0)
729               ThrowImportException(OptionError,"UnrecognizedDitherMethod",
730                 argv[i]);
731             quantize_info->dither=MagickTrue;
732             quantize_info->dither_method=(DitherMethod) method;
733             break;
734           }
735         ThrowImportException(OptionError,"UnrecognizedOption",option);
736       }
737       case 'e':
738       {
739         if (LocaleCompare("encipher",option+1) == 0)
740           {
741             if (*option == '+')
742               break;
743             i++;
744             if (i == (long) (argc-1))
745               ThrowImportException(OptionError,"MissingArgument",option);
746             break;
747           }
748         if (LocaleCompare("encoding",option+1) == 0)
749           {
750             if (*option == '+')
751               break;
752             i++;
753             if (i == (long) argc)
754               ThrowImportException(OptionError,"MissingArgument",option);
755             break;
756           }
757         if (LocaleCompare("endian",option+1) == 0)
758           {
759             long
760               endian;
761
762             if (*option == '+')
763               break;
764             i++;
765             if (i == (long) argc)
766               ThrowImportException(OptionError,"MissingArgument",option);
767             endian=ParseMagickOption(MagickEndianOptions,MagickFalse,
768               argv[i]);
769             if (endian < 0)
770               ThrowImportException(OptionError,"UnrecognizedEndianType",
771                 argv[i]);
772             break;
773           }
774         ThrowImportException(OptionError,"UnrecognizedOption",option);
775       }
776       case 'f':
777       {
778         if (LocaleCompare("filter",option+1) == 0)
779           {
780             long
781               filter;
782
783             if (*option == '+')
784               break;
785             i++;
786             if (i == (long) (argc-1))
787               ThrowImportException(OptionError,"MissingArgument",option);
788             filter=ParseMagickOption(MagickFilterOptions,MagickFalse,argv[i]);
789             if (filter < 0)
790               ThrowImportException(OptionError,"UnrecognizedImageFilter",
791                 argv[i]);
792             break;
793           }
794         if (LocaleCompare("frame",option+1) == 0)
795           {
796             (void) CopyMagickString(argv[i]+1,"sans0",MaxTextExtent);
797             ximage_info.frame=(*option == '-') ? MagickTrue : MagickFalse;
798             break;
799           }
800         if (LocaleCompare("format",option+1) == 0)
801           {
802             if (*option == '+')
803               break;
804             i++;
805             if (i == (long) (argc-1))
806               ThrowImportException(OptionError,"MissingArgument",option);
807             break;
808           }
809         ThrowImportException(OptionError,"UnrecognizedOption",option);
810       }
811       case 'g':
812       {
813         if (LocaleCompare("geometry",option+1) == 0)
814           {
815             if (*option == '+')
816               break;
817             i++;
818             if (i == (long) argc)
819               ThrowImportException(OptionError,"MissingArgument",option);
820             if (IsGeometry(argv[i]) == MagickFalse)
821               ThrowImportInvalidArgumentException(option,argv[i]);
822             break;
823           }
824         if (LocaleCompare("gravity",option+1) == 0)
825           {
826             long
827               gravity;
828
829             if (*option == '+')
830               break;
831             i++;
832             if (i == (long) argc)
833               ThrowImportException(OptionError,"MissingArgument",option);
834             gravity=ParseMagickOption(MagickGravityOptions,MagickFalse,argv[i]);
835             if (gravity < 0)
836               ThrowImportException(OptionError,"UnrecognizedGravityType",
837                 argv[i]);
838             break;
839           }
840         ThrowImportException(OptionError,"UnrecognizedOption",option);
841       }
842       case 'h':
843       {
844         if (LocaleCompare("help",option+1) == 0)
845           break;
846         ThrowImportException(OptionError,"UnrecognizedOption",option);
847       }
848       case 'i':
849       {
850         if (LocaleCompare("identify",option+1) == 0)
851           break;
852         if (LocaleCompare("interlace",option+1) == 0)
853           {
854             long
855               interlace;
856
857             if (*option == '+')
858               break;
859             i++;
860             if (i == (long) argc)
861               ThrowImportException(OptionError,"MissingArgument",option);
862             interlace=ParseMagickOption(MagickInterlaceOptions,MagickFalse,
863               argv[i]);
864             if (interlace < 0)
865               ThrowImportException(OptionError,"UnrecognizedInterlaceType",
866                 argv[i]);
867             break;
868           }
869         if (LocaleCompare("interpolate",option+1) == 0)
870           {
871             long
872               interpolate;
873
874             if (*option == '+')
875               break;
876             i++;
877             if (i == (long) argc)
878               ThrowImportException(OptionError,"MissingArgument",option);
879             interpolate=ParseMagickOption(MagickInterpolateOptions,MagickFalse,
880               argv[i]);
881             if (interpolate < 0)
882               ThrowImportException(OptionError,"UnrecognizedInterpolateMethod",
883                 argv[i]);
884             break;
885           }
886         ThrowImportException(OptionError,"UnrecognizedOption",option);
887       }
888       case 'l':
889       {
890         if (LocaleCompare("label",option+1) == 0)
891           {
892             if (*option == '+')
893               break;
894             i++;
895             if (i == (long) argc)
896               ThrowImportException(OptionError,"MissingArgument",option);
897             status=SetImageOption(image_info,"label",argv[i]);
898             if (status == MagickFalse)
899               ThrowImportException(OptionError,"UnrecognizedOption",argv[i]);
900             break;
901           }
902         if (LocaleCompare("limit",option+1) == 0)
903           {
904             char
905               *p;
906
907             double
908               value;
909
910             long
911               resource;
912
913             if (*option == '+')
914               break;
915             i++;
916             if (i == (long) argc)
917               ThrowImportException(OptionError,"MissingArgument",option);
918             resource=ParseMagickOption(MagickResourceOptions,MagickFalse,
919               argv[i]);
920             if (resource < 0)
921               ThrowImportException(OptionError,"UnrecognizedResourceType",
922                 argv[i]);
923             i++;
924             if (i == (long) argc)
925               ThrowImportException(OptionError,"MissingArgument",option);
926             value=strtod(argv[i],&p);
927             if ((p == argv[i]) && (LocaleCompare("unlimited",argv[i]) != 0))
928               ThrowImportInvalidArgumentException(option,argv[i]);
929             break;
930           }
931         if (LocaleCompare("list",option+1) == 0)
932           {
933             long
934               list;
935
936             if (*option == '+')
937               break;
938             i++;
939             if (i == (long) argc)
940               ThrowImportException(OptionError,"MissingArgument",option);
941             list=ParseMagickOption(MagickListOptions,MagickFalse,argv[i]);
942             if (list < 0)
943               ThrowImportException(OptionError,"UnrecognizedListType",argv[i]);
944             (void) MogrifyImageInfo(image_info,(int) (i-j+1),(const char **)
945               argv+j,exception);
946             DestroyImport();
947             return(MagickTrue);
948           }
949         if (LocaleCompare("log",option+1) == 0)
950           {
951             if (*option == '+')
952               break;
953             i++;
954             if ((i == (long) argc) || (strchr(argv[i],'%') == (char *) NULL))
955               ThrowImportException(OptionError,"MissingArgument",option);
956             break;
957           }
958         ThrowImportException(OptionError,"UnrecognizedOption",option);
959       }
960       case 'm':
961       {
962         if (LocaleCompare("monitor",option+1) == 0)
963           break;
964         if (LocaleCompare("monochrome",option+1) == 0)
965           {
966             if (*option == '+')
967               break;
968             quantize_info->number_colors=2;
969             quantize_info->colorspace=GRAYColorspace;
970             break;
971           }
972         ThrowImportException(OptionError,"UnrecognizedOption",option);
973       }
974       case 'n':
975       {
976         if (LocaleCompare("negate",option+1) == 0)
977           break;
978         ThrowImportException(OptionError,"UnrecognizedOption",option);
979       }
980       case 'p':
981       {
982         if (LocaleCompare("page",option+1) == 0)
983           {
984             if (*option == '+')
985               break;
986             i++;
987             if (i == (long) argc)
988               ThrowImportException(OptionError,"MissingArgument",option);
989             status=SetImageOption(image_info,"page",argv[i]);
990             if (status == MagickFalse)
991               ThrowImportException(OptionError,"UnrecognizedOption",argv[i]);
992             break;
993           }
994         if (LocaleCompare("pause",option+1) == 0)
995           {
996             resource_info.pause=0;
997             if (*option == '+')
998               break;
999             i++;
1000             if (i == (long) argc)
1001               ThrowImportException(OptionError,"MissingArgument",option);
1002             if (IsGeometry(argv[i]) == MagickFalse)
1003               ThrowImportInvalidArgumentException(option,argv[i]);
1004             resource_info.pause=(unsigned int) atoi(argv[i]);
1005             break;
1006           }
1007         if (LocaleCompare("ping",option+1) == 0)
1008           break;  /* deprecated option */
1009         if (LocaleCompare("pointsize",option+1) == 0)
1010           {
1011             if (*option == '+')
1012               break;
1013             i++;
1014             if (i == (long) argc)
1015               ThrowImportException(OptionError,"MissingArgument",option);
1016             if (IsGeometry(argv[i]) == MagickFalse)
1017               ThrowImportInvalidArgumentException(option,argv[i]);
1018             break;
1019           }
1020         ThrowImportException(OptionError,"UnrecognizedOption",option);
1021       }
1022       case 'q':
1023       {
1024         if (LocaleCompare("quality",option+1) == 0)
1025           {
1026             if (*option == '+')
1027               break;
1028             i++;
1029             if (i == (long) argc)
1030               ThrowImportException(OptionError,"MissingArgument",option);
1031             if (IsGeometry(argv[i]) == MagickFalse)
1032               ThrowImportInvalidArgumentException(option,argv[i]);
1033             break;
1034           }
1035         if (LocaleCompare("quantize",option+1) == 0)
1036           {
1037             long
1038               colorspace;
1039
1040             if (*option == '+')
1041               break;
1042             i++;
1043             if (i == (long) (argc-1))
1044               ThrowImportException(OptionError,"MissingArgument",option);
1045             colorspace=ParseMagickOption(MagickColorspaceOptions,
1046               MagickFalse,argv[i]);
1047             if (colorspace < 0)
1048               ThrowImportException(OptionError,"UnrecognizedColorspace",
1049                 argv[i]);
1050             break;
1051           }
1052         if (LocaleCompare("quiet",option+1) == 0)
1053           break;
1054         ThrowImportException(OptionError,"UnrecognizedOption",option);
1055       }
1056       case 'r':
1057       {
1058         if (LocaleCompare("regard-warnings",option+1) == 0)
1059           break;
1060         if (LocaleCompare("repage",option+1) == 0)
1061           {
1062             if (*option == '+')
1063               break;
1064             i++;
1065             if (i == (long) (argc-1))
1066               ThrowImportException(OptionError,"MissingArgument",option);
1067             if (IsGeometry(argv[i]) == MagickFalse)
1068               ThrowImportInvalidArgumentException(option,argv[i]);
1069             break;
1070           }
1071         if (LocaleCompare("resize",option+1) == 0)
1072           {
1073             if (*option == '+')
1074               break;
1075             i++;
1076             if (i == (long) argc)
1077               ThrowImportException(OptionError,"MissingArgument",option);
1078             if (IsGeometry(argv[i]) == MagickFalse)
1079               ThrowImportInvalidArgumentException(option,argv[i]);
1080             break;
1081           }
1082         if (LocaleNCompare("respect-parentheses",option+1,17) == 0)
1083           {
1084             respect_parenthesis=(*option == '-') ? MagickTrue : MagickFalse;
1085             break;
1086           }
1087         if (LocaleCompare("rotate",option+1) == 0)
1088           {
1089             i++;
1090             if (i == (long) argc)
1091               ThrowImportException(OptionError,"MissingArgument",option);
1092             if (IsGeometry(argv[i]) == MagickFalse)
1093               ThrowImportInvalidArgumentException(option,argv[i]);
1094             break;
1095           }
1096         ThrowImportException(OptionError,"UnrecognizedOption",option);
1097       }
1098       case 's':
1099       {
1100         if (LocaleCompare("sampling-factor",option+1) == 0)
1101           {
1102             if (*option == '+')
1103               break;
1104             i++;
1105             if (i == (long) argc)
1106               ThrowImportException(OptionError,"MissingArgument",option);
1107             if (IsGeometry(argv[i]) == MagickFalse)
1108               ThrowImportInvalidArgumentException(option,argv[i]);
1109             break;
1110           }
1111         if (LocaleCompare("scene",option+1) == 0)
1112           {
1113             if (*option == '+')
1114               break;
1115             i++;
1116             if (i == (long) argc)
1117               ThrowImportException(OptionError,"MissingArgument",option);
1118             if (IsGeometry(argv[i]) == MagickFalse)
1119               ThrowImportInvalidArgumentException(option,argv[i]);
1120             break;
1121           }
1122         if (LocaleCompare("set",option+1) == 0)
1123           {
1124             i++;
1125             if (i == (long) argc)
1126               ThrowImportException(OptionError,"MissingArgument",option);
1127             if (*option == '+')
1128               break;
1129             i++;
1130             if (i == (long) argc)
1131               ThrowImportException(OptionError,"MissingArgument",option);
1132             break;
1133           }
1134         if (LocaleCompare("screen",option+1) == 0)
1135           {
1136             ximage_info.screen=(*option == '-') ? MagickTrue : MagickFalse;
1137             break;
1138           }
1139         if (LocaleCompare("seed",option+1) == 0)
1140           {
1141             if (*option == '+')
1142               break;
1143             i++;
1144             if (i == (long) (argc-1))
1145               ThrowImportException(OptionError,"MissingArgument",option);
1146             if (IsGeometry(argv[i]) == MagickFalse)
1147               ThrowImportInvalidArgumentException(option,argv[i]);
1148             break;
1149           }
1150         if (LocaleCompare("silent",option+1) == 0)
1151           {
1152             ximage_info.silent=(*option == '-') ? MagickTrue : MagickFalse;
1153             break;
1154           }
1155         if (LocaleCompare("snaps",option+1) == 0)
1156           {
1157             (void) CopyMagickString(argv[i]+1,"sans",MaxTextExtent);
1158             i++;
1159             if (i == (long) argc)
1160               ThrowImportException(OptionError,"MissingArgument",option);
1161             if (IsGeometry(argv[i]) == MagickFalse)
1162               ThrowImportInvalidArgumentException(option,argv[i]);
1163             snapshots=atol(argv[i]);
1164             break;
1165           }
1166         if (LocaleCompare("strip",option+1) == 0)
1167           break;
1168         if (LocaleCompare("support",option+1) == 0)
1169           {
1170             i++;  /* deprecated */
1171             break;
1172           }
1173         ThrowImportException(OptionError,"UnrecognizedOption",option);
1174       }
1175       case 't':
1176       {
1177         if (LocaleCompare("thumnail",option+1) == 0)
1178           {
1179             if (*option == '+')
1180               break;
1181             i++;
1182             if (i == (long) argc)
1183               ThrowImportException(OptionError,"MissingArgument",option);
1184             if (IsGeometry(argv[i]) == MagickFalse)
1185               ThrowImportInvalidArgumentException(option,argv[i]);
1186             break;
1187           }
1188         if (LocaleCompare("transparent",option+1) == 0)
1189           {
1190             i++;
1191             if (i == (long) argc)
1192               ThrowImportException(OptionError,"MissingArgument",option);
1193             break;
1194           }
1195         if (LocaleCompare("transparent-color",option+1) == 0)
1196           {
1197             if (*option == '+')
1198               break;
1199             i++;
1200             if (i == (long) (argc-1))
1201               ThrowImportException(OptionError,"MissingArgument",option);
1202             break;
1203           }
1204         if (LocaleCompare("treedepth",option+1) == 0)
1205           {
1206             quantize_info->tree_depth=0;
1207             if (*option == '+')
1208               break;
1209             i++;
1210             if (i == (long) argc)
1211               ThrowImportException(OptionError,"MissingArgument",option);
1212             if (IsGeometry(argv[i]) == MagickFalse)
1213               ThrowImportInvalidArgumentException(option,argv[i]);
1214             quantize_info->tree_depth=(unsigned long) atol(argv[i]);
1215             break;
1216           }
1217         if (LocaleCompare("trim",option+1) == 0)
1218           break;
1219         if (LocaleCompare("type",option+1) == 0)
1220           {
1221             long
1222               type;
1223
1224             if (*option == '+')
1225               break;
1226             i++;
1227             if (i == (long) argc)
1228               ThrowImportException(OptionError,"MissingArgument",option);
1229             type=ParseMagickOption(MagickTypeOptions,MagickFalse,argv[i]);
1230             if (type < 0)
1231               ThrowImportException(OptionError,"UnrecognizedImageType",argv[i]);
1232             break;
1233           }
1234         ThrowImportException(OptionError,"UnrecognizedOption",option);
1235       }
1236       case 'w':
1237       {
1238         i++;
1239         if (i == (long) argc)
1240           ThrowImportException(OptionError,"MissingArgument",option);
1241         (void) CloneString(&target_window,argv[i]);
1242         break;
1243       }
1244       case 'v':
1245       {
1246         if (LocaleCompare("verbose",option+1) == 0)
1247           break;
1248         if ((LocaleCompare("version",option+1) == 0) ||
1249             (LocaleCompare("-version",option+1) == 0))
1250           {
1251             (void) fprintf(stdout,"Version: %s\n",
1252               GetMagickVersion((unsigned long *) NULL));
1253             (void) fprintf(stdout,"Copyright: %s\n\n",GetMagickCopyright());
1254             break;
1255           }
1256         ThrowImportException(OptionError,"UnrecognizedOption",option);
1257       }
1258       case '?':
1259         break;
1260       default:
1261         ThrowImportException(OptionError,"UnrecognizedOption",option);
1262     }
1263     fire=ParseMagickOption(MagickImageListOptions,MagickFalse,option+1) < 0 ?
1264       MagickFalse : MagickTrue;
1265     if (fire != MagickFalse)
1266       FireImageStack(MagickFalse,MagickTrue,MagickTrue);
1267   }
1268   if (k != 0)
1269     ThrowImportException(OptionError,"UnbalancedParenthesis",argv[i]);
1270   if (i-- != argc)
1271     ThrowImportException(OptionError,"MissingAnImageFilename",argv[i]);
1272   if (image == (Image *) NULL)
1273     ThrowImportException(OptionError,"MissingAnImageFilename",argv[argc-1]);
1274   FinalizeImageSettings(image_info,image,MagickTrue);
1275   status&=WriteImages(image_info,image,filename,exception);
1276   DestroyImport();
1277   return(status != 0 ? MagickTrue : MagickFalse);
1278 #else
1279   (void) argc;
1280   (void) argv;
1281   (void) ThrowMagickException(exception,GetMagickModule(),MissingDelegateError,
1282     "DelegateLibrarySupportNotBuiltIn","`%s' (X11)",image_info->filename);
1283   return(ImportUsage());
1284 #endif
1285 }