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